Blazor WebAssembly接入PayPal调用JS方法提示undefined问题咨询
Blazor WebAssembly接入PayPal支付报错解决方案
报错信息
Microsoft.AspNetCore.Components.WebAssembly.Rendering.WebAssemblyRenderer[100]
Unhandled exception rendering component: Could not find 'initPayPalButton' ('initPayPalButton' was undefined).
Error: Could not find 'initPayPalButton' ('initPayPalButton' was undefined).
问题原因&修复方案
1. 全局方法未挂载到window对象
Blazor的IJSRuntime默认只会从window全局作用域查找调用的JS方法,你当前直接声明的initPayPalButton函数没有显式挂载到window上,部分场景下函数作用域被限制就会出现找不到的问题。
- 修复方式:将函数定义改为
window.initPayPalButton = function() { /* 原有逻辑 */ }
2. 脚本加载顺序错误
如果PayPal SDK脚本和自定义JS脚本放在了blazor.webassembly.js的引用之后,Blazor启动完成调用JS方法时,你的自定义函数还没有被加载解析,也会触发未定义报错。
- 修复方式:将两个JS脚本都放到
index.html的<head>标签内,或者放在<body>里blazor.webassembly.js引用的前面,保证Blazor启动前JS方法已经注册到全局。
3. 原有JS代码存在语法逻辑问题
你当前的JS代码里还有两处潜在错误,即使解决了方法找不到的问题,后续运行也会报错:
var quantity = parseInt();未给parseInt传参数,返回NaN会导致后续计算错误- 你注释了
itemOptions的DOM获取逻辑,直接赋值为数字3,后续调用itemOptions.options会因为数字没有该属性直接报错
修正后代码示例
index.html 中的JS代码
<script src="https://www.paypal.com/sdk/js?client-id=MY-CLIENT-CODE"></script> <script> // 显式挂载到window对象,供Blazor调用 window.initPayPalButton = function() { var shipping = 0; // 测试阶段先写死商品信息,后续替换为实际业务逻辑 var selectedItemDescription = "测试商品"; var selectedItemPrice = 9.9; var quantity = 1; var orderDescription = 'Fund'; if (orderDescription === '') { orderDescription = 'Item'; } paypal.Buttons({ style: { shape: 'rect', color: 'blue', layout: 'vertical', label: 'paypal', }, createOrder: function (data, actions) { var tax = 0; tax *= quantity; tax = Math.round(tax * 100) / 100; var priceTotal = quantity * selectedItemPrice + parseFloat(shipping) + tax; priceTotal = Math.round(priceTotal * 100) / 100; var itemTotalValue = Math.round((selectedItemPrice * quantity) * 100) / 100; return actions.order.create({ purchase_units: [{ description: orderDescription, amount: { currency_code: 'USD', value: priceTotal, breakdown: { item_total: { currency_code: 'USD', value: itemTotalValue, }, shipping: { currency_code: 'USD', value: shipping, }, tax_total: { currency_code: 'USD', value: tax, } } }, items: [{ name: selectedItemDescription, unit_amount: { currency_code: 'USD', value: selectedItemPrice, }, quantity: quantity }] }] }); }, onApprove: function (data, actions) { return actions.order.capture().then(function (details) { alert('Transaction completed by ' + details.payer.name.given_name + '!'); }); }, onError: function (err) { console.log(err); }, }).render('#paypal-button-container'); } </script>
Razor页面代码
@inject IJSRuntime JSRuntime <div id="paypal-button-container"></div> @code { protected override async Task OnAfterRenderAsync(bool firstRender) { if (firstRender) { await JSRuntime.InvokeVoidAsync("initPayPalButton"); // 无UI更新需求可删除StateHasChanged调用 } } }
内容的提问来源于stack exchange,提问作者T0bi
相关产品推荐
相关产品推荐

