module UnionpayApp::Service
Public Class Methods
get_public_key_by_cert_id(cert_id)
click to toggle source
银联支付 根据证书id返回公钥
# File lib/unionpay_app/service.rb, line 61 def self.get_public_key_by_cert_id cert_id certificate = OpenSSL::X509::Certificate.new(UnionpayApp.cer) #读取cer文件 certificate.serial.to_s == cert_id ? certificate.public_key.to_s : nil #php 返回的直接是cer文件 UnionpayApp.cer end
post(union_params)
click to toggle source
# File lib/unionpay_app/service.rb, line 34 def self.post union_params request = Typhoeus::Request.new(UnionpayApp.uri, method: :post, params: union_params[:sign], ssl_verifypeer: false, headers: {'Content-Type' =>'application/x-www-form-urlencoded'} ) request.run if request.response.success? tn = Hash[*request.response.body.split("&").map{|a| a.gsub("==", "@@").split("=")}.flatten]['tn'] else tn = "" end end
query(order_id, txnTime)
click to toggle source
# File lib/unionpay_app/service.rb, line 66 def self.query order_id, txnTime union_params = { :version => '5.0.0', #版本号 :encoding => 'utf-8', #编码方式 :certId => UnionpayApp.cert_id, #证书ID :signMethod => '01', #签名方法 :txnType => '00', #交易类型 :txnSubType => '00', #交易子类 :bizType => '000000', #业务类型 :accessType => '0', #接入类型 :channelType => '07', #渠道类型 :orderId => order_id, #请修改被查询的交易的订单号 :merId => UnionpayApp.mer_id, #商户代码,请修改为自己的商户号 :txnTime => txnTime, #请修改被查询的交易的订单发送时间 } data = Digest::SHA1.hexdigest(union_params.sort.map{|key, value| "#{key}=#{value}" }.join('&')) sign = Base64.encode64(OpenSSL::PKey::RSA.new(UnionpayApp.private_key).sign('sha1', data.force_encoding("utf-8"))).gsub("\n", "") request = Typhoeus::Request.new(UnionpayApp.query_uri, method: :post, params: union_params.merge(signature: sign), ssl_verifypeer: false, headers: {'Content-Type' =>'application/x-www-form-urlencoded'} ) request.run if request.response.success? code = Hash[*request.response.body.split("&").map{|a| a.gsub("==", "@@").split("=")}.flatten]['origRespCode'] elsif request.response.timed_out? code = "got a time out" elsif request.response.code == 0 code = request.response.return_message else code = request.response.code.to_s end end
sign(txtAmt, orderId)
click to toggle source
银联支付签名
# File lib/unionpay_app/service.rb, line 10 def self.sign txtAmt, orderId union_params = { :version => "5.0.0", :encoding => "utf-8", :certId => UnionpayApp.cert_id, :txnType => '01', :txnSubType => "01", :bizType => "000201", :channelType => "08", :frontUrl => UnionpayApp.front_url, :backUrl => UnionpayApp.back_url, :accessType => "0", :merId => UnionpayApp.mer_id, :orderId => orderId, #商户订单号 :txnTime => Time.now.strftime("%Y%m%d%H%M%S"), #订单发送时间 :txnAmt => txtAmt, #以分为单位 :currencyCode => '156', :signMethod => '01', } data = Digest::SHA1.hexdigest(union_params.sort.map{|key, value| "#{key}=#{value}" }.join('&')) sign = Base64.encode64(OpenSSL::PKey::RSA.new(UnionpayApp.private_key).sign('sha1', data.force_encoding("utf-8"))).gsub("\n", "") {time: union_params[:txnTime], sign: union_params.merge(signature: sign)} end
verify(params)
click to toggle source
银联支付验签
# File lib/unionpay_app/service.rb, line 45 def self.verify params if get_public_key_by_cert_id params['certId'] public_key = get_public_key_by_cert_id params['certId'] signature_str = params['signature'] p = params.reject{|k, v| k == "signature"}.sort.map{|key, value| "#{key}=#{value}" }.join('&') signature = Base64.decode64(signature_str) data = Digest::SHA1.hexdigest(p) key = OpenSSL::PKey::RSA.new public_key digest = OpenSSL::Digest::SHA256.new key.verify digest, signature, data else false end end