DynamoDB TTL attribute must be a Number

TL;DR — DynamoDB の Time to Live は、指定された TTL 属性が 秒単位の Unix エポックタイムスタンプ を表す Number を保持するときのみアイテムを削除します。"1735689600" のような文字列、ミリ秒値、ISO-8601 の日付、または欠落した属性は黙って無視され、アイテムは決して期限切れになりません。TTL をエポック秒の Number として格納し、影響を受けたアイテムを書き直してください。

意味

# A second UpdateTimeToLive call within one hour of the first raises:
ValidationException  (TTL settings can only be modified once per table per hour)

# The quieter failure — no error at all, item just never expires:
TTL attribute "expiresAt" = "2026-01-01T00:00:00Z"   ← String, ignored
TTL attribute "expiresAt" = 1735689600000            ← milliseconds: tens of thousands of years away

TTL の有効化(UpdateTimeToLive)は、属性がまだ存在しない、または誤った型でも成功します。DynamoDB は前もって型チェックしません。失敗は後で現れます: バックグラウンドの TTL プロセスは、属性が過去(かつ 5 年以内の過去)の 秒単位の Unix エポックタイムスタンプ を保持する Number のときのみアイテムを削除します。それ以外はすべて「期限切れなし」として扱われます。

発生する理由

  • 文字列として格納された — 値が {"N": "1735689600"} ではなく {"S": "1735689600"}。TTL は N 以外の型を無視します。
  • 秒ではなくミリ秒Date.now()(JavaScript)はミリ秒を返します。13 桁の値は数万年先の未来なので、アイテムは事実上決して期限切れになりません。
  • エポック秒ではなく ISO-8601 / 人間可読の日付文字列
  • 5 年より前の過去のタイムスタンプ — TTL プロセスはアイテムを削除する代わりにそれを無視します。
  • TTL に登録されたのとは 別の属性名(名前は大文字小文字を区別します)。
  • UpdateTimeToLive を早すぎるタイミングで再度呼び出す — 変更が完全に処理されるまで最大 1 時間かかり、その 1 時間の間に同じテーブルへの追加の UpdateTimeToLive 呼び出しは ValidationException を発生させます。

修正方法

  1. TTL 値をエポック秒の Number として書き込みます — JavaScript では Math.floor(Date.now() / 1000) + ttlSeconds、Python では int(time.time()) + ttl。決してミリ秒を格納しないでください。
  2. S ではなく N 型を使います。低レベルクライアントではそれは {"N": "1735689600"} です。Document Client はネイティブの数値を代わりにマーシャルします。
  3. 大文字小文字を含め、登録された属性名に正確に一致させますDescribeTimeToLive で確認します。
  4. 既存のアイテムをバックフィルします — 修正前に書かれたアイテムは依然として不正な値を持ちます。正しいエポック秒の Number で書き直します。
  5. TTL 設定変更の間は 1 時間待ちますUpdateTimeToLive は処理に最大 1 時間かかり、そのウィンドウ内のさらなる呼び出しは ValidationException で拒否されます。

テーブルを閲覧しながらすべての属性のワイヤー型を見たいですか?DynoTable デスクトップアプリN/S/M 型タグをインラインでレンダリングするため、文字列として格納された TTL が、期限切れにならないアイテムのコストになる前に飛び出します。

よくある質問

DynamoDB の TTL がアイテムを削除しないのはなぜですか? TTL 属性は、秒単位の Unix エポックタイムスタンプを保持する Number である必要があります。文字列値、ミリ秒値、ISO 日付、または登録された TTL 属性と一致しない名前は、すべて黙って無視されるため、アイテムは決して期限切れになりません。削除も即時ではありません。DynamoDB は通常、期限切れ時刻から数日以内に期限切れアイテムを削除します。

TTL を有効にするとき DynamoDB は TTL 属性の型を検証しますか? いいえ。UpdateTimeToLive は、属性が欠落していても誤った型でも成功します。型要件(Number、エポック秒)はバックグラウンドの削除プロセスによってのみ強制されるため、不正な TTL は静かに失敗します。

関連するエラー

参考資料

最終検証日 2026-07-13、上記にリンクした公式 AWS ドキュメントに照らして確認しました。

Console なしで DynamoDB を扱う

DynamoDB では実行できない本物の SQL(JOINs、GROUP BY、集計)を実行する高速な DynamoDB デスクトップクライアント。ビジュアル編集と、あなた自身の Bedrock キーで動く AI エージェントを備えています。

30日間無料トライアル、クレジットカード不要 — その後は期限のない Free プラン。