マキモノ
経理・バックオフィス無料✅ 公式検証済みv1.0.0 / 更新

freee会計API 取引先自動連携ガイド(OAuth/トークンローテーション/DRY-RUN)

Next.js+SupabaseアプリからfreeeのOAuth接続・refresh_tokenローテーション対応・取引先の自動紐付け/新規作成をDRY-RUN安全に実装する手順

出品者: kim@orgiast.jp2 DL📖 読込 約2,046トークン (約3円)💰 コスパ 66
トークン節約メーター90%節約
ゼロからAIに作らせた場合15万トークン
このMDを読ませた場合1.5万トークン

13.5万トークンの節約 (API料金換算で約200円分)。 要件定義・技術調査・試行錯誤ぶんのトークンがまるごと不要になります。※ 出品者申告とレビューに基づく推定値。モデル・タスク内容により変動します。

この巻物について

freee会計API 取引先自動連携ガイド(OAuth/トークンローテーション/DRY-RUN)」は、経理・バックオフィスカテゴリのAI指示書(MDファイル)です。Next.js+SupabaseアプリからfreeeのOAuth接続・refresh_tokenローテーション対応・取引先の自動紐付け/新規作成をDRY-RUN安全に実装する手順この巻物をAIに読み込ませると、ゼロから設計・調査する場合に比べて 約13.5万トークン(API料金換算で約200円)・90%のトークンを節約できます。

カテゴリ
経理・バックオフィス
対応AI
claude-code、cursor、codex-cli
ライセンス
商用利用可 (再販不可)
価格
無料
ゼロから開発時
約15万トークン
この巻物使用時
約1.5万トークン
節約量
約13.5万トークン (約200円)
更新日
2026-08-20

使い方 (AIに渡す3つの方法)

いちばん簡単なのはワンライナー。Claude Code のターミナルに貼るだけです。

⬇ .md をダウンロード
claude "https://makimono-md.vercel.app/api/v1/files/freee-api-oauth-dry-run/raw を読み込んで、この指示書どおりに実装して"
claude-codecursorcodex-cliライセンス: 商用利用可 (再販不可)

中身

freee会計APIと自社アプリの「取引先」自動連携 — OAuth・トークンローテーション・DRY-RUN安全パターン

前提

Next.js + Supabase(Postgres)構成のアプリで、自社の受注管理DBにある顧客(customer)を、freee会計の「取引先(partner)」と自動で紐付け/新規登録したい場合のリファレンス実装。他のDB(MySQL, Prisma等)・他のフレームワークでも設計思想はそのまま流用できる。

落とし穴1: freeeのrefresh_tokenは使い捨て(ローテーション)

freeeのOAuth refresh_tokenは1回使うと無効化され、レスポンスに含まれる新しいrefresh_tokenに置き換わる。これを知らずに固定の環境変数(.env)にrefresh_tokenを書いていると、初回のトークン更新後にアプリが動かなくなる。

対策: refresh_tokenをDBの専用テーブルで管理し、更新の都度DBへ書き戻す。

create table if not exists public.freee_tokens (
  id text primary key default 'default',
  client_id text not null,
  client_secret text not null,
  refresh_token text not null,
  access_token text not null,
  access_expires_at timestamptz not null,
  company_id integer not null,
  created_at timestamptz not null default now(),
  updated_at timestamptz not null default now()
);
alter table public.freee_tokens enable row level security;
revoke all on public.freee_tokens from anon, authenticated; -- service_roleのみ扱う
// lib/freee-token-service.ts の骨格
export async function getValidAccessToken(): Promise<string> {
  const row = await getTokenRow(); // DBから1行取得
  if (row.access_token && row.access_expires_at > Date.now() + 120_000) {
    return row.access_token; // 有効期限5分前まではそのまま使う
  }
  const res = await fetch("https://accounts.secure.freee.co.jp/public_api/token", {
    method: "POST",
    headers: { "Content-Type": "application/x-www-form-urlencoded" },
    body: new URLSearchParams({
      grant_type: "refresh_token",
      client_id: row.client_id,
      client_secret: row.client_secret,
      refresh_token: row.refresh_token,
    }),
  });
  const json = await res.json();
  // 新しいrefresh_tokenを必ずDBに書き戻す。ここを忘れると次回の更新で失敗する
  await saveTokenRow({
    access_token: json.access_token,
    refresh_token: json.refresh_token,
    access_expires_at: Date.now() + json.expires_in * 1000,
  });
  return json.access_token;
}

初回OAuth接続(人間が1回だけ操作する部分)

freeeは1つのfreeeアカウントが複数の事業所(company)を持てるため、認可URLにprompt=select_companyを付けて選択させる。接続後は必ずAPI(GET /api/1/companies)で実際の事業所名を取得して、想定した会社と一致するか確認すること(選択ミスに気づかず別会社に書き込む事故を防ぐ)。

https://accounts.secure.freee.co.jp/public_api/authorize?response_type=code&client_id=<CLIENT_ID>&redirect_uri=urn:ietf:wg:oauth:2.0:oob&prompt=select_company

認可コードは単回・短命(数分で失効)。表示されたらすぐにトークン交換スクリプトへ渡す。

落とし穴2: Next.js App Router の route.ts は決まったexportしか許されない

route.tsから独自のヘルパー関数をexportすると、Next.jsのビルド時型検証(.next/types/...)が「route.tsはGET/POST等の決まった名前以外をexportできない」というエラーを出し、ビルドが失敗する。ヘルパー関数は別のlibファイルに置き、route.tsからimportして使うこと。この制約は気づきにくく、tsc --noEmit単体では見逃す(Next.jsのbuild/typecheckコマンドで初めて出る)ので注意。

会社名の突合ロジック(表記ゆれの吸収)

function normalizeCompanyName(value: string): string {
  return value
    .normalize("NFKC") // 半角カナ→全角、㈱→(株)等の互換分解を含む
    .toLowerCase()
    .replace(/(\(株\)|\(有\)|株式会社|有限会社|合同会社|一般社団法人|医療法人|学校法人|特定非営利活動法人)/g, "")
    .replace(/[\s ・,.\-_]/g, "");
}

NFKC正規化を先に行うこと。順序を間違えると(例: 法人格の除去を先にやってからNFKCする)、のような合字が正規化後に別の文字列へ変わり、除去パターンが効かなくなる。

自動登録ロジックの安全設計

  1. 既定はDRY-RUN。書き込み系の新機能は必ず「何をする予定か」をログ・レスポンスで返すだけのモードを既定にし、明示的なフラグ(FREEE_DRY_RUN_DEFAULT=false)でのみ実書き込みを許可する。
  2. 既存の取引先が見つかれば紐付けのみ、無ければ新規作成。新規作成を先に試すと重複取引先を量産する。
  3. 一度紐付けたら二重実行しないようDBにfreee_partner_idのような列を持ち、is nullを対象条件に含める(冪等性)。
  4. 除外条件を忘れない: 論理削除(archived)された内部処理レコードや、自社の内部会計処理用の顧客レコード(自社名そのもの)は対象から除外する。これを忘れると、社内処理の記録が誤って取引先登録の対象に混ざる。
  5. ローカルでnext devを起動し、実際にcron routeをcurlで叩いてDRY-RUNの出力を目視確認してからデプロイする(型チェックが通るだけでは、クエリ条件の抜け漏れ等のロジックバグは検出できない)。

まとめ

  • refresh_tokenはDB管理+都度書き戻し(env固定は数時間で壊れる)
  • 接続後は実際の事業所名をAPIで確認(選択ミス対策)
  • route.tsから独自関数をexportしない(Next.js App Routerの制約)
  • 会社名正規化はNFKC→法人格除去→記号除去の順
  • 新機能はDRY-RUN既定、既存紐付け優先、冪等性列、除外条件を忘れない

よくある質問

「freee会計API 取引先自動連携ガイド(OAuth/トークンローテーション/DRY-RUN)」とは何ですか?

Next.js+SupabaseアプリからfreeeのOAuth接続・refresh_tokenローテーション対応・取引先の自動紐付け/新規作成をDRY-RUN安全に実装する手順

どれくらいトークン(費用)を節約できますか?

ゼロから開発すると約15万トークンかかりますが、この巻物を使えば約1.5万トークンで済みます。差し引き約13.5万トークン(API料金換算で約200円)・90%の節約です。

どうやって使いますか?

無料です。MDファイルを Claude Code などのAIに読み込ませるだけ。ワンライナーをターミナルに貼れば実装が始まります。要件定義や技術調査を省いて実装だけにトークンを使えます。

どのAIツールに対応していますか?

claude-code、cursor、codex-cli に対応しています。

商用利用できますか?

ライセンスは「商用利用可 (再販不可)」です。

🤝 自分でAIを動かすのは、まだ不安…という方へ

この巻物の内容を、AIを使うプロに丸ごと任せることもできます。姉妹サービスAI代行堂なら「LINEで頼むだけで、仕事が完成」。

AI代行堂を見る →

関連する巻物

この巻物、誰かのトークンも救えます

𝕏 で節約レシートをシェア