localized-pricing について
DodoPaymentsを利用する開発者向けに、固定のローカライズ価格、決済時の通貨換算、購買力平価価格の設定を説明します。価格設定、国・通貨の判定、プラン変更、税の扱いを扱います。
主な機能
- 01国または通貨別の固定価格設定
- 02決済時のリアルタイムレート換算
- 03国別PPP比率の設定
- 04ローカライズ価格レコードの管理
- 05フォールバック、プラン変更、税の説明
活用シーン
- 01国ごとに予測可能な価格を設定
- 02顧客の現地通貨で決済を提供
- 03市場別に購買力平価を適用
- 04サブスクリプション変更時の現地価格処理
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ dodopayments/ skills --skill localized-pricingインストール後、Claude Code で/localized-pricingを入力して読み込まれたか確認します。
詳細
ローカライズされた価格設定、適応型通貨、PPP
このスキルでは、複数の国や通貨で価格を設定するための、互いに異なる3つの仕組みを扱います。開発者はこれらを混同しがちです。このスキルでは、それぞれの違いを明確にし、実装方法を紹介するとともに、プラン変更、日割り計算、税金との相互作用について説明します。
このスキルを使用する場面
- 特定の国や通貨に固定価格を設定する必要がある場合。
- チェックアウト時にリアルタイムの為替換算を提供したい場合。
- 新興市場向けに購買力平価に基づく割引を検討している場合。
- ローカライズされた価格設定と適応型通貨のどちらを使うべきか分からない場合。
- ローカライズされた価格に関する請求先の国や通貨の判定、フォールバック動作、プラン変更への対応が必要な場合。
基本概念
3つの仕組み、3つの目的
| 仕組み | 内容 | 管理者 | 価格が変わるタイミング |
|---|---|---|---|
| ローカライズされた価格設定 | 開発者が国や通貨ごとに固定価格を設定します | あなた(API 経由) | 価格を更新したときのみ |
| 適応型通貨 | チェックアウト時にリアルタイムの為替換算を行います | Dodo(リアルタイムの為替レート) | 現在の為替レートに基づき、取引ごとに変わります |
| 購買力平価(PPP) | 国ごとに基本価格の一定割合を請求します | あなた(ダッシュボードでビジネス全体の国別割合を設定し、商品ごとに有効化) | 割合を変更したときのみ |
重要な違い: ローカライズされた価格は固定です。適応型通貨は変動します。PPP は国ごとに設定された割合を基本価格に適用し、その後、適応型通貨で換算するネイティブ機能です。
ローカライズされた価格設定
特定の国や通貨に固定価格を設定します。作成後、価格を更新しない限り変わりません。為替レートには連動しません。
管理したい、予測可能な地域別価格を提供する場合に、ローカライズされた価格設定を使用してください。
適応型通貨
チェックアウト時のリアルタイム為替換算を有効にします。顧客には現地通貨で価格が表示され、Dodo が現在の為替レートを使って基本価格を換算します。
通貨ごとに手動で価格を設定せず、あらゆる通貨でチェックアウトを提供したい場合に、適応型通貨を使用してください。
PPP(購買力平価)
PPP はネイティブ機能です(ドキュメント)。Dodo は国ごとにビジネス全体で共通の割合(30~100)を保持し、ダッシュボードでのみ管理できます。顧客は請求先の国に基づき、設定した割合分の表示価格を支払います。各商品で price.purchasing_power_parity: true を指定して有効にします(デフォルトは false)。
PPP を利用するには、適応型通貨が必要です。あらかじめ Settings → Business で有効にしてください。有効にしていない場合、商品でのオプトインは拒否されます。一致するローカライズされた価格がある場合は、常に PPP より優先されます。割引コードは、PPP 適用後の価格に適用されます。
await client.products.create({
name: 'Starter Plan',
tax_category: 'saas',
price: {
type: 'one_time_price',
currency: 'USD',
price: 2000, // $20.00; a customer in India at 30% pays $6.00
discount: 0,
purchasing_power_parity: true,
},
});
商品の価格設定モード
すべての商品には、価格の判定方法を決める pricing_mode があります。
by_country:Dodo は顧客の請求先の国に基づいて、ローカライズされた価格を検索します。by_currency:Dodo は顧客の請求通貨に基づいて、ローカライズされた価格を検索します。
client.products.update(...) を使って、商品ごとにモードを一度設定します。同じ商品で複数のモードを併用することはできません。
import DodoPayments from 'dodopayments';
const client = new DodoPayments({
bearerToken: process.env.DODO_PAYMENTS_API_KEY,
environment: 'test_mode',
});
// Set pricing mode to by_country
await client.products.update('pdt_premium_plan', {
pricing_mode: 'by_country',
});
// Or by_currency
await client.products.update('pdt_premium_plan', {
pricing_mode: 'by_currency',
});
ローカライズされた価格の CRUD
ローカライズされた価格は商品に紐づきます。金額はすべて、通貨の最小単位で指定します(USD はセント、INR はパイサ)。
ローカライズされた価格を作成する
// ₹999.00 for customers in India
const localizedPrice = await client.products.localizedPrices.create('pdt_premium_plan', {
currency: 'INR',
country_code: 'IN',
amount: 99900, // 999.00 in paise
});
商品のローカライズされた価格を一覧表示する
const prices = await client.products.localizedPrices.list('pdt_premium_plan');
console.log(prices);
特定のローカライズされた価格を取得する
const price = await client.products.localizedPrices.retrieve('lp_abc123', {
product_id: 'pdt_premium_plan',
});
console.log(price.amount, price.currency, price.country_code);
ローカライズされた価格を更新する
await client.products.localizedPrices.update('lp_abc123', {
product_id: 'pdt_premium_plan',
amount: 109900, // Update to ₹1099.00
});
ローカライズされた価格をアーカイブする
await client.products.localizedPrices.archive('lp_abc123', {
product_id: 'pdt_premium_plan',
});
アーカイブされた価格は論理削除されます。新しいチェックアウトには適用されませんが、履歴には残ります。
チェックアウト時のアダプティブ通貨
ダッシュボードの 設定 → ビジネス でアダプティブ通貨を有効にします(ドキュメント)。Dodo はその後、基準となる商品価格をリアルタイムの為替レートで換算します。チェックアウトセッションで billing_currency と billing_address.country を渡すと、請求に使用する通貨が固定されます。これらを省略した場合、アダプティブ通貨は顧客の IP アドレスから通貨と国を選択します。
// Server route (e.g. POST /api/checkout): create the session and return its URL
export async function POST() {
const session = await client.checkoutSessions.create({
product_cart: [
{
product_id: 'pdt_premium_plan',
quantity: 1,
},
],
billing_currency: 'AED', // Pin the charge currency (requires Adaptive Currency)
billing_address: { country: 'AE' },
return_url: 'https://example.com/return',
});
return Response.json({ checkout_url: session.checkout_url });
}
SDK を呼び出したり、API キーをブラウザーコードで公開したりしないでください。ブラウザーが受け取るのは URL だけで、そこへリダイレクトします。
// Browser
const res = await fetch('/api/checkout', { method: 'POST' });
const { checkout_url } = (await res.json()) as { checkout_url: string };
window.location.href = checkout_url;
手数料: アダプティブ通貨では、デフォルトで表示価格に段階制の換算手数料が加算されます(500 ドル未満は 4%、500 ドルから 1,500 ドルまでは 3%、1,500 ドル超は 2%)。代わりに決済金額から手数料を差し引くには、設定 → ビジネス で 手数料込み を有効にします。現地通貨価格が一致した場合、取引は常に手数料込みとして扱われます。
端数価格設定: アダプティブ通貨を有効にすると、端数価格設定 によって、換算価格を 49.99 のような切りのよい末尾に丸めることができます。アダプティブ通貨が必要です。
アダプティブ通貨は、サブスクリプションの作成やプラン変更でも利用できます。使用するエンドポイントで billing_currency がサポートされているか、API リファレンスで確認してください。
請求先の国と通貨の決定
Dodo は次の順序で顧客の請求先の国と通貨を決定します。
- チェックアウトで渡された
billing_address.countryまたはbilling_currency。 - 顧客の保存済み住所(顧客が Dodo に登録されている場合)。
- IP ジオロケーション(利用可能な場合)。
- 商品の基準価格と通貨にフォールバックします。
決定された国または通貨に対応する現地通貨価格がない場合、Dodo は基準価格にフォールバックします。このフォールバックは自動で行われ、エラーは発生しません。
プラン変更および日割り計算との連携
顧客がプランを変更すると、新しいプランには、元のサブスクリプションと同じ請求先の国または通貨に基づいて現地通貨価格が適用されます。
日割り計算は、顧客の国または通貨に対応する新しいプランの現地通貨価格がある場合、その価格を使用して行われます。
await client.subscriptions.changePlan('sub_abc123', {
product_id: 'pdt_enterprise_plan',
quantity: 1,
proration_billing_mode: 'prorated_immediately',
});
日割り計算額には、新しいプランの現地通貨価格が使用されます。
現地通貨価格に対する税の扱い
税は基準価格ではなく、現地通貨価格に対して計算されます。インド向けに ₹999.00 の現地通貨価格を設定した場合、その金額に税が適用されます。
税込み価格も同様です。現地通貨価格は税込みの合計額として扱われます。
よくある間違い
間違い 1:現地通貨価格が為替レートに応じて自動更新されると思い込む
現地通貨価格は固定です。今日 INR 999.00 に設定した場合、手動で更新するまで 999.00 のままです。USD/INR の為替レートには連動しません。
リアルタイムの為替換算が必要な場合は、代わりにアダプティブ通貨を使用してください。
間違い 2:by_country と by_currency を混同する
by_country:Dodo は顧客の請求先の国を現地通貨価格のcountry_codeと照合します。by_currency:Dodo は顧客の請求通貨を現地通貨価格のcurrencyと照合します。
USD カードを使用するインドの顧客は、by_currency: USD には一致しますが、by_country: IN には一致しません(インド向けにも USD 価格を設定している場合を除く)。
間違い 3:フォールバック価格を忘れる
pricing_mode: by_country を設定していても、顧客の国に対応する現地通貨価格がない場合、Dodo は基準価格にフォールバックします。顧客がすでに基準通貨を使用している場合はそのまま請求され、アダプティブ通貨が有効な場合はアダプティブ通貨で換算されます(ドキュメント)。アダプティブ通貨が無効の場合は、基準通貨で基準価格が請求されるため、通常は望ましくありません。
モードを有効にする前に、対象市場の現地通貨価格を必ず作成してください。
間違い 4:地域別価格と通貨の自動換算を混同する
同じ商品で両方を利用できますが、目的は異なります。地域別価格は、地域ごとに固定価格を設定するためのものです。通貨の自動換算は、リアルタイムの為替換算に使用します。
インド向けに地域別価格を設定し、通貨の自動換算も有効にした場合、インドのお客様には地域別価格が優先されます。
間違い 5:PPP のためにサードパーティ製ツールを利用する
PPP は標準機能です。price.purchasing_power_parity: true で商品を対象に設定し、ダッシュボードで国ごとの割合を設定します(通貨の自動換算が有効になっている必要があります)。ParityDeals などのサードパーティ製ツールは、サイトにバナーを表示したい場合の代替手段にすぎません。これらのツールのコードは、チェックアウト時に通常の discount_codes として渡されます。
間違い 6:本番環境で地域別価格がない場合の処理を設定しない
必ずフォールバックの動作をテストしてください。お客様の国または通貨に地域別価格が設定されていない場合、基本価格が表示されます。それで問題ないか、または対応していない地域ではチェックアウトをブロックする必要があるかを判断してください。