Django应用集成PayPal结账报错:需传递订单ID
解决PayPal结账"Expected an order id to be passed"报错问题
我开发了一个Django应用,在通过PayPal结账创建订单时,一直报错:"Uncaught Error: Expected an order id to be passed"。订单和收货地址已经在后端成功创建,但PayPal无法识别。尝试了多种方法仍未解决,求解决方案,当前使用的脚本如下:
<script> paypal.Buttons({ // Order is created on the server and the order id is returned createOrder: function() { // Call the /get_cart_id/ endpoint to get the cart id return fetch('/get_cart_id/') .then(function(response) { return response.json(); }) .then(function(data) { var cartId = data.cart_id; return fetch('/api/orders/', { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-CSRFToken': csrftoken }, body: JSON.stringify({ cart_id: cartId }) }) .then(function(response) { return response.json(); }) .then(function(order) { // Call the Checkout function to handle the order var shippingInfo = { house: form.house.value, street: form.street.value, city: form.city.value, postcode: form.postcode.value }; return fetch('/get_shipping_address/', { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-CSRFToken': csrftoken }, body: JSON.stringify({ shipping: shippingInfo }) }) .then(function(response) { return response.json(); }) .then(function(data) { console.log('Success:', data); alert('Transaction completed'); }); }); }); }, // Finalize the transaction on the server after payer approval onApprove: function(data) { return fetch(`/api/orders/${orderId}/`, { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-CSRFToken': csrftoken }, body: JSON.stringify({ order_id: data.orderId }) }) .then(function(response) { return response.json(); }) .then(function(orderData) { // Successful capture! For dev/demo purposes: console.log('Capture result', orderData, JSON.stringify(orderData, null, 2)); var transaction = orderData.purchase_units[0].payments.captures[0]; alert(`Transaction ${transaction.status}: ${transaction.id}\n\nSee console for all available details`); // When ready to go live, remove the alert and show a success message within this page. For example: // var element = document.getElementById('paypal-button-container'); // element.innerHTML = '<h3>Thank you for your payment!</h3>'; // Or go to another URL: window.location.href = 'thank_you.html'; }); } }).render('#paypal-button-container'); </script>
问题根源
createOrder未返回PayPal订单ID:PayPal按钮组件要求createOrder必须返回由PayPal生成的有效订单ID,你的代码最后返回的是收货地址接口的响应,完全没把后端创建的PayPal订单ID传给组件,导致PayPal无法识别订单。onApprove中orderId未定义:onApprove里用了orderId变量,但这个变量在当前作用域根本不存在,应该使用PayPal返回的data.orderId。
修改后的脚本
<script> paypal.Buttons({ // 从后端创建PayPal订单并返回订单ID createOrder: function() { // 获取购物车ID return fetch('/get_cart_id/') .then(function(response) { return response.json(); }) .then(function(data) { var cartId = data.cart_id; // 创建订单(后端需返回PayPal生成的order_id) return fetch('/api/orders/', { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-CSRFToken': csrftoken }, body: JSON.stringify({ cart_id: cartId }) }) .then(function(response) { return response.json(); }) .then(function(order) { // 处理收货地址 var shippingInfo = { house: form.house.value, street: form.street.value, city: form.city.value, postcode: form.postcode.value }; return fetch('/get_shipping_address/', { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-CSRFToken': csrftoken }, body: JSON.stringify({ shipping: shippingInfo }) }) .then(function() { // 关键:返回PayPal订单ID给按钮组件 return order.paypal_order_id; // 请根据后端实际返回的字段名修改 }); }); }); }, // 用户批准后完成交易 onApprove: function(data) { // 使用PayPal返回的data.orderId,替换未定义的orderId return fetch(`/api/orders/${data.orderId}/`, { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-CSRFToken': csrftoken }, body: JSON.stringify({ order_id: data.orderId }) }) .then(function(response) { return response.json(); }) .then(function(orderData) { console.log('Capture result', orderData, JSON.stringify(orderData, null, 2)); var transaction = orderData.purchase_units[0].payments.captures[0]; alert(`Transaction ${transaction.status}: ${transaction.id}\n\n详情请查看控制台`); // 上线后可替换为成功提示 // var element = document.getElementById('paypal-button-container'); // element.innerHTML = '<h3>感谢您的付款!</h3>'; // 或跳转页面:window.location.href = 'thank_you.html'; }); } }).render('#paypal-button-container'); </script>
额外注意事项
- 确认后端
/api/orders/接口创建PayPal订单后,返回包含PayPal订单ID的JSON(例如{"paypal_order_id": "XXX"}),你需要根据后端实际返回的字段名调整return order.paypal_order_id这一行。 - 收货地址的处理不要阻塞
createOrder返回订单ID,PayPal需要先拿到订单ID才能加载结账界面,也可以选择在创建订单时就把地址信息传给后端,减少一次请求。 - 检查后端创建PayPal订单的逻辑,确保确实调用了PayPal官方API生成了有效订单ID,而不是仅创建了本地订单记录。
内容的提问来源于stack exchange,提问作者David Henson
相关产品推荐
相关产品推荐

