【初心者向け】Pay.jpとは?クレカ決済を爆速導入できるサービスを解説!特徴・使い方・実装例まとめ

【初心者向け】Pay.jpとは?クレカ決済を爆速導入できるサービスを解説! Next.js
【初心者向け】Pay.jpとは?クレカ決済を爆速導入できるサービスを解説!
この記事は約13分で読めます。

※当サイトはアフィリエイト広告を利用しています。商品リンクにはプロモーションを含む場合があります。

未経験でも気軽に!サブスク型プログラミングスクール【Freeks】

困ってた自分に届けたい話

「クレジットカード決済をサイトに組み込みたい…でも難しそう」
いざ調べてみると、知らない英語・セキュリティの話・カード情報の取り扱いなど、何をどうすればいいか混乱…。


そんなときに出会ったのが 「Pay.jp(ペイジェーピー)」
コード数行で決済ができるようになり、「え、こんなに簡単でいいの?」と驚き。

てんハロ運営者
てんハロ運営者

この記事は、同じように困っていた方への備忘録兼シェアとして書いています。

Pay.jpとは?

Pay.jp は、クレジットカード決済を簡単に導入できる日本発の決済サービスです。

  • Visa / Mastercard / JCB / AMEX などに対応
  • JavaScriptやAPI経由で簡単に組み込み可能
  • セキュリティ対策もばっちり(PCI DSS準拠)
    PCI DSS:クレジットカード情報を安全に扱うための世界共通のルール
  • 日本語ドキュメント完備&開発者向けにやさしい

どんなときに使うの?

たとえばこんな場面で使えます。

  • ECサイトで商品を購入するときの決済
  • サブスク(月額課金)サービスの実装
  • 会員登録+決済を一括で処理
  • アプリ内課金のバックエンド処理 など

なぜPay.jpが選ばれているのか?

クレジットカード決済サービスはたくさんありますが、「使いやすさ」「サポートの手厚さ」「日本向けかどうか」などで違いがあります。

以下は、Pay.jpと他の代表的なサービスを比較した表です。

項目Pay.jpStripeSquareKomoju
開発元日本アメリカアメリカ日本
日本語サポート(完全対応)△(一部対応)△(やや弱め)◎(完全対応)
導入のしやすさ(数行で完結)○(高機能だが設定が複雑)○(ノーコード寄り)○(初期設定が少し複雑)
カード情報の取り扱い不要(トークン化でOK)◎(同様)◎(同様)◎(同様)
決済手数料(参考)3.0%〜3.6%〜3.25%〜3.6%〜
定期課金対応△(回数券などで代用)
日本の決済文化への対応(コンビニ払い・銀行振込など)△(海外寄り)△(海外寄り)◎(多様な支払い手段)
管理画面の使いやすさ(直感的で見やすいUI)○(多機能だがやや複雑)

実装内容

実際の流れ(1回課金)

  1. ユーザーがカード情報を入力(Pay.jsを使ってトークン化)
  2. トークンをバックエンド(Python/Nodeなど)に送る
  3. バックエンドがトークンを使ってPay.jp APIで課金

👉 自分のサーバーでカード番号を扱わないから、セキュリティ的にも安心!

Pay.jpを利用するために必要なものは?

  • Pay.jpのアカウント:無料で登録OK
  • 公開鍵(フロント用)と秘密鍵(バックエンド用)のAPIキー:Pay.jpのダッシュボードで取得
  • JavaScript or バックエンド(Python, PHP, Nodeなど)の知識少し

デモで見る「1回課金」の実装イメージ

【初心者向け】Pay.jpとは?クレカ決済を爆速導入できるサービスを解説!

🖥️ フロントエンドの実装(Next.js)

tsxファイルで、トークン作成後にAPI呼び出しを行います。

下記の「✅ 1つ渡せばOK」のコードですが、cardNumber 要素だけを createToken に渡しても、同じ elements インスタンスから作られ、かつ mount() された要素が揃っていれば、Pay.jp 側で裏側で統合されて処理されます。

"use client";
import { useEffect, useRef } from "react";
import { createCharge } from "@/lib/api/charge";

export default function CardForm() {
  const numberRef = useRef<any>(null);
  const expiryRef = useRef<any>(null);
  const cvcRef = useRef<any>(null);

  useEffect(() => {
    const payjp = Payjp("pk_test_********");
    const elements = payjp.elements();

    numberRef.current = elements.create("cardNumber");
    expiryRef.current = elements.create("cardExpiry");
    cvcRef.current = elements.create("cardCvc");

    numberRef.current.mount("#card-number");
    expiryRef.current.mount("#card-expiry");
    cvcRef.current.mount("#card-cvc");
  }, []);

  const handleSubmit = async () => {
    const payjp = Payjp("pk_test_********");
    const result = await payjp.createToken(numberRef.current); // ✅ 1つ渡せばOK

    if (result.error) {
      alert("カード情報が正しくありません");
    } else {
      const token = result.id;
      await createCharge({ token, amount: 1000 });
    }
  };

  return (
    <>
      <div id="card-number" />
      <div id="card-expiry" />
      <div id="card-cvc" />
      <button onClick={handleSubmit}>支払う</button>
    </>
  );
}

tsファイルで、クライアントコンポーネントで取得したトークンと、金額をFastAPIサーバーへ安全に送信するためのAPI呼び出し関数

type ChargePayload = {
  token: string;
  amount: number;
};

export const createCharge = async (
  payload: ChargePayload
): Promise<"ok" | "error"> => {
  try {
    const res = await fetch(`${process.env.NEXT_PUBLIC_BACKEND_URL}/api/charge`, {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
      },
      body: JSON.stringify(payload),
    });
    return res.ok ? "ok" : "error";
  } catch (e) {
    return "error";
  }
};

🧪 バックエンドの実装(FastAPI)

Pay.jpのPython SDKを使って、受け取ったトークンを使い課金処理をします。
事前準備でPay.jpが提供しているPython用のSDK(ソフトウェア開発キット)pip install payjp とコマンド実行してインストールしましょう。

import payjp
from fastapi import FastAPI, Request

payjp.api_key = "sk_test_********"  # 秘密鍵を設定

app = FastAPI()

@app.post("/api/charge")
async def charge(request: Request):
    body = await request.json()
    token = body["token"]
    amount = body["amount"]

    try:
        charge = payjp.Charge.create(
            amount=amount,
            currency="jpy",
            card=token
        )
        return {"status": "success", "charge_id": charge.id}
    except payjp.error.PayjpError as e:
        return {"status": "error", "message": str(e)}

なぜトークン化はフロントで行う?

  • クレジットカード番号は絶対にバックエンドに送ってはいけない(セキュリティリスク)
    →クレジットカード番号は PCI DSS などの厳しいルールに則って管理する必要があり、サーバーで直接扱うと大きなセキュリティリスクになります。そのため、Pay.jsを使ってトークン化(疑似的なカード情報への変換)を行い、サーバーではそのトークンだけを扱うことで、セキュリティを保ちながら決済処理ができます。
  • Pay.jsがカード番号をトークンに変換してくれる(createToken)
  • 自分のサーバーではトークンしか扱わないため、安心・安全

実装注意ポイントまとめ

  • 公開鍵(pk_test_〜)はフロントで使う
  • 秘密鍵(sk_test_〜)はバックエンドで使う
  • カード番号などはトークン化され、自分のサーバーでは触れない仕組みになっている(PCI DSS対応)
  • 開発モードではテストカード 4242 4242 4242 4242 が使える(有効期限やCVCは適当でOK)
    テストカード一覧

他のAPI連携の記事はこちらです!

初心者におすすめなのはどれ?

条件おすすめサービス
はじめて決済を導入する人✅ Pay.jp
海外展開も視野に入れている場合✅ Stripe
店舗+ネットで使いたい✅ Square
コンビニ払いや多様な支払いを取り入れたい✅ Komoju
てんハロ運営者
てんハロ運営者

おつかれさまでした!

更新をF5連打で待つの、そろそろやめませんか?
( ブログ更新をメールでそっとお知らせします🙇‍♂️ )

スパムはしません!詳細については、プライバシーポリシーをご覧ください。

コメント