class Public::OrdersController < ApplicationController
  layout "public"
  http_basic_authenticate_with name: "nico", password: "852321nb", only: :paid_force
  before_filter :check_paybox_integrity!, :only => [:e_trans_cancel, :e_trans_ipn, :e_trans_refuse,:e_trans_effectue]
  protect_from_forgery :except => [:hipay_ipn]
  def billing
    
    @annonce_account = current_annonce_account
    @annonce_account.force_address = true
  end
  
  def new
    @no_search = true
    if params[:credit_product_id]
      @credit_product = CreditProduct.find(params[:credit_product_id])
      @order = Order.new(:devise => Devise.find(@credit_product.devise))
      session[:order] = @order
      session[:order].credit_product = @credit_product
      
      
      
    elsif session[:order]
      @order = Order.new(session[:order])
    else
      
    end
    if params[:with_com]
      @order.with_com = true
      
    elsif
      @order.with_com = false
      
    end
    @annonce_account = current_annonce_account
    @annonce_account.force_address = true
    @order.annonce_account = @annonce_account
    
    if @order.billing_address?
    else
      render :action => :billing
    end
    
    
  end
  
  def create

    
    @order = Order.new session[:order]
    @annonce_account = current_annonce_account
    @order.annonce_account = @annonce_account
    @order.name = current_annonce_account.name
    @order.firstname = current_annonce_account.firstname
    @order.address = current_annonce_account.address
    @order.address2 = current_annonce_account.address2
    @order.cp = current_annonce_account.cp
    @order.city = current_annonce_account.city
    @order.country = current_annonce_account.country
    @order.pro = current_annonce_account.pro
    @order.organisation = current_annonce_account.organisation
    
    
    @order.name = @order.credit_product.name
    @order.description = @order.credit_product.description
    @order.nbr_credits = @order.credit_product.nbr_credits_final(current_annonce_account)
    @order.validity = @order.credit_product.validity
    @order.price_ht = @order.credit_product.price_ht_final(current_annonce_account)
    @order.binary_points = @order.credit_product.binary_points_final(current_annonce_account)
    @order.binary_percentage = @order.credit_product.binary_percentage
    
    @order.nbr_parts = @order.credit_product.nbr_parts_final(current_annonce_account)
    
    @order.with_com = params[:with_com]
    
    if @order.with_com
      @order.com_amount = @order.evaluate_use_coms
      @order.amount_ht = @order.evaluate_price_with_coms_ht
      @order.amount_ttc = @order.evaluate_price_with_coms_ttc
    else

      @order.amount_ht = @order.credit_product.price_ht_final(current_annonce_account)
      @order.amount_ttc = @order.credit_product.price_ttc_final(current_annonce_account)
    end
    
    @order.cgv = params[:order][:cgv]
    @order.retractation = params[:order][:retractation]
    
    if @order.save
      
      #redirect_to paid_public_order_path(@order)
      if @order.with_com
        @commission = current_annonce_account.commissions.new(:commission_type_id => 5, :amount => ((@order.com_amount)*(-1.0)))
        @order.commission = @commission
        @order.save
      end

      if @order.amount_ht ==  0
        @order.paid = true
        @order.paid_at = Time.now
        @order.payment_type_id = 3
  
        @order.save
        @order.after_paid(true)
  
        
      end

      

          
  	else
  		render :action => "new" 
  	end
    
    
  end

  def paid
    @order = current_annonce_account.orders.find(params[:id])
    
    if @order.devise_id == 1
      
      if Rails.env.development?

      @host_ts = "http://localhost:3000"
      @server_host = "https://preprod-tpeweb.e-transactions.fr/cgi/MYchoix_pagepaiement.cgi"
      @key = "a828b1a278581b8296aba818b9f3252f125a96ebe34d0f83fabd523dee60ca6dfed109c266d4b0a540ecc479c59c44846fe399756c267344f548e07e7a29f99f"

      elsif Rails.env.production? 
      @host_ts = "https://sideplace.com"
      @server_host = "https://tpeweb.e-transactions.fr/cgi/MYchoix_pagepaiement.cgi"
      @key = "11003ee0bd90d3adc4df6a7a8f80e804079c0630b87fc8ad6f504ac4655224fb990e4d043d7f605454a229b7dd937dcece3a4d4e7115f01d686ddb6856f925ab"
      end
    
    
    
    
    
      require "time"
      require "openssl"
      require "base64"
      require "rack"
    
      options = {
                    :site => "1351265", 
                    :rang => "01", 
                    :identifiant => "277631463",
                    :total => (@order.amount_ttc*100).to_i.to_s,
                    :devise => "978",
                    :cmd => @order.id.to_s+"-"+SecureRandom.hex(3).to_s,
                    :porteur => @order.annonce_account.email,
                    :retour => "M:M;Ref:R;T:T;A:A;B:B;C:C;D:D;E:E;F:F;G:G;H:H;I:I;J:J;N:N;O:O;P:P;Q:Q;S:S;U:U;W:W;Y:Y;Z:Z;sign:K;",
                    :annule => "#{@host_ts}/public/orders/e_trans_cancel",
                    :effectue => "#{@host_ts}/public/orders/e_trans_effectue",
                    :refuse => "#{@host_ts}/public/orders/e_trans_refuse",
                    :repondre_a => "#{@host_ts}/public/orders/e_trans_ipn"

      
      }
      #Generation Hash + HMAC
        formatted_options = Hash[options.map { |k, v| ["PBX_#{k.to_s.upcase}", v] }]
        formatted_options["PBX_HASH"] = "SHA512"

        date_iso = Time.now.utc.iso8601
        formatted_options["PBX_TIME"] = date_iso

        base_params_query = formatted_options.to_a.map { |a| a.join("=") }.join("&")

        key = @key

        binary_key = [key].pack("H*")
        signature = OpenSSL::HMAC.hexdigest(OpenSSL::Digest::Digest.new('sha512'),
                    binary_key, base_params_query).upcase

        formatted_options["PBX_HMAC"] = signature

        formatted_options
        @base_params_query = base_params_query
      
      @paybox_hash = formatted_options
      
    else
      
      
      
    end
    
  end
  
  def hipay_confirm
    @order = current_annonce_account.orders.find(params[:id])
    
    flash[:notice] = "Merci pour votre paiement, si votre nombre de crédits n'a pas encore augmenté pas d'inquiétudes, cela peut prendre quelques minutes, merci de ré-actualiser la page."
    redirect_to public_my_account_path
    
  end
  
  def hipay_decline
    @order = current_annonce_account.orders.find(params[:id])
    
    flash[:notice] = "Votre paiement n'a pas abouti, merci de bien vouloir essayer de nouveau ou nous contacter."
    redirect_to paid_public_order_path(@order)
  end
  
  def paid_by_hipay
    @order = current_annonce_account.orders.find(params[:id])
    
    if Rails.env.development?
    @host_sp = "http://78.245.74.12"
    @host_hipay = "https://test-ws.hipay.com/soap/payment-v2?wsdl"
    @host_hipay = "https://ws.hipay.com/soap/payment-v2?wsdl"
    elsif Rails.env.production? 
      @host_sp = "https://sideplace.com"
    @host_hipay = "https://ws.hipay.com/soap/payment-v2?wsdl"
  
    end
    
     
    
    
    @client = Savon.client(wsdl: @host_hipay, ssl_version: :TLSv1)

    @client.operations
    
    message = {
      
      
      :categoryId => 644,
      :amount => @order.amount_ttc,
      :rating => "ALL",
      :locale => "fr_FR",
      :customerIpAddress => request.ip,
      :merchantReference => @order.id ,
      :description => "Commande de crédits d'annonce" ,
      :executionDate => Time.now.to_s(:db),
      :manualCapture => 0,
      :customerEmail => @order.annonce_account.email,
      :urlCallback => @host_sp+hipay_ipn_public_orders_path(),
      :urlAccept => @host_sp+hipay_confirm_public_order_path(@order),
      :urlDecline => @host_sp+hipay_decline_public_order_path(@order),
      :urlCancel => @host_sp+paid_public_order_path(@order),
      :urlLogo => "https://sideplace.com/black_logo.png",
     
      
    }
    
    if @order.devise.code == "USD"
      message[:currency] = @order.devise.code
      message[:wsLogin] = "10850b5beb65cbfacbd748fa231652f2" 
      message[:wsPassword] = "6df1b0ad1c55a1e511e33e7bc42ee3cc"
      message[:websiteId] = 283694
      
    elsif @order.devise.code == "CAD"
      message[:currency] = @order.devise.code
      message[:wsLogin] = "4b914f9a84e773fa07aff82ed896dd9c" 
      message[:wsPassword] = "26d098a1d239dca34c9c3aaf151a8673"
      message[:websiteId] = 285311
    
    elsif @order.devise.code == "GBP"
      message[:currency] = @order.devise.code
      message[:wsLogin] = "8dfff4b14fb9fd7e79b79e50e22fe242" 
      message[:wsPassword] = "7cd17cec7bbfccacfc96ff5f3710eb22"
      message[:websiteId] = 285319
      
    elsif @order.devise.code == "CHF"
      message[:currency] = @order.devise.code
      message[:wsLogin] = "9c8bb8673a712c6bb4a2e3c89f760e98" 
      message[:wsPassword] = "cff22a090bed10e0001754fb724c7843"
      message[:websiteId] = 285320
      
    elsif @order.devise.code == "AUD"
      message[:currency] = @order.devise.code
      message[:wsLogin] = "22804a107d27702252ae8833fcc98b5e" 
      message[:wsPassword] = "6b764308b87aef21a0ca7e88810d96e0"
      message[:websiteId] = 285345
      
    elsif @order.devise.code == "EUR"
      message[:currency] = @order.devise.code
      message[:wsLogin] = "cb9db4d771d58fa1354747f8891c3875" 
      message[:wsPassword] = "52d67e65baa8bd436a5dcbc7f3764efc"
      message[:websiteId] = 320499
      

    
    end
    
    

    
    
    
    
    
    
    @response = @client.call(:generate, :message => {:parameters => message})

    @response.body
    # => { find_user_response: { id: 42, name: 'Hoff' } }
    if @response.body[:generate_response][:generate_result][:redirect_url] and @response.body[:generate_response][:generate_result][:redirect_url].to_s
      redirect_to @response.body[:generate_response][:generate_result][:redirect_url].to_s
    end
  end
  
  def hipay_ipn
    data = Hash.from_xml(params[:xml])
    @result = data["mapi"]["result"]
    logger.info "test"
    logger.debug @result
    logger.info "test"
    @order = Order.find(@result["idForMerchant"])
    logger.debug @order
    
    
    @hipay_history = @order.hipay_histories.new
    
    @hipay_history[:operation] = @result["operation"]
    @hipay_history[:status] = @result["status"]
    @hipay_history[:transaction_date] = @result["date"].to_s+" "+@result["time"].to_s
    @hipay_history[:origamount] = @result["origAmount"]
    @hipay_history[:origcurrency] = @result["origCurrency"]
    @hipay_history[:idformerchant] = @result["idForMerchant"]
    @hipay_history[:emailclient] = @result["emailClient"]
    @hipay_history[:idclient] = @result["idClient"]
    @hipay_history[:merchantdatas] = @result["merchantDatas"]
    @hipay_history[:cardcountry] = @result["cardCountry"]
    @hipay_history[:ipcountry] = @result["ipCountry"]
    @hipay_history[:transid] = @result["transid"]
    @hipay_history[:is3ds] = @result["is3ds"]
    @hipay_history[:paymentmethod] = @result["paymentMethod"]
    @hipay_history[:customercountry] = @result["customerCountry"]
    @hipay_history[:returncode] = @result["returnCode"]
    @hipay_history[:returndescriptionshort] = @result["returnDescriptionShort"]
    @hipay_history[:returndescriptionlong] = @result["returnDescriptionLong"]
    
    @hipay_history.save
    
    if @hipay_history.operation == "capture" and @hipay_history.status == "ok"
      @order.paid = true
      @order.paid_at = Time.now
      @order.payment_type_id = 6
  
      @order.save
      @order.after_paid
    else
      
    end
    render :inline => "ok"
    
    
  end
  
  def e_trans_cancel
    params[:order_id] =params[:Ref].split('-')[0] 
    @order = current_annonce_account.orders.find(params[:order_id])
    @etrans_history = EtransHistory.create(
    :order => @order,
      :M => params[:M],
      :R => params[:Ref],
      :T => params[:T],
      :A => params[:A],
      :B => params[:B],
      :C => params[:C],
      :D => params[:D],
      :E => params[:E],
      :F => params[:F],
      :G => params[:G],
      :H  => params[:H],
      :I => params[:I],
      :J => params[:J],
      :K => params[:K],
      :N => params[:N],
      :O => params[:O],
      :P => params[:P],
      :Q => params[:Q],
      :S  => params[:S],
      :U  => params[:U],
      :W => params[:W],
      :Y => params[:Y],
      :Z  => params[:Z]
    )
  end
  
  def e_trans_refuse
    params[:order_id] =params[:Ref].split('-')[0] 
    @order = current_annonce_account.orders.find(params[:order_id])
    @etrans_history = EtransHistory.create(
    :order => @order,
      :M => params[:M],
      :R => params[:Ref],
      :T => params[:T],
      :A => params[:A],
      :B => params[:B],
      :C => params[:C],
      :D => params[:D],
      :E => params[:E],
      :F => params[:F],
      :G => params[:G],
      :H  => params[:H],
      :I => params[:I],
      :J => params[:J],
      :K => params[:K],
      :N => params[:N],
      :O => params[:O],
      :P => params[:P],
      :Q => params[:Q],
      :S  => params[:S],
      :U  => params[:U],
      :W => params[:W],
      :Y => params[:Y],
      :Z  => params[:Z]
    )
    
  end
  
  def e_trans_ipn
    params[:order_id] =params[:Ref].split('-')[0] 
    @order = Order.find(params[:order_id])
    
    
    
    if !@order.paid and params[:E] == "00000"
      
      @etrans_history = EtransHistory.create(
      :order => @order,
        :M => params[:M],
        :R => params[:Ref],
        :T => params[:T],
        :A => params[:A],
        :B => params[:B],
        :C => params[:C],
        :D => params[:D],
        :E => params[:E],
        :F => params[:F],
        :G => params[:G],
        :H  => params[:H],
        :I => params[:I],
        :J => params[:J],
        :K => params[:K],
        :N => params[:N],
        :O => params[:O],
        :P => params[:P],
        :Q => params[:Q],
        :S  => params[:S],
        :U  => params[:U],
        :W => params[:W],
        :Y => params[:Y],
        :Z  => params[:Z]
      )
      
      @order.paid = true
      @order.paid_at = Time.now
      @order.payment_type_id = 2
  
      @order.save
      @order.after_paid
    end
    
    render :inline => "OK"
    

  end
  
  def e_trans_effectue
    params[:order_id] =params[:Ref].split('-')[0] 
    @order = current_annonce_account.orders.find(params[:order_id])
    
    
    
    if !@order.paid and params[:E] == "00000"
      
      @etrans_history = EtransHistory.create(
      :order => @order,
        :M => params[:M],
        :R => params[:Ref],
        :T => params[:T],
        :A => params[:A],
        :B => params[:B],
        :C => params[:C],
        :D => params[:D],
        :E => params[:E],
        :F => params[:F],
        :G => params[:G],
        :H  => params[:H],
        :I => params[:I],
        :J => params[:J],
        :K => params[:K],
        :N => params[:N],
        :O => params[:O],
        :P => params[:P],
        :Q => params[:Q],
        :S  => params[:S],
        :U  => params[:U],
        :W => params[:W],
        :Y => params[:Y],
        :Z  => params[:Z]
      )
      
      @order.paid = true
      @order.paid_at = Time.now
      @order.payment_type_id = 2
  
      @order.save
      @order.after_paid
    end
    
  end
  
  
  def paid_force
    
      @order = current_annonce_account.orders.find(params[:id])
      if !@order.paid
        @order.paid = true
        @order.paid_at = Time.now
        @order.payment_type_id = 1
  
        @order.save
        @order.after_paid(true)
      end
      
    redirect_to public_my_account_path
  
  end
  
  
  def bill_print_od
    @order = current_annonce_account.orders.find(params[:id])
    
    render :layout => false
    
    
    
   
    
  end
  
  
  def bill_print
    @order = current_annonce_account.orders.find(params[:id])
    
      @temp_file = "#{Rails.root}/pdf/order_bills/#{@order.bill_number}_temp.pdf"
      @final_file = "#{Rails.root}/pdf/order_bills/#{@order.bill_number}.pdf"
    
    
      view = ActionView::Base.new(Rails.root.join('app/views'))
      view.class.include ApplicationHelper
      view.class.include Rails.application.routes.url_helpers

      pdf = view.render( 
              :pdf => "#{@order.bill_number}",
              :template => "public/orders/bill_print.html.haml",  
              
              :locals => {:@order => @order})
                                          
      # then save to a file
      pdf = WickedPdf.new.pdf_from_string(pdf, :margin =>  {   top:               0,                     # default 10 (mm)
                                          bottom:            0,
                                          left:              0,
                                          right:             0 })

      save_path = @temp_file
      File.open(save_path, 'wb') do |file|
      file << pdf
      end
      
      
      
      require 'posix/spawn'
     
      ::POSIX::Spawn::Child.new 'pdftk', @temp_file, 'background', Rails.root.join('pdf_stamp', 'orders.pdf').to_s, 'output',  @final_file
    
      #pdftk /Users/nico/Dev/sideplace_app.old/pdf/order_bills/SP20150700003.pdf background fond.pdf output sortie.pdf
      
      
      
      
      @data_to_send = File.open( @final_file).read
      
      send_data @data_to_send, :filename =>"facture.pdf" , :type => 'application/pdf',:disposition => (params[:inline] ? 'inline' : "attachment")
  
  
  end
  
  def bills
    @no_search = true
  end
  
  protected
  
  def check_paybox_integrity!
      
      render :inline => "Bad response" unless params[:sign].present?
      request_fullpath = request.fullpath

      request_params = request_fullpath[request_fullpath.index("?")+1..request_fullpath.index("&sign")-1]
      request_sign = request_fullpath[request_fullpath.index("&sign")+6..-1]

      digest = OpenSSL::Digest::SHA1.new
      public_key = OpenSSL::PKey::RSA.new(File.read(Rails.root.join('pubkey.pem')))

      @verif = public_key.verify(digest, Base64.decode64(Rack::Utils.unescape(request_sign)), request_params)
      
      if !@verif
        render :inline => "Bad integrity test"
      end
      
  end
  


end
