使用 Elixir 实现微信支付

1,843 阅读2分钟

最近用 Phoenix 在开发「时习」的时候,有个需求是需要实现在微信内的支付系统,发现 Elixir 还没有现成的包,goofansu 的 wechat-elixir 也还未实现支付功能,于是鼓捣出了 github.com/linjunpop/w…

目前支持公众号支付,扫码支付,App 支付。

一个公众号支付的例子

先使用统一下单接口创建微信订单:

{:ok, data} = WechatPay.API.PlaceOrder.request({
  device_info: "WEB",
  body: "Wechat-666",
  attach: nil,
  out_trade_no: "1415757673",
  fee_type: "CNY",
  total_fee: 709,
  spbill_create_ip: "127.0.0.1",
  notify_url: "http://example.com/wechat-pay-callback",
  time_start: 20091225091010,
  time_expire: 20091227091010,
  trade_type: "JSAPI",
  openid: "oUpF8uMuAJO_M2pxb1Q9zNjWeS6o",
})

然后使用 WechatPay.HTML.generate_pay_request(data["prepay_id"]) 来生成 pay request:

%{
  "appId" => "wx2421b1c4370ec43b",
  "timeStamp" => "1395712654",
  "nonceStr" => "e61463f8efa94090b1f366cccfbbb444",
  "package" => "prepay_id=u802345jgfjsdfgsdg888",
  "signType" => "MD5",
  "paySign" => "70EA570631E4BB79628FBCA90534C63FF7FADD89"
 }

然后在客户端使用生成的 pay request 来调用 JavaScript 的接口,就可以向用户收钱啦,如下图:


IMG_1708.PNG

除了公众号支付外的其他功能都是依据文档实现,未在 production 的 app 里测试,如有问题,欢迎反馈。

最后再吐槽下微信:

  • 文档说所有的 API 都有 sandbox 环境,但是事实并非如此,发邮件咨询之后也不了了之。
  • sandbox 环境下的 sign 值不会根据提交数据的 appid 来计算,而永远是一个无法匹配的值,官方也没有给出一个测试可用的 appid 和 appkey,这样 sandbox 环境也没有实用意义
  • 「交易保障」接口文档里写的提交数据需要的字段是 execute_time,然而实际请求服务器要求的字段名却是 execute_time_,末尾多了一个莫名的下划线,发邮件咨询后说会修改,然而到现在还是一样。╮(╯_╰)╭