# SaaS プラットフォームとして、代理店経由で販売 AI チャットエージェントを通じて事業者が商品を販売できるようにする方法をご紹介します。 > プラットフォームでエージェンティックコマースを使用してビジネスの商品を販売する場合は、[ウェイトリストに登録](https://go.stripe.global/agentic-commerce-contact-sales)できます。プラットフォーム向けのエージェンティックコマースは米国のビジネスで利用でき、ウェイトリストの承認が必要です。 エージェンティックコマースを使用すると、連結アカウントが AI チャットエージェントを通じて商品を販売できるようになります。プラットフォームは[商品フィードデータ](https://docs.stripe.com/agentic-commerce/product-feed.md)をアップロードし、税金や手数料に対応するための決済フックを設定します。連結アカウントはエージェントチャネルにオプトインします。買い手がエージェントを通じて購入すると、Stripe は決済を実行し、取引を完了する前にプラットフォームのフックを呼び出します。 プラットフォーム向けエージェンティックコマースフローの概要 (See full diagram at https://docs.stripe.com/connect/saas/tasks/enable-in-context-selling-on-ai-agents) ## プラットフォームを設定する ダッシュボードの[エージェンティックコマース設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページに移動して、プラットフォームの登録を行います。オンボーディングウィザードでは、次の手順が案内されます。 - プラットフォーム用の [Stripe プロフィール](https://docs.stripe.com/get-started/account/profile.md)を作成します。 - 決済方式を選択します (*direct* (A charge type where customers transact directly with a connected account, which is always the merchant of record. With each payment, the connected account pays fees to Stripe and, optionally, to your platform) または *destination* (A charge type where customers transact with your platform for products or services provided by a connected account. Your platform pays Stripe fees and immediately transfers funds to the connected account with each payment) と *on\_behalf\_of* (A parameter that allows a Connect platform to create an indirect payment where the connected account is the merchant of record (MoR)))。 - 連結アカウントが商品を販売できる AI エージェントチャネルを有効にします。 - Webhook エンドポイント、領収書タイプ、サポートポリシーなど、売り手の設定を行います。 オンボーディングが完了すると、これらの設定を同じページから管理できます。 ## 決済方式を選択する コンテキスト内ショッピングフローでは、Stripe がプラットフォーム用のエージェント型決済セッションを作成します。このセッションを作成するには、使用する決済方式を Stripe が把握している必要があります。Stripe は、`on_behalf_of` パラメーターを使用したダイレクト請求とデスティネーション支払いに対応しています。どちらの決済方式でも、連結アカウントが売り手として機能します。 [プラットフォームのオンボーディング](https://docs.stripe.com/connect/saas/tasks/enable-in-context-selling-on-ai-agents.md#set-up-platform)時に決済方式を設定するか、後でダッシュボードの[エージェンティックコマース設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページから更新します。 ## Stripe に商品カタログデータをアップロードする ### 製品カタログを準備する 連結アカウントごとに、[Stripe 製品カタログ仕様](https://docs.stripe.com/agentic-commerce/product-feed.md)に準拠した CSV ファイルを作成します。 ### 商品カタログデータを Stripe にアップロードする 連結アカウントごとに製品カタログデータを個別にアップロードします。15 分ごとに更新を送信できます。本番更新を有効にする前に、サンドボックスを使用して解析、フィールドマッピング、データ品質を検証します。 #### API > [制限付き API キー](https://docs.stripe.com/keys.md#create-restricted-api-key)を使用する場合、**商品カタログのインポート**の書き込み権限が必要です。この権限がない場合、API リクエストは `403` エラーを返します。 連結アカウントの `ProductCatalogImport` を作成します。リクエストが成功すると、[ProductCatalogImport オブジェクト](https://docs.stripe.com/api/v2/commerce/product-catalog-imports/object.md)が `awaiting_upload` 状態で返されます。レスポンスの `status_details.awaiting_upload.upload_url.url` フィールドには、ファイルのアップロード用の署名付き URL が含まれます。アップロード可能な最大サイズは 4 GB です。 ```curl curl -X POST https://api.stripe.com/v2/commerce/product_catalog/imports \ -H "Authorization: Bearer <>" \ -H "Stripe-Version: 2026-06-24.preview" \ -H "Stripe-Account: {{CONNECTEDACCOUNT_ID}}" \ --json '{ "feed_type": "product", "mode": "upsert", "metadata": { "file_name": "march_11_2026_product_upload.csv" } }' ``` ```json { "id": "pcimprt_xxx", "object": "v2.commerce.product_catalog_import", "created": "2026-03-26T00:35:01.000Z", "feed_type": "product", "status": "awaiting_upload", "status_details": { "awaiting_upload": { "upload_url": { "expires_at": "2026-03-26T00:40:02.000Z", "url": "https://stripeusercontent.com/files/us-west-2/upload/wksp_xxx" } } }, "livemode": true } ``` > 署名済みアップロード URL は 5 分後に有効期限が切れます。URL が期限切れになる前に CSV をアップロードしてください。URL が期限切れになった場合は、新しい `ProductCatalogImport` を作成して新しいアップロード URL を取得します。 署名済み URL に CSV をアップロードしてください。ファイルは CSV 形式で、各行が 1 つの商品またはバリアントを表している必要があります。ファイルサイズは最大 4 GB です。 ```curl curl -X PUT \ -H "Content-Type: text/csv" \ --data-binary @"/path/to/your/file.csv" \ "{{PRESIGNED_URL}}" ``` Stripe がファイルを受信すると、インポートは `awaiting_upload` から `processing` に移行します。 ### フィードステータスの監視 Stripe は商品カタログデータを検証してクリーンアップし、インデックスを作成して、AI エージェントが使用できる形式に変換します。[インポートオブジェクト](https://docs.stripe.com/api/v2/commerce/product-catalog-imports/object.md)が最終状態 (`succeeded`、`succeeded_with_errors`、または `failed`) に達するまでポーリングします。 ```curl curl https://api.stripe.com/v2/commerce/product_catalog/imports/{{PRODUCTCATALOGIMPORT_ID}} \ -H "Authorization: Bearer <>" \ -H "Stripe-Version: 2026-06-24.preview" \ -H "Stripe-Account: {{CONNECTEDACCOUNT_ID}}" ``` または、`v2.commerce.product_catalog.imports.succeeded`、`v2.commerce.product_catalog.imports.succeeded_with_errors`、および `v2.commerce.product_catalog.imports.failed` の最終状態を示す Webhook イベントをリッスンすることもできます。Webhook の `related_object.id` にはインポート ID が含まれており、それを使用してオブジェクト全体を取得できます。 インポートがエラーなしで完了すると、`succeeded` 状態になります。ファイルの構造は有効でも、行レベルの検証の問題が含まれる場合、インポートは `succeeded_with_errors` 状態になります。たとえば、ファイルが一度もアップロードされなかった、ファイルを読み取れない、内部エラーが発生したなどの理由でインポートを完了できない場合は、`failed` 状態になります。 インポートのステータスが `succeeded_with_errors` の場合は、エラーファイルをダウンロードできます。 1. レスポンス内の `status_details.succeeded_with_errors.error_file.url` フィールドを探します。 2. 有効期限が切れる前に、その URL から CSV を直接ダウンロードします。 3. CSV には失敗した行のみが含まれ、先頭の `stripe_error_message` 列で各エラーが説明されます。 > エラーファイル URL の有効期限は 5 分後に切れます。新しい URL を取得するには、[取得エンドポイント](https://docs.stripe.com/api/v2/commerce/product-catalog-imports/retrieve.md)を再度呼び出してください。 #### ダッシュボード **連結アカウント**ページに移動してアカウントを選択し、**資金管理**セクションまでスクロールすると、**エージェンティックコマース**でそのアカウントの商品カタログ CSV をアップロードできます。このページでは、カタログエラーと商品カタログのステータスを確認できます。 **商品カタログステータス**で連結アカウントの一覧を絞り込むことで、どのアカウントにカタログがアップロードされているかを確認することもできます。 ## 連結アカウントの税金を設定する 完全に管理された税金計算には Stripe Tax を使用します。カスタムの課税ロジックが必要な場合や、サードパーティーの税務プロバイダーを導入する必要がある場合は、導入に税金フックを実装します。 #### Stripe Tax による税金の自動計算 Stripe Tax を使用して、連結アカウントごとに課税される税金を計算して徴収します。[プラットフォームの税金設定](https://docs.stripe.com/tax/tax-for-platforms.md)を参照して、Stripe Tax を設定してください。 商品カタログの CSV アップロードで、`stripe_product_tax_code` 列を設定して、各商品を課税処理に関連付けます。 サポートされている税コードの一覧については、[税コード](https://docs.stripe.com/tax/tax-codes.md)を参照してください。 また、Anrok、Avalara、Sphere などの[サードパーティーの税務プロバイダー](https://docs.stripe.com/tax/third-party-apps.md)を通じて税金を計算することもできます。 #### フックによるカスタム税金計算 [決済カスタマイズフック](https://docs.stripe.com/connect/saas/tasks/enable-in-context-selling-on-ai-agents.md#checkout-customization-hook)を使用して、`v1.delegated_checkout.customize_checkout` イベントを処理し、項目ごとに `tax_rates` を返します。 税金フックを設定するには、以下を実行します。 1. 決済カスタマイズイベントを受信するエンドポイントをサーバーに作成します。 アプリケーションでの Webhook の設定の詳細については、[Webhook](https://docs.stripe.com/webhooks.md) を参照してください。 #### Node.js ```javascript const stripe = require('stripe'); const express = require('express'); const app = express(); app.use("/checkout-customization-hook", express.raw({ type: "application/json" })); app.post("/checkout-customization-hook", (req, res) => { const sig = req.headers["stripe-signature"]; const endpointSecret = process.env.WEBHOOK_SECRET; // Store this securely try { stripe.webhooks.signature.verifyHeader(req.body, sig, endpointSecret, stripe.webhooks.DEFAULT_TOLERANCE); } catch (err) { console.log(`Webhook signature verification failed: ${err.message}`); return res.status(400).send(`Webhook Error: ${err.message}`); } const event = JSON.parse(req.body); if (event.type === "v1.delegated_checkout.customize_checkout") { const data = event.data; const connectedAccount = event.context; const response = { line_items: data.line_item_details?.map((item) => ({ id: item.id, tax_rates: [ { rate_data: { display_name: "Sales tax", inclusive: false, percentage: 8.5, // Replace with your actual tax rate }, }, { rate_data: { display_name: "Environmental fee", inclusive: false, percentage: 1.0, // Replace with your actual fee rate }, }, ], })) || [], }; return res.status(200).json(response); } return res.status(400).json({ error: "Unsupported webhook type" }); }); app.listen(4567, () => console.log("Server is running on port 4567")); ``` 1. ダッシュボードの[エージェンティックコマース設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページで、Webhook エンドポイント URL を登録できます。 2. コード例に示すように、`v1.delegated_checkout.customize_checkout` イベントを処理し、項目ごとに税率を返します。 ## 取引を収益化する デフォルトでは、エージェント型の決済セッションを作成するときに、プラットフォーム手数料は適用されません。 > プラットフォームが連結アカウントの Stripe 手数料を支払うときに、プラットフォーム手数料を追加する必要があります。プラットフォーム手数料がないと、取引ごとに損失が生じる可能性があります。 #### プラットフォーム手数料フック [決済カスタマイズフック](https://docs.stripe.com/connect/saas/tasks/enable-in-context-selling-on-ai-agents.md#checkout-customization-hook)を使用して、`v1.delegated_checkout.finalize_checkout` イベントを処理し、プラットフォーム手数料を返します。 アプリケーションでの Webhook の設定については、[Webhook](https://docs.stripe.com/webhooks.md) を参照してください。 #### Node.js ```javascript const stripe = require('stripe'); const express = require('express'); const app = express(); app.use("/agentic-commerce-hook", express.raw({ type: "application/json" })); app.post("/agentic-commerce-hook", async (req, res) => { const sig = req.headers["stripe-signature"]; const endpointSecret = process.env.WEBHOOK_SECRET; // Store this securely try { stripe.webhooks.signature.verifyHeader(req.body, sig, endpointSecret, stripe.webhooks.DEFAULT_TOLERANCE); } catch (err) { console.log(`Webhook signature verification failed: ${err.message}`); return res.status(400).send(`Webhook Error: ${err.message}`); } const event = JSON.parse(req.body); console.log("Received event:", event.type); if (event.type === "v1.delegated_checkout.finalize_checkout") { const data = event.data; // Perform validation checks for order approval const orderAmount = data.amount_total || 0; const lineItems = data.line_items_details || []; const connectedAccount = event.context; const stripeCheckoutSessionId = data.checkout_session; const applicatonFee = await calculateApplicationFee(lineItems); const {reason, isApproved} = await calculateOrderApproval(); if (isApproved) { return res.status(200).json({ manual_approval_details: { type: "approved" }, application_fee_details: { application_fee_amount: applicatonFee } }); } else { return res.status(200).json({ manual_approval_details: { type: "declined", declined: { reason, } } }); } } return res.status(400).json({ error: "Unsupported webhook type" }); }); app.listen(4567, () => console.log("Server is running on port 4567")); ``` #### プラットフォーム料金設定ツールによるプラットフォーム手数料の請求 連結アカウントが、プラットフォームが Stripe 手数料を支払う手数料負担の設定を使用している場合は、[プラットフォーム料金設定ツール](https://docs.stripe.com/connect/platform-pricing-tools.md)を使用してプラットフォーム手数料を請求できます。 ## 連結アカウントがエージェントを通じて販売できるようにする方法 連結アカウントは、エージェントを通じて販売する前に、エージェント利用規約を確認し、エージェントを有効にする必要があります。Stripe はエージェントに承認リクエストを送信し、エージェントはそれを承認する必要があります。連結アカウントは、どの AI エージェントが自社の商品を販売するかを管理し、各エージェントプラットフォームでのビジネスの表示方法をカスタマイズし、任意のエージェントでの販売を一時停止または停止できます。 #### 埋め込みコンポーネント エージェンティックコマース設定コンポーネントをプラットフォームの UI に直接埋め込むことで、連結アカウントにネイティブなオンボーディングと管理の体験を提供できます。ウェブサイトにダッシュボードの機能を埋め込む方法については、[Get started with Connect embedded components](https://docs.stripe.com/connect/get-started-connect-embedded-components.md) を参照してください。 #### Ruby ```ruby require 'sinatra' require 'stripe' # This is a placeholder - it should be replaced with your secret API key. # Sign in to see your own test API key embedded in code samples. # Don't submit any personally identifiable information in requests made with this key. # Don't put any keys in code. See https://docs.stripe.com/keys-best-practices. client = Stripe::StripeClient.new('<>') post '/account_session' do content_type 'application/json' begin account_session = client.v1.account_sessions.create({ account: '{{CONNECTED_ACCOUNT_ID}}', components: { agentic_commerce_settings: { enabled: true, } } }) { client_secret: account_session[:client_secret] }.to_json rescue => error puts "An error occurred when calling the Stripe API to create an account session: #{error.message}"; return [500, { error: error.message }.to_json] end end ``` #### HTML + JS ```html

Payments

``` ```javascript import {loadConnectAndInitialize} from '@stripe/connect-js'; const fetchClientSecret = async () => { // Fetch the AccountSession client secret const response = await fetch('/account_session', { method: "POST" }); if (!response.ok) { // Handle errors on the client side here const {error} = await response.json(); console.error('An error occurred: ', error); document.querySelector('#error').removeAttribute('hidden'); return undefined; } else { const {client_secret: clientSecret} = await response.json(); document.querySelector('#error').setAttribute('hidden', ''); return clientSecret; } } const stripeConnectInstance = loadConnectAndInitialize({ // This is a placeholder - it should be replaced with your publishable API key. // Sign in to see your own test API key embedded in code samples. // Don't submit any personally identifiable information in requests made with this key. publishableKey: "<>", fetchClientSecret: fetchClientSecret, }); const paymentComponent = stripeConnectInstance.create("agentic-commerce-settings"); const container = document.getElementById("container"); container.appendChild(paymentComponent); ``` #### Stripe ダッシュボードのフル機能 Stripe ダッシュボードのフル機能にアクセスできる連結アカウントは、**設定 > 決済 > エージェンティックコマース**に移動すると、エージェンティックコマースのオンボーディングを行えます。このページでは、Stripe プロフィールを作成し、売り手設定を構成して、エージェントチャネルを有効または無効にできます。 #### Express ダッシュボード Express ダッシュボードを使用する連結アカウントは、**設定**に移動する**エージェンティックコマース**セクションを見つけられます。そこから、売り手プロフィールを管理し、設定を構成して、エージェントチャネルを有効または無効にできます。 ## 購入への対応と注文のフルフィルメント Stripe Webhook をリッスンして、AI チャットエージェントで行われた注文を監視します。 注文が確定されると、Stripe はフルフィルメントロジックを実行するためにサーバーが処理できる Webhook イベントを送信します。これらのイベントを受け入れ、処理し、承認するようにサーバーにエンドポイントを設定します。Stripe Webhook の導入とテストの手順については、[Webhook ガイド](https://docs.stripe.com/webhooks.md)を参照してください。 Stripe は `checkout.session.completed` と `payment_intent.succeeded` を送信します。フルフィルメントロジックがすでにこれらのイベントを処理している場合は、追加の導入変更は必要ありません。コンテキストに応じたエージェント販売のフルフィルメントロジックをカスタマイズできます (たとえば、注文確認メールで決済がエージェントを介して発生したことを通知するなど)。 連結アカウントの Webhook の設定の詳細については、[Connect Webhook](https://docs.stripe.com/connect/webhooks.md) を参照してください。 #### Node.js ```javascript const stripe = require('stripe')(process.env.STRIPE_SECRET_KEY); const express = require('express'); const app = express(); // Use the secret provided by Stripe CLI for local testing // or your webhook endpoint's secret const endpointSecret = 'whsec_...'; app.post('/webhook', async (request, response) => { const sig = request.headers['stripe-signature']; let event; try { event = stripe.webhooks.constructEvent(request.body, sig, endpointSecret); } catch (err) { response.status(400).send(`Webhook Error: ${err.message}`); return; } if (event.type === 'checkout.session.completed') { let session = event.data.object; // For V1 webhooks event.account is the connected account session = await stripe.checkout.sessions.retrieve( session.id, { expand: ["line_items.data.price.product", "line_items.data.price"], }, // If using direct charges, the checkout session is created on the connected account and the `stripeAccount` parameter must be passed. If using destination charges the checkout session is created on the platform account and `stripeAccount` parameter can be ignored. { stripeAccount: "{{CONNECTED_ACCOUNT_ID}}", }, ); // SKU id is available at session.line_items.data[number].price.external_reference fulfillCheckout(event.account, session); } response.status(200).send(); }); ``` Webhook を受信したら、1 回の API コールですべての必須フィールドを取得します。複数のリクエストを回避するには、`Stripe-Version: 2025-12-15.preview` のプレビューヘッダーを指定して、[expand](https://docs.stripe.com/api/expanding_objects.md) リクエストパラメーターを使用してサブリソースを展開します。 ```curl curl https://api.stripe.com/v1/checkout/sessions/{{SESSION_ID}}?expand[]=line_items.data.price.product&expand[]=line_items.data.taxes&expand[]=payment_intent.latest_charge \ -u <>: \ -H "Stripe-Version: 2025-12-15.preview" \ -H "Stripe-Account: {{CONNECTED_ACCOUNT_ID}}" ``` `amount_total`、quantity、SKU ID など、拡張された [Checkout Session](https://docs.stripe.com/api/checkout/sessions/object.md) のフィールドをご覧ください。 ### Checkout セッションのフィールドリファレンス | 注文フィールド | 利用可能なリソース | API パス | | --- | --- | --- | | **注文日** | `CheckoutSession.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.created` | | **注文数量** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].quantity` | | **SKU** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].price.external_reference` | | **商品説明** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].price.product.description` | | **単価** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].price.unit_amount` | | **税額** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].Taxes[].amount` | | **税種別** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].Taxes[].Rate.tax_type` | | **税率** | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].Taxes[].Rate.percentage` | | **ShippingAddress** | `CheckoutSessions` | `CheckoutSessions.CollectedInformation.shipping_details` | | **BillingAddress** | `CheckoutSessions.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.billing_details` | | **Last4** | `CheckoutSessions.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.payment_method_details.card.last4` | | **ExpMonth** | `CheckoutSessions.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.payment_method_details.card.exp_month` | | **ExpYear** | `CheckoutSessions.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.payment_method_details.card.exp_year` | | **CreditCardType** | `CheckoutSessions.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.payment_method_details.card.brand` | | **最終金額** | `CheckoutSessions` | `CheckoutSessions.amount_total` | | **GTIN** (Private preview) | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].price.product.identifiers.gtin` | | **MPN** (Private preview) | `CheckoutSessions` | `CheckoutSession.LineItems.Data[].price.product.identifiers.mpn` | | **エージェント詳細** (Private preview) | `CheckoutSession.PaymentIntent` | `CheckoutSessions.PaymentIntent.agent_details` | | **OrderNo** | `CheckoutSession.PaymentIntent.LatestCharge` | `CheckoutSessions.PaymentIntent.LatestCharge.receipt_number` | ## 実装のテスト ダッシュボードから[サンドボックス](https://docs.stripe.com/sandboxes.md)で直接インテグレーションをテストできます。 1. ワークベンチで [Trigger Agentic Purchase](https://dashboard.stripe.com/test/workbench/blueprints/agentic-commerce-turnkey-agentic-purchase) ブループリントを開く 2. 連結アカウントの ID と SKU ID を入力する 3. **実行** をクリックして、エージェントからの決済をシミュレーションします ## Optional: 手動によるキャプチャー デフォルトでは、Stripe は購入が完了するとすぐに決済をキャプチャします。手動キャプチャを使用するには、ダッシュボードの[エージェンティックコマース設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページで有効にします。手動キャプチャを有効にした後、前のセクションで説明した Webhook で返された `PaymentIntent` に対して、capture メソッドを呼び出します。 ```curl curl -X POST https://api.stripe.com/v1/payment_intents/{{PAYMENTINTENT_ID}}/capture \ -u "<>:" ``` ## Optional: 注文承認フックを設定する Stripe は、決済を確定する前に、お客様の商品カタログデータに基づいて在庫を確認し、[Radar](https://docs.stripe.com/radar.md) の設定によっては不正利用チェックを実行する場合があります。購入を完了するかどうかを制御するには、注文承認フックを設定します。決済フローを完了する前に、Stripe はお客様のサービスに承認リクエストを送信します。このリクエストは承認または拒否する必要があります。 Stripe はフックに 4 秒のタイムアウトを適用します。この時間内にフックが応答しない場合、Stripe は支払いを拒否します。 注文承認フックを設定するには: 1. ダッシュボードの [Agentic Commerce 設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページでエンドポイントを指定します。 2. **Order approvals** を有効にします。 3. エンドポイントにロジックを実装し、以下のリクエストとレスポンスの形式を使用します。 > エンドポイントが `2xx` 以外のステータスコードを返すと、Stripe はエージェントに `424` ステータスコードを返します。一部のエージェントはこれらの API リクエストを再試行する可能性があるため、エンドポイントが冪等であることを確認する必要があります。 ### リクエスト形式 Stripe はエンドポイントに次のリクエストを送信します。 ```typescript { type: "v1.delegated_checkout.finalize_checkout", id: string, livemode: boolean, // account ID context?: string, // request specific data data: { amount_subtotal?: number, amount_total?: number, billing_details?: { name?: string, address?: { line1?: string, line2?: string, city?: string, state?: string, postal_code?: string, country?: string } }, currency: string, email?: string, line_item_details: Array<{ id: string, sku_id: string, unit_amount: number, amount_discount: number, amount_subtotal: number, amount_tax: number, amount_total: number, quantity: number, name: string, tax_rates: Array<{ rate: { id: string, display_name: string, percentage: number, inclusive: boolean, }, // Amount of tax applied for this rate. amount: number }> }>, payment_method_details?: { type: "card" | ..., card?: { brand: "amex" | "visa" | "master_card" | ..., country?: string, exp_month: number, exp_year: number, fingerprint?: string, funding: "credit" | "debit" | "prepaid" | "unknown", iin?: string, last4: string, wallet?: { type: "apple_pay" | "google_pay" | ... } } }, phone?: string, shipping_details?: { name?: string, address?: { line1?: string, line2?: string, city?: string, state?: string, postal_code?: string, country?: string }, }, total_details?: { amount_discount?: number, amount_shipping?: number, amount_tax?: number }, metadata?: Map } } ``` ### 応答形式 エンドポイントは、次の形式で `200` HTTP 応答を返す必要があります。 ```typescript { manual_approval_details: { type: "approved" | "declined", declined?: { reason: string } }, // Connect only: set an application fee for the transaction application_fee_details?: { application_fee_amount: number, transfer_data?: { amount?: number, } }, // will be propagated to Checkout Session metadata metadata?: Map } ``` ## Optional: 決済カスタマイズフックを設定する デフォルトでは、Stripe は[商品カタログ](https://docs.stripe.com/agentic-commerce/product-feed.md)に定義されているオプションに基づいて、商品の税金と配送オプションを計算します。 税金または配送オプションとコストをロジックで動的に計算するには、以下のようにします。 1. ダッシュボードの [Agentic Commerce 設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページでエンドポイントを指定します。 2. **カスタム税率**または**カスタム配送オプション**を有効にします。 3. エンドポイントにロジックを実装し、以下のリクエストとレスポンスの形式を使用します。 > エンドポイントが `2xx` 以外のステータスコードを返すと、Stripe はエージェントに `424` ステータスコードを返します。一部のエージェントはこれらの API リクエストを再試行する可能性があるため、エンドポイントが冪等であることを確認する必要があります。 ### リクエスト形式 Stripe はエンドポイントに次のリクエストを送信します。 ```typescript { type: "v1.delegated_checkout.customize_checkout", id: string, livemode: boolean, // Connected account ID context?: string, // Request specific data data: { // Used by the seller to determine whether they can set manual tax rates on line items automatic_tax: { enabled: boolean, }, currency: string, line_item_details?: Array<{ id: string, sku_id: string, unit_amount: number, amount_discount: number, amount_subtotal: number, amount_tax: number, amount_total: number, quantity: number, name: string, tax_rates: Array<{ rate: { id: string, display_name: string, percentage: number, inclusive: boolean, }, // Amount of tax applied for this rate. amount: number }> }>, shipping_details?: { // Same as the shipping rate object described at https://docs.stripe.com/api/shipping_rates/object#shipping_rate_object shipping_rate?: { id: string, display_name?: string, metadata?: Map, tax_code?: string , tax_behavior: 'unspecified' | 'inclusive' | 'exclusive', fixed_amount: { amount: number, currency: 'usd' | 'cad' | etc., currency_options: { : { amount: number, tax_behavior: 'unspecified' | 'inclusive' | 'exclusive', } } }, delivery_estimate?: { maximum: { unit: 'business_day' | 'day' | 'hour' | 'month' | 'year', value: number }, minimum: { unit: 'business_day' | 'day' | 'hour' | 'month' | 'year', value: number } } }, // Same as the shipping rate object described at https://docs.stripe.com/api/shipping_rates/object#shipping_rate_object shipping_rates?: Array<{ id: string, display_name?: string, metadata?: Map, tax_code?: string, tax_behavior: 'unspecified' | 'inclusive' | 'exclusive', fixed_amount: { amount: number, currency: 'usd' | 'cad' | etc., currency_options: { : { amount: number, tax_behavior: 'unspecified' | 'inclusive' | 'exclusive', } } }, delivery_estimate?: { maximum: { unit: 'business_day' | 'day' | 'hour' | 'month' | 'year', value: number }, minimum: { unit: 'business_day' | 'day' | 'hour' | 'month' | 'year', value: number } } }>, address?: { line1?: string, line2?: string, city?: string, state?: string, postal_code?: string, country?: string } }, amount_total?: number, amount_subtotal?: number, total_details?: { amount_discount?: number, amount_shipping?: number, amount_tax?: number }, metadata?: Map } } ``` ### 応答形式 エンドポイントは、次の形式で `200` HTTP レスポンスを返す必要があります。 ```typescript { shipping_options?: Array<{ // ID of the shipping rate, or data provided to create the shipping rate. Only provide one; not both shipping_rate?: string, shipping_rate_data: { display_name?: string, fixed_amount: { amount: number, currency: 'usd' | 'cad' | etc., }, metadata?: Map, tax_code?: string , tax_behavior?: 'unspecified' | 'inclusive' | 'exclusive', // Same as the shipping rate object described at https://docs.stripe.com/api/shipping_rates/create#create_shipping_rate-delivery_estimate delivery_estimate?: { maximum: { unit: 'business_day' | 'day' | 'hour' | 'month' | 'year', value: number }, minimum: { unit: 'business_day' | 'day' | 'hour' | 'month' | 'year', value: number } } }, }>, line_items?: Array<{ // Corresponding ID of the line item to update id: string, // List of tax rates to apply to this line item // Provide either `rate` or `rate_data` tax_rates: Array<{ // ID of a v1 tax rate rate?: string, // Or `rate_data`. // This will use an existing tax rate that matches the params or will create one if a matching rate does not exist rate_data?: { display_name: string, inclusive: boolean, // percentage out of 100 percentage: number, } }, }>, // will be propagated to Checkout Session metadata metadata?: Map } ``` ## Optional: 商品の価格と在庫状況のフックを設定する このフックを実装することで、エージェントにリアルタイムの価格および在庫データが提供されます。実装しない場合、エージェントはアップロードされた商品カタログにのみ依存するため、決済時に在庫切れエラーや価格の不一致が生じる可能性があります。 商品の価格と在庫状況のフックを設定するには、次の手順を実行します。 1. ダッシュボードの [Agentic Commerce 設定](https://dashboard.stripe.com/settings/connect/agentic-commerce)ページでエンドポイントを指定します。 2. **商品の価格と在庫状況** を有効にします。 3. エンドポイントにロジックを実装し、以下のリクエストとレスポンスの形式を使用します。 ### リクエスト形式 Stripe はエンドポイントに次のリクエストを送信します。 ```typescript { type: "delegated_commerce.product_price_availability", id: string, livemode: boolean, // account ID context?: string, // request specific data data: { sku_id: string, } } ``` ### 応答形式 エンドポイントは、次の形式で `200` HTTP レスポンスを返す必要があります。 ```typescript { sku_id: string, merchant_id: string, availability: { status: "in_stock" | "out_of_stock" | "preorder" | "backorder", quantity?: number, // current inventory count availability_date?: string // ISO 8601 date when a preorder item becomes available }, price: { unit_amount: number, // current selling price in smallest currency unit currency: string // ISO 4217 currency code }, sale_price?: { unit_amount: number, // sale price in smallest currency unit currency: string, // ISO 4217 currency code start_date: string, // ISO 8601 sale start date end_date: string // ISO 8601 sale end date }, as_of?: number // Unix timestamp of when this data was last accurate } ``` ## Optional: フックをテストする `POST` メソッドでフックリクエストを受け付けられる、一般にアクセス可能なエンドポイントを提供することで、注文承認または決済のカスタマイズフックをテストできます。エンドポイント関数を設定して、以下を行います。 1. JSON ペイロードで `POST` リクエストを処理する 2. 成功ステータスコード (`200`) を返す ローカル開発では、[ngrok](https://ngrok.com/) などのトンネリングツールを使用してローカルエンドポイントを公開します。 ### エンドポイントの例 このコードスニペットは、`v1.delegated_checkout.finalize_checkout` リクエストを受信して `200` レスポンスを返すエンドポイント関数を示しています。署名シークレットは、Webhook 設定の **Agentic Commerce Extension** イベント送信先にある [開発者ダッシュボード](https://docs.stripe.com/development/dashboard.md) から確認できます。 #### Ruby ```ruby require 'json' require 'sinatra' require 'stripe' set :port, 4242 # Replace with your endpoint's secret from your webhook settings endpoint_secret = 'whsec_...' # Using Sinatra post '/hooks' do payload = request.body.read sig_header = request.env['HTTP_STRIPE_SIGNATURE'] # Verify the webhook signature begin Stripe::Webhook::Signature.verify_header( payload, sig_header, endpoint_secret ) rescue Stripe::SignatureVerificationError => e status 400 return end # Handle the payload payload = JSON.parse(payload) case payload['type'] when 'v1.delegated_checkout.finalize_checkout' # Check inventory and accept payment data = { manual_approval_details: { type: 'approved' } } end status 200 body data.to_json end ``` ## Optional: エージェントとの契約の処理 > この API はプライベートプレビュー版です。以下の例は変更される場合があります。 連結アカウントがエージェントにユーザー登録すると、Stripe は売り手とエージェントとの間に Agreement オブジェクトを作成します。Stripe は、Agreement オブジェクトのステータスが変更されるごとに Webhook イベントをプラットフォームとエージェント双方に送信します。 - `v2.orchestrated_commerce.agreement.created`: 売り手とエージェントの間で契約が作成されました。 - `v2.orchestrated_commerce.agreement.partially_confirmed`: 売り手が契約を確定しました。 - `v2.orchestrated_commerce.agreement.confirmed`: エージェントが契約を確定しました。 - `v2.orchestrated_commerce.agreement.terminated`: 売り手または代理人が契約を終了しました。 Webhook エンドポイントでこれらのイベントを受信して、プラットフォームの状態を常に同期させます (UI の更新、エージェントへのアクセスの有効化・無効化、売り手への通知など)。 ### 規約を取得する Agreements API を使用して Agreement オブジェクトを取得します。 ```curl curl https://api.stripe.com/v2/orchestrated_commerce/agreements/{{AGREEMENT_ID}} \ -H "Authorization: Bearer {{API_KEY}}" \ -H "Stripe-Version: 2025-12-19-17.internal" \ -H "Stripe-Account: {{CONNECTED_ACCOUNT_ID}}" ``` ## Optional: 増分インベントリ更新を送信する 商品カタログのアップロードに加えて、[インポート API](https://docs.stripe.com/api/v2/commerce/product-catalog-imports.md) を使用して個々の商品在庫の更新を送信できます。カタログのアップロード時と同じアップロードプロセスを使用しますが、`feed_type` を `inventory` に設定します。在庫フィードは `upsert` モードにのみ対応しています。 ```curl curl -X POST https://api.stripe.com/v2/commerce/product_catalog/imports \ -H "Authorization: Bearer <>" \ -H "Stripe-Version: 2026-06-24.preview" \ -H "Stripe-Account: {{CONNECTEDACCOUNT_ID}}" \ --json '{ "feed_type": "inventory", "mode": "upsert", "metadata": { "file_name": "march_11_2026_inventory_upload.csv" } }' ``` ## Optional: 差分の価格更新を送信する 商品カタログデータをアップロードしてから、[インポート API](https://docs.stripe.com/api/v2/commerce/product-catalog-imports.md) を使用して個別の価格更新を送信します。カタログのアップロード時と同じアップロードプロセスを使用し、`feed_type` を `pricing` に設定します。価格フィードは `upsert` モードにのみ対応しています。 ```curl curl -X POST https://api.stripe.com/v2/commerce/product_catalog/imports \ -H "Authorization: Bearer <>" \ -H "Stripe-Version: 2026-06-24.preview" \ -H "Stripe-Account: {{CONNECTEDACCOUNT_ID}}" \ --json '{ "feed_type": "pricing", "mode": "upsert", "metadata": { "file_name": "march_11_2026_pricing_upload.csv" } }' ``` ## Optional: 返金および不審請求の申し立ての処理 すでに [Payment Intents API](https://docs.stripe.com/api/payment_intents.md) または [Checkout Sessions API](https://docs.stripe.com/api/checkout/sessions.md) を使用している場合は、既存の返金フローと不審請求の申し立てフローを、インコンテキストのエージェンティックな販売でも変更せずにそのまま使用できます。Stripe はエージェントによる決済フロー用に `PaymentIntents` を作成するため、`PaymentIntent` ID を注文に関連付けている限り、既存の導入は引き続き機能します。 顧客が決済完了後にウェブサイトまたはカスタマーサービス経由で注文をキャンセルした場合は、返金を開始できます。ダッシュボードの [Transactions page](https://dashboard.stripe.com/payments) で返金と不審請求の申し立てを管理するか、[Refunds API](https://docs.stripe.com/api/refunds.md) を使用してプログラムで処理できます。