最近在搞微信公众号支付,即用户在 h5 页面通过 jssdk 发起支付请求,看了下文档
wx.chooseWXPay({
timestamp: 0, // 支付签名时间戳,注意微信jssdk中的所有使用timestamp字段均为小写。但最新版的支付后台生成签名使用的timeStamp字段名需大写其中的S字符
nonceStr: '', // 支付签名随机串,不长于 32 位
package: '', // 统一支付接口返回的prepay_id参数值,提交格式如:prepay_id=***)
signType: '', // 签名方式,默认为'SHA1',使用新版支付需传入'MD5'
paySign: '', // 支付签名
success: function (res) {
// 支付成功后的回调函数
}
});
这里的 package 需要从统一支付接口拿到,所以在代码里按照文档要求先去请求了统一支付接口
def self.random_string
chars = ("a".."z").to_a + ("A".."Z").to_a + ("0".."9").to_a
newpass = ""
1.upto(16) { |i| newpass << chars[rand(chars.size-1)] }
return newpass
end
def self.generate_sign(hash)
stringA = hash.sort.map{|e| e.join('=')}.join('&')
stringSignTemp = stringA + "&key=#{Wechart.apikey}"
sign = Digest::MD5.hexdigest(stringSignTemp).upcase
return sign
end
def self.unifiedorder(opt)
param = {
appid:self.appid,
mch_id:self.mch_id,
nonce_str:self.random_string,
body:opt[:body],
out_trade_no:opt[:trade],
total_fee:opt[:total_fee].to_i * 100,
spbill_create_ip:opt[:ip],
notify_url:self.notify_url,
trade_type:'JSAPI',
openid:opt[:openid]
}
sign = generate_sign(param)
param.merge!({sign:sign})
builder = Nokogiri::XML::Builder.new(:encoding => 'UTF-8') do |xml|
xml.root {
xml.appid param[:appid]
xml.mch_id param[:mch_id]
xml.nonce_str self.random_string
xml.sign sign
xml.body param[:body]
xml.out_trade_no param[:out_trade_no]
xml.total_fee param[:total_fee]
xml.spbill_create_ip param[:spbill_create_ip]
xml.notify_url param[:notify_url]
xml.trade_type param[:trade_type]
xml.openid param[:openid]
}
end
uri = URI.parse("https://api.mch.weixin.qq.com/pay/unifiedorder")
Net::HTTP.start(uri.host,uri.port,use_ssl:true) do |http|
request = Net::HTTP::Post.new(uri.path)
request.body = builder.to_xml
response = http.request(request)
res = Nokogiri::XML(response.body,nil,'UTF-8')
end
end
上述方法的入口是 unifiedorder 这个函数,在 console 里面测试,一直返回错误信息:
#<Nokogiri::XML::Document:0x2d42798 name="document" children=[#<Nokogiri::XML::Element:0x2d41244 name="xml" children=[#<Nokogiri::XML::Element:0x2d4072c name="return_code" children=[#<Nokogiri::XML::CDATA:0x2d3db94 "FAIL">]>, #<Nokogiri::XML::Text:0x2d3ce24 "\n">, #<Nokogiri::XML::Element:0x2d3c820 name="return_msg" children=[#<Nokogiri::XML::CDATA:0x2d33cd4 "appid and openid not match">]>, #<Nokogiri::XML::Text:0x2d33310 "\n">]>]>
看错误提示很明显 appid 和 openid 不匹配,但是没明白是什么意思,不知道 appid 和 openid 怎么扯上关系了,于是各种 google,无果,发到这里请大家帮忙,看 api,支付需要三个步骤:
* 步骤1:网页授权获取用户openid
* 步骤2:使用统一支付接口,获取prepay_id
* 步骤3:使用jsapi调起支付
现在我已经知道了我的个人 openid,所以,第一步省略了,上面的代码直接列出的是第二步,一直是这个错误,不知道各路高手是怎么解决的,求答案