@blocklet/payment-react
Version:
Reusable react components for payment kit v2
163 lines (125 loc) • 7.8 kB
Markdown
`CheckoutForm` 组件是处理支付链接和结账会话的主要入口点。它作为一个高级封装器,根据提供的 ID 获取所有必要数据,并渲染相应的支付或捐赠界面。此组件是将完整的结账流程集成到您的应用程序中的最简单方法。
必须用 `PaymentProvider` 包裹 `CheckoutForm` 或其任何父组件,以确保它能访问必要的上下文,例如会话信息和 API 配置。更多详情,请参阅 [PaymentProvider 文档](./providers-payment-provider.md)。
该组件协调整个结账流程:
1. **初始化**:它通过 `paymentLink` ID(前缀为 `plink_`)或 `checkoutSession` ID(前缀为 `cs_`)进行挂载。
2. **数据获取**:它与支付后端通信,以检索所有必要的上下文,包括支付方式、订单项和客户详细信息。
3. **UI 渲染**:根据 `formType` 属性,它在内部渲染标准的 `Payment` 组件或专门的 `DonationForm` 组件。
4. **状态管理**:它处理支付的整个生命周期,包括加载状态、完成状态和错误处理。
```d2 CheckoutForm 的基本流程 icon=lucide:workflow
direction: down
shape: sequence_diagram
User-Action: {
shape: c4-person
label: "用户"
}
Application: {
label: "你的 React 应用"
CheckoutForm-Component: {
label: "CheckoutForm"
}
Payment-Component: {
label: "Payment 组件"
}
Donation-Component: {
label: "DonationForm 组件"
}
}
Payment-API: {
label: "支付后端 API"
shape: cylinder
}
User-Action -> Application.CheckoutForm-Component: "1. 使用 'id' 属性挂载"
Application.CheckoutForm-Component -> Payment-API: "2. 获取会话数据"
Payment-API -> Application.CheckoutForm-Component: "3. 返回结账上下文"
alt "如果 formType 是 'payment'" {
Application.CheckoutForm-Component -> Application.Payment-Component: "4. 渲染支付 UI"
}
alt "如果 formType 是 'donation'" {
Application.CheckoutForm-Component -> Application.Donation-Component: "5. 渲染捐赠 UI"
}
User-Action -> Application.Payment-Component: "6. 完成支付"
User-Action -> Application.Donation-Component: "7. 完成捐赠"
```
`CheckoutForm` 组件接受以下属性:
| 属性 | 类型 | 必填 | 默认值 | 描述 |
|---------------|----------------------------------------------------------------------------|----------|---------------|-------------------------------------------------------------------------------------------------------------------------|
| `id` | `string` | 是 | - | 支付链接(`plink_...`)或结账会话(`cs_...`)的唯一标识符。 |
| `mode` | `'standalone'` \| `'inline'` \| `'popup'` \| `'inline-minimal'` \| `'popup-minimal'` | 否 | `'inline'` | 定义渲染模式。`'standalone'` 用于全页视图,`'inline'` 用于嵌入容器。 |
| `formType` | `'payment'` \| `'donation'` | 否 | `'payment'` | 决定要渲染的表单类型。使用 `'donation'` 以实现专门的捐赠流程。 |
| `onPaid` | `(res: CheckoutContext) => void` | 否 | - | 支付成功后执行的回调函数。接收最终的结账上下文作为参数。 |
| `onError` | `(err: Error) => void` | 否 | `console.error` | 在流程中发生错误时执行的回调函数。 |
| `onChange` | `(data: CheckoutFormData) => void` | 否 | - | 当任何表单字段值发生变化时触发的回调函数。 |
| `goBack` | `() => void` | 否 | - | 如果提供,则渲染一个返回按钮,并在点击时调用此函数。 |
| `extraParams` | `Record<string, any>` | 否 | `{}` | 从支付链接启动会话时,在 URL 中传递的额外参数对象。 |
| `theme` | `'default'` \| `'inherit'` \| `PaymentThemeOptions` | 否 | `'default'` | 控制组件的主题。`'inherit'` 使用父主题,或者您可以传递一个自定义主题对象。 |
| `action` | `string` | 否 | `''` | 一个字符串标识符,用于自定义 UI 元素(如按钮文本)或跟踪特定流程。 |
这是将支付表单直接嵌入到您的应用程序 UI 中的最常见用例。该组件在内部处理所有逻辑。
```tsx MyStorePage.tsx icon=lucide:shopping-cart
import { PaymentProvider, CheckoutForm } from '@blocklet/payment-react';
import { useSessionContext } from './hooks/session-context'; // 您的应用的会话钩子
export default function MyStorePage() {
const { session, connectApi } = useSessionContext();
const handlePaymentSuccess = (result) => {
console.log('支付成功!', result);
alert('感谢您的购买!');
};
const handlePaymentError = (error) => {
console.error('支付失败:', error);
alert('抱歉,您的支付无法处理。');
};
return (
<PaymentProvider session={session} connectApi={connectApi}>
<div style={{ maxWidth: '960px', margin: '0 auto' }}>
<h1>结账</h1>
<CheckoutForm
id="plink_xxxxxxxxxxxxxx" // 替换为您的支付链接 ID
mode="inline"
onPaid={handlePaymentSuccess}
onError={handlePaymentError}
/>
</div>
</PaymentProvider>
);
}
```
使用 `mode="standalone"` 来渲染一个专用的全页结账体验。这对于将用户重定向到单独页面以完成支付的场景非常理想。
```tsx CheckoutPage.tsx icon=lucide:layout-template
import { PaymentProvider, CheckoutForm } from '@blocklet/payment-react';
import { useSessionContext } from './hooks/session-context';
export default function CheckoutPage() {
const { session, connectApi } = useSessionContext();
const paymentLinkId = 'plink_xxxxxxxxxxxxxx'; // 可从 URL 参数中检索
return (
<PaymentProvider session={session} connectApi={connectApi}>
<CheckoutForm id={paymentLinkId} mode="standalone" />
</PaymentProvider>
);
}
```
通过设置 `formType="donation"`,该组件会渲染一个专为捐赠活动量身定制的 UI,包括金额预设和权益显示等功能。
```tsx DonationPage.tsx icon=lucide:gift
import { PaymentProvider, CheckoutForm } from '@blocklet/payment-react';
import { useSessionContext } from './hooks/session-context';
export default function DonationPage() {
const { session, connectApi } = useSessionContext();
return (
<PaymentProvider session={session} connectApi={connectApi}>
<div style={{ padding: '2rem' }}>
<h2>支持我们的事业</h2>
<CheckoutForm
id="plink_yyyyyyyyyyyyyy" // 替换为您的捐赠链接 ID
formType="donation"
onPaid={() => alert('感谢您的慷慨捐赠!')}
/>
</div>
</PaymentProvider>
);
}
```