我正在编写一个用于处理Paypal IPN消息和响应的监听器。
根据Paypal IPN要求,收听者必须以相同的顺序发回从Paypal收到的值,并在值列表的前面插入新参数“cmd = _notify-validate”。
您的侦听器HTTP将完整的,未经更改的消息发送回PayPal。 注意:此消息必须包含与PayPal中的原始IPN相同的字段,顺序,所有字段都以cmd = _notify-validate开头。此外,此消息必须使用与原始编码相同的编码。
但是,Go的url.Values变量在地图数据结构中实现,每次迭代时,该值的顺序不保证相同。
...在使用范围循环迭代地图时,未指定迭代顺序,并且不保证从一次迭代到下一次迭代“
当调用url.Values编码方法时,它将按键排序
将值编码为按URL排序的“URL编码”形式(“bar = baz& foo = quux”)。
监听器在GAE上运行,因此我使用“appengine / urlfetch”的PostForm函数,它将url.Values作为第二个参数
c := appengine.NewContext(r)
client := urlfetch.Client(c)
resp, err := client.PostForm("https://www.sandbox.paypal.com/cgi-bin/webscr", r.Form)
由于url.Values是一张地图,因此不保证地图中值的顺序是有序的。如何以Paypal IPN收到的相同顺序将参数值传回Paypal并使用GAE urlfetch服务?
答案 0 :(得分:4)
使用Post
代替PostForm
。您可以使用请求中的正文:
var buf bytes.Buffer
buf.WriteString("cmd=_notify-validate&")
io.Copy(&buf, r.Body)
client.Post("http://localhost", "application/x-www-form-urlencoded", &buf)