React Native中集成Flutterwave支付出现usePaymentLink错误如何解决?
问题原因与修复方案
1 报错的核心原因
this.usePaymentLink is not a function报错是因为usePaymentLink不是flutterwave-react-native库提供的内置方法,也不是React类组件的原生API,官方文档示例里仅将它作为支付链接处理逻辑的占位符,需要你自行在组件内实现。
同时你的现有代码还存在几个容易忽略的语法错误:
handlePaymentInitialization方法中使用了await调用异步的FlutterwaveInit,但对应的setState回调函数没有声明async关键字- 组件卸载生命周期函数拼写错误,正确为
componentWillUnmount,你少写了末尾的n AbortController实例化缺少括号,正确写法为new AbortController()- 你没有声明
displayErrorMessage的方法实现,报错时也会触发异常
2 正确实现代码
2.1 前置依赖(如果使用WebView加载支付页)
如果选择在应用内嵌入WebView打开支付链接,需要先安装依赖:npm install react-native-webview
2.2 完整修正代码
import React from 'react'; import {View, TouchableOpacity, Alert, StyleSheet} from 'react-native'; import { WebView } from 'react-native-webview'; import {FlutterwaveInit} from 'flutterwave-react-native'; // 自行实现交易号生成方法 const generateTransactionRef = () => `tx_${Date.now()}_${Math.random().toString(36).substring(2, 10)}`; class MyCart extends React.Component { state = { isPending: false, showPaymentWebview: false, paymentLink: '' } abortController = null; componentWillUnmount() { if (this.abortController) { this.abortController.abort(); } } // 自行实现usePaymentLink方法:存储支付链接,唤起WebView usePaymentLink = (link) => { this.setState({ isPending: false, paymentLink: link, showPaymentWebview: true }) } // 自行实现错误提示方法 displayErrorMessage = (msg) => { Alert.alert('支付失败', msg, [ {text: '确定', onPress: () => this.setState({isPending: false})} ]) } // 回调函数加async关键字 handlePaymentInitialization = () => { this.setState({ isPending: true, }, async () => { // 实例化加括号 this.abortController = new AbortController(); try { const paymentLink = await FlutterwaveInit( { tx_ref: generateTransactionRef(), authorization: '替换为你的商户公钥', amount: 100, currency: 'USD', customer: { email: 'customer-email@example.com', }, payment_options: 'card', }, this.abortController ); return this.usePaymentLink(paymentLink); } catch (error) { if (error.code === 'ABORTERROR') { this.setState({isPending: false}) return; } this.displayErrorMessage(error.message); } }); } // 支付完成/关闭WebView的回调 handleWebViewNavigationStateChange = (navState) => { // 自行判断支付结果回调地址,匹配成功后关闭WebView处理结果 if (navState.url.includes('你的支付回调地址')) { this.setState({ showPaymentWebview: false, paymentLink: '' }) // 后续处理支付成功/失败逻辑 } } render() { const {isPending, showPaymentWebview, paymentLink} = this.state; return ( <View style={styles.container}> { showPaymentWebview && paymentLink ? ( <WebView source={{ uri: paymentLink }} onNavigationStateChange={this.handleWebViewNavigationStateChange} /> ) : ( <> {/* 你的其他购物车页面逻辑 */} <TouchableOpacity style={[ styles.paymentButton, isPending ? styles.paymentButtonBusy : {} ]} disabled={isPending} onPress={this.handlePaymentInitialization} > Pay $100 </TouchableOpacity> </> ) } </View> ) } } const styles = StyleSheet.create({ container: { flex: 1, padding: 20, justifyContent: 'center' }, paymentButton: { backgroundColor: '#f5a623', padding: 15, borderRadius: 8, alignItems: 'center' }, paymentButtonBusy: { opacity: 0.6 } }) export default MyCart;
2.3 替代实现(调用系统浏览器打开支付链接)
如果你不想嵌入WebView,也可以用React Native自带的Linking打开支付链接,只需要修改usePaymentLink的实现:
import { Linking } from 'react-native'; // 修改usePaymentLink实现 usePaymentLink = async (link) => { this.setState({isPending: false}) const supported = await Linking.canOpenURL(link); if (supported) { await Linking.openURL(link); } else { this.displayErrorMessage('无法打开支付页面,请重试') } }
内容的提问来源于stack exchange,提问作者Blessing
相关产品推荐
相关产品推荐

