Claude Codeのclaude.aiサインインがいつ切れるかを確かめる:auth statusのloginExpiresAtとclaude -pの期限警告

Claude Codeのclaude.aiサインインがいつ切れるかを確かめる:auth statusのloginExpiresAtとclaude -pの期限警告

Claude Code 2.1.318で、保存したclaude.aiサインインが切れる日時をclaude auth statusとclaude -pの結果で取れるようになりました。残り日数ごとの表示と日時が出ないログイン方法を調べ、残り日数をチェックするスクリプトも試しました。
2026.11.14

どうも!オペ部の西村祐二です!

Claude Codeにclaude.aiのアカウント(Pro・Maxなど)でログインしたまま、claude -p をcronや定期タスクから動かしていると、そのサインインがいつ切れるのかが気になります。公式ドキュメントによると、保存したログインが切れて更新もできなくなると、サインインし直すまでモデルへのリクエストは失敗します。

Claude Code 2.1.318で、保存したclaude.aiサインインが切れる日時を、次の3か所で確かめられるようになりました。

  • claude auth status のJSONの loginExpiresAt
  • claude -p --output-format json の結果の credential_expires_at
  • claude -p のテキスト出力で、切れる10日前からstderrに出る1行の警告

この記事では、期限を変えたダミーのログイン情報を用意して、残り日数ごとに何が表示されるか、どのログイン方法だと日時が出ないかを確かめました。定期実行の前に残り日数をチェックする短いスクリプトも試しています。

今回の変更点

  • 対象バージョン / 日付: Claude Code 2.1.318(2026年11月4日公開)
  • 変更の要点:
    • 上の3か所の追加(リリースノートでは、2つのフィールドの追加と、10日前からの警告の2項目)
    • あわせて、保存したclaude.aiログインが期限に達したときのサインイン失敗が、期限に達したことを伝え、claude -p では claude auth login と claude setup-token を案内するように直った(実際の表示は確かめていません)
  • 公式リンク: v2.1.318 リリースノート

loginExpiresAtはアクセストークンの期限ではない

2026年11月14日時点で、Claude Codeのドキュメント(AuthenticationとCLI referenceのページ)には、この日時が何を表すかの説明はありませんでした。Claude Agent SDK(TypeScript)の型定義 sdk.d.ts にある credential_expires_at の説明では、次のように説明されています(0.3.323で確認)。

  • 保存済みのclaude.aiログインでは、サインイン時に記録した期限を表す。サインインし直さずにアクセストークンを更新し続けられる期限(型定義の言葉ではrefresh chainの終わり)で、アクセストークンを更新してもこの日時は動かない
  • サーバーが日時を返した場合はその値、返さなかった場合は30日の見積もりを使う
  • 実際に切れるのは、この日時より最大3日早いことがある
  • サーバーには問い合わせないため、途中で取り消されたログインでも日時は残る。過去の日時はおそらく切れたことを表し、切れたと決まったわけではない
  • APIキー、環境変数で渡したトークン、ほかのプロバイダーを使う場合は出ない

つまり、Claude Codeがアクセストークンを自動で更新し続けていても、この日時(早ければその3日前)までにサインインし直す必要があります。このあとの検証で確かめた表示の変化を、残り日数とClaude Codeの表示の関係として図にまとめました(自作の図です)。

自作した概念図。claude -pのテキスト出力では、期限の10日前までは警告なし、10日前からはin N days at the earliestの警告、期限の3日前からはcan end at any time、期限日を過ぎるとmay have endedと変わる。claude auth status --textは、期限の3日前まではSign-in ends: between、その後はany day now、期限日を過ぎるとmay have endedになる

claude -p の警告は期限の10日前から出て、表示の文言は期限の3日前(以下、最も早い日)と期限日で切り替わります。claude auth status --text の表示は、10日前を境には変わりません。

なお、対話モードについては、公式ドキュメントによると、期限の3日前から起動時に Your login expires in 3 days · run /login to renew と表示されます。定期実行の claude -p には関係しないため、今回は対話モードの画面は確かめていません。

試してみる

環境と確かめ方

  • OS: Ubuntu 24.04(Dockerコンテナ、aarch64)。macOS 26.7.2(Claude Code 2.1.319)では、実際のclaude.aiログインで claude auth status だけを確認
  • ツール: Claude Code 2.1.322(変更後)、2.1.317(変更前の比較用)、jq 1.7
  • 実行日時: 2026年11月14日5時台(日本時間)、UTCでは11月13日20時台。Claude Codeは日付をUTCで表示するため、以下の出力の日付は11月13日(UTC)が起点です

LinuxのClaude Codeは、claude.aiのログイン情報を ~/.claude/.credentials.json に保存します(公式ドキュメント)。このファイルは、切れる日時(refreshTokenExpiresAt)だけ変えたダミーの内容で用意し、ケースごとに新しいホームディレクトリで実行しました。ファイルの中身はClaude Codeの内部形式で、今後変わる可能性があります。

claude -p のリクエストは、ANTHROPIC_BASE_URL でコンテナ内のテスト用APIサーバー(どのリクエストにも ok と返すだけのもの)に向けています。実際のモデルにはリクエストしていません。

1. claude auth statusで切れる日時を見る

切れる日時を5日後にしたダミーのログインで、claude auth status を実行しました。--text を付けると、人が読む形式で表示されます。

claude auth statusのJSONにloginExpiresAtが入り、--textではSign-in endsの行に最も早い日と期限日が出ている画面

JSONの loginExpiresAt には、ログイン情報に入れた日時がそのまま(ミリ秒まで)出ました。--text では Sign-in ends: between 2026-11-15 and 2026-11-18 のように、最も早い日から期限日までの幅で表示されます。Agent SDKの説明にある「最大3日早く切れることがある」点を、表示に反映しています。Login method の行はダミーのログイン情報による表示で、Anthropic base URL の行はテスト用サーバーに向けているために出ている行です。

期限を変えたときの --text の表示は次のとおりです。

切れる日時 claude auth status --text の表示
20日後 Sign-in ends: between 2026-11-30 and 2026-12-03 (...)
5日後 Sign-in ends: between 2026-11-15 and 2026-11-18 (...)
2日後(最も早い日を過ぎている) Sign-in ends: any day now, by 2026-11-15 (...)
期限を1日過ぎている Sign-in may have ended: between 2026-11-09 and 2026-11-12 (...)

macOSの実際のログインでも、claude auth status の loginExpiresAt に日時が入り、--text に Sign-in ends: の行が出ました。macOSではログイン情報をKeychainに保存するため、上記のようにファイルを書き換える確かめ方はしていません。サインインした日がはっきりしないため、実際のサインインで期限がどれくらいの長さになるかも確かめていません。

2. claude -pの警告とcredential_expires_atを見る

同じく切れる日時を5日後にしたダミーのログイン(撮影ごとに作り直したため、1枚目とは時刻が数十秒ずれています)で、claude -p をテキスト出力とJSON出力で実行しました。応答はファイルにリダイレクトし、端末にはstderrだけが出るようにしています。

claude -pのテキスト出力ではstderrに警告が1行出て、JSON出力ではcredential_expires_atに期限が入っている画面

テキスト出力では、stderrに次の警告が出ました。stdoutの応答(ok)には混ざっていません。

Warning: this sign-in ends between 2026-11-15 and 2026-11-18 (in 2 days at the earliest). Renewing it does not move those dates. Run claude auth login before then, or use claude setup-token for unattended jobs.

警告では、サインインし直すコマンド(claude auth login)と、無人のジョブ向けの別の方法(claude setup-token。1年有効のトークンを発行するコマンド)まで案内しています。

JSON出力では、同じログインで実行すると credential_expires_at に loginExpiresAt と同じ日時が入り、stderrには何も出ませんでした。

切れる日時を変えて、テキスト出力の警告が出るかを比べました。

切れる日時 テキスト出力の警告(stderr)
11日後 出ない
10日後より1分あと 出ない
10日後より1分前 this sign-in ends between 2026-11-20 and 2026-11-23 (in 7 days at the earliest)
9日後 this sign-in ends between 2026-11-19 and 2026-11-22 (in 6 days at the earliest)
5日後 this sign-in ends between 2026-11-15 and 2026-11-18 (in 2 days at the earliest)
2日後 this sign-in can end at any time from now until 2026-11-15
期限を1日過ぎている this sign-in may have ended between 2026-11-09 and 2026-11-12

警告は期限日の10日前から出ました。括弧内の日数は、期限日ではなく最も早い日までのものです。期限を1日過ぎたケースでもテスト用サーバーは応答を返しましたが、これはサーバーが認証を検証していないためです。実際のサービスでリクエストが拒否されるかは確かめていません。

日付はUTCで表示されます。TZ=Asia/Tokyo を付けて5日後のケースを実行しても、表示は日本時間の日付(11-16 / 11-19)ではなく、UTCの日付(between 2026-11-15 and 2026-11-18)でした。日数(in N days)は、このケースではどちらで数えても同じになり区別できませんが、Claude Code本体に含まれるコードを見ると、UTCの日付の差で数えていました。

3. 日時が出ないケースを確かめる

ログイン方法やバージョンを変えたときの結果です。

条件 claude auth status claude -p のJSON テキスト出力の警告
claude.aiログイン(切れる日時の記録なし) authMethod: "claude.ai"、loginExpiresAt: null credential_expires_at なし 出ない
ANTHROPIC_API_KEY authMethod: "api_key"、loginExpiresAt: null credential_expires_at なし 出ない
CLAUDE_CODE_OAUTH_TOKEN authMethod: "oauth_token"、loginExpiresAt: null credential_expires_at なし 出ない
2.1.317 で5日後のログイン loginExpiresAt のキー自体がない credential_expires_at なし 出ない

1行目は、ログイン情報ファイルから切れる日時の値を消して再現しました。実際のログインでどういう場合にこの状態になるかは確かめていません。claude auth status では loginExpiresAt のキーは残って値が null になり、claude -p のJSONではキーごとなくなります。jqの // empty を使えば、どちらの形でも空として扱えます。

CLAUDE_CODE_OAUTH_TOKEN は、claude setup-token で発行したトークンを渡す環境変数です。この方法では切れる日時が出ないので、発行した日を自分で控えておく必要があります。

定期実行の前に残り日数を確かめる

claude auth status はモデルにリクエストしないので、ジョブの前や別の定期チェックで呼べます。最も早い日(loginExpiresAt の3日前)までの日数を数え、しきい値を下回ったら終了コード1を返すスクリプトを書きました。jqが必要です。

check-sign-in.sh
#!/bin/bash
# 保存済みの claude.ai サインインが、早ければ何日後に切れるかを確かめる
# loginExpiresAt は「最大で3日早く切れることがある」日時なので、3日前を基準に数える
threshold_days=${1:-7}

status=$(claude auth status) || { echo "claude auth status が失敗しました(未ログインなど)" >&2; exit 1; }
exp=$(printf '%s' "$status" | jq -r '.loginExpiresAt // empty')
if [ -z "$exp" ]; then
  echo "loginExpiresAt がありません(claude.ai のログイン以外、または期限が記録されていないログイン)"
  exit 0
fi

earliest=$(jq -rn --arg e "$exp" '$e | sub("\\.[0-9]+Z$"; "Z") | fromdateiso8601 - 3 * 86400')
# Claude Code の警告と同じく、UTC の日付の差で数える
left=$(( earliest / 86400 - $(date +%s) / 86400 ))

if [ "$left" -lt "$threshold_days" ]; then
  echo "サインインが切れる最も早い日まで残り ${left} 日です(loginExpiresAt: $exp)" >&2
  exit 1
fi
echo "サインインが切れる最も早い日まで残り ${left} 日です(loginExpiresAt: $exp)"

claude auth status は未ログインのとき終了コード1を返すので(CLI reference)、その場合もスクリプトは終了コード1で止まります。jqの fromdateiso8601 は秒の小数部を読めないため、sub でミリ秒を落としています。日数をUTCの日付の差で数えているのは、Claude Codeの警告と数字をそろえるためです。24時間単位の切り捨てで数えると、5日後のケースが警告より1日少ない「1日」になります。

しきい値を7日にして、前の節で使ったダミーのログイン情報で実行しました。

# 20日後(終了コード 0)
サインインが切れる最も早い日まで残り 17 日です(loginExpiresAt: 2026-12-03T20:14:46.229Z)
# 5日後(終了コード 1)
サインインが切れる最も早い日まで残り 2 日です(loginExpiresAt: 2026-11-18T20:14:51.928Z)
# 期限を1日過ぎている(終了コード 1)
サインインが切れる最も早い日まで残り -4 日です(loginExpiresAt: 2026-11-12T20:15:14.786Z)
# 切れる日時の記録なし / CLAUDE_CODE_OAUTH_TOKEN(終了コード 0)
loginExpiresAt がありません(claude.ai のログイン以外、または期限が記録されていないログイン)
# 未ログイン(終了コード 1)
claude auth status が失敗しました(未ログインなど)

5日後のケースの「2日」は、claude -p の警告の in 2 days at the earliest と一致しました。

ジョブの前に置くなら、ジョブは止めずに記録や通知だけ残す形が使いやすそうです。例えば次のようにします。

bash check-sign-in.sh 7 || echo "$(date) claude.ai のサインインの期限が近い" >> "$HOME/claude-sign-in.log"
claude -p "..."

検証結果の考察

  • 確認できたこと:
    • 2.1.322では、保存したclaude.aiログインの切れる日時が loginExpiresAt と credential_expires_at に同じ値で出て、2.1.317では出なかった
    • テキスト出力の警告は、期限日まで10日を1分切ると出て、1分超えると出なかった。stdoutの応答には混ざらず、JSON出力では出ない
    • 残り日数と between の表示は最も早い日を過ぎると any day now / can end at any time に、期限日を過ぎると may have ended に変わる。日付はUTCで表示し、日数もUTCの日付の差で数えている(日数は本体のコードで確認)
    • APIキー、CLAUDE_CODE_OAUTH_TOKEN、切れる日時の記録がないログインでは日時が出ない
  • 公式情報と照合したこと:
    • 10日前からの警告と2つのフィールド名は、v2.1.318のリリースノートと一致した
    • Agent SDKの型定義にある「最大3日早く切れることがある」という説明は、between <最も早い日> and <期限日> の表示と一致した。期限を過ぎた日時でも、切れたと言い切らずに may have ended と表示した点も、型定義の説明と合っている(サーバーに問い合わせないこと自体は、型定義の記述に基づく)
  • 運用上の注意点:
    • テキスト出力のジョブでstderrを捨てていると、警告に気づけない
    • JSON出力のジョブでは警告が出ないので、credential_expires_at を記録するか、上のようなチェックを別に置く
    • claude setup-token のトークンは1年有効で長期の無人実行に向くが、切れる日時は出ないので、発行日を控えておく

ダミーのログイン情報とテスト用サーバーでは、次の3点は確かめられませんでした。

  • 実際のサインインで期限がどれくらいの長さになるか(サーバーの値か、30日の見積もりか)
  • アクセストークンを更新しても期限が動かないこと
  • 期限を過ぎたログインが実際に拒否される様子

これらについての記述は、いずれもAgent SDKの型定義と公式ドキュメントに基づいています。実際の期限の長さが分からないため、スクリプトのしきい値(例では7日)は、自分の loginExpiresAt を見て決めるのが良さそうです。

まとめ

Claude Code 2.1.318から、保存したclaude.aiサインインが切れる日時を、claude auth status の loginExpiresAt と claude -p のJSONの credential_expires_at で取れるようになりました。テキスト出力では、期限の10日前からstderrに警告が出ます。この日時はアクセストークンの期限ではなく、更新しても延びないサインインそのものの期限で、実際には最大3日早く切れることがあります。期限の3日前を過ぎると表示は any day now / can end at any time に、期限を過ぎると may have ended に変わります。

claude.aiのログインで定期実行しているなら、claude auth status で残り日数のチェックを置いておくと、ジョブが止まる前に気づけます。APIキーや claude setup-token のトークンではこの日時は出ません。1年で切れる claude setup-token のトークンは、発行日を自分で控えておくことになります。

誰かの参考になれば幸いです。


参考リンク:


Claudeならクラスメソッドにお任せください

クラスメソッドは、Anthropic社とリセラー契約を締結しています。各種製品ガイドから、業種別の活用法、フェーズごとのお悩み解決などサービス支援ページにまとめております。まずはご覧いただき、お気軽にご相談ください。

サービス詳細を見る

この記事をシェアする

AI白書

関連記事