Skip to main content
CC Safety Net は、コマンドの判定を構造化された監査ログに書き込みます。このログから、エージェントが実行しようとした操作と、その判定結果を確認できます。形式は JSON Lines(JSONL)で、1 行に 1 つの JSON オブジェクトを記録します。ログはローカルマシンに保存されます。 このページでは、ファイル配置、レコードスキーマ、対象範囲、保持、マスクの制限を定義します。UI で読む場合はダッシュボード、ターミナルで読む場合は logsを参照してください。

ログの配置

レコードは、プロジェクトおよび月ごとのパスに書き込まれます。
セッション ID はファイル名に入る前にサニタイズされます。A-Za-z0-9_.- 以外の連続した文字は _ にまとめられます。先頭と末尾の .-_ は削除されます。結果は 128 文字に切り詰められます。サニタイズ後に空文字列、... になった場合、書き込み全体を中止します。これはパストラバーサルに対する防御であり、単なる書式調整ではありません。 ディレクトリはモード 0700 で作成され、ログファイルにはモード 0600 で追記されます。 書き込みの失敗は無視されます。監査ログは、許可またはブロックの判定を変更できません。
~/.cc-safety-net/logs/ の直下にあるフラットファイルは、以前のバージョンが使ったレガシー配置です。logs は今もこれらを読み、保持処理もこれらを対象にします。logs --prune-legacy は、このファイルを対象にします。新しいレコードがこの場所に書き込まれることはありません。

各レコードには 1 つの判定が入る

各行には、許可またはブロックされた 1 つのコマンド判定が記録されます。コマンド、判定の原因となったセグメント、理由、一致したルールが含まれます。
  • 書き込み処理では、コマンド出力、モデルプロンプト、ツール結果、会話内容を読み取らず、保存もしません。
  • 拒否は常に記録されます。
  • 許可の判定は、ツール呼び出しが実際にコマンドへルーティングされた場合にのみ記録されます。許可されたコマンド以外のツール呼び出しでは、レコードは作られません。
  • fail closed パスから生じたブロック、つまりアナライザーでエラーが発生し、推測せずにガードが拒否した場合も記録されます。このレコードには failureStageerrorCode が設定されるため、正確に検索できます。logs --suspect はこのフィールドを使います。

レコードスキーマ

レコードの例:

長さの上限と切り詰めインジケーター

上限はマスク処理のに適用されます。そのため、マスクの途中で文字列が切れてしまうことはありません。 failureStage を持つエントリは、fail closed の原因を調べるための主な記録です。そのため、コマンドは切り詰めずに全文を保存します。前段のツール入力のバイト数上限が、この長さをすでに制限しています。segmenttoolNamecwd の上限は変わらず、このエントリにも適用されます。 commandsegmenttoolNamecwd のいずれかが上限を超えると、レコードに truncated: true が追加されます。failureStage を持つエントリでは、コマンドにそもそも上限がありません。そのため、コマンドが長いというだけでこのフラグが付くことはありません。segmenttoolNamecwd はこれまでどおりフラグの原因になります。このフラグが false として書き込まれることはありません。フラグがなければ、何も切り詰められていません。logs --id は、これを truncated: yes または - として表示します。

記録内容:監査の対象範囲

CC_SAFETY_NET_AUDIT_SCOPE は、許可されたコマンド判定を拒否と一緒にログへ記録するかを決めます。 無効な値が黙って無視されることはありません。doctor は警告重大度の finding environment.audit-scope-invalid を生成します。内容は「Audit scope value is invalid」で、変数を all または blocked に設定して連携を再起動する修正ヒントが付きます。問題の値自体は意図的に表示されません。 拒否が対象範囲によって抑制されることはありません。対象範囲は許可の分岐のみを制御します。

保持

audit.retention_days は 1~365 の整数である必要があります。それ以外は検証で拒否されます。まったく使用できない値は、既定の 30 日にフォールバックします。保持期間は、ポリシーファイルから単独で直接読み取られます。そのため、ポリシーのほかの部分が検証に失敗しても削除処理は動作します。 同じ値が、logs --since の上限と GUI の Activity ビューが提示する期間を制限します。
保持期間の短縮は元に戻せません。スイープは実行ごとにカットオフを再計算します。値を小さくすると、既存のレコードが即座に削除対象になり、リンクが解除されます。アーカイブ、ゴミ箱、取り消しはありません。このため、GUI は値を小さくする前に確認を求めます。

削除処理は操作時に実行される

タイマーで動作する処理はありません。保持スイープは、次の操作によって開始されます。
  • 各監査書き込みの後。削除の失敗によってレコードが失われないように、意図的に書き込み後に実行する
  • logs が読み取る前
  • doctor がアクティビティの要約を作る前
  • GUI の Activity フィードが読み込まれる前
スイープは、監査ルートごとに UTC の 1 日に最大 1 回だけ走査します。監査ルートにある 0 バイトの .last-prune マーカーで抑制します。例外を送出せず、監査ルートを作成せず、シンボリックリンクをたどらず、認識しないファイル形式には触れません。空の月ディレクトリと空のプロジェクトディレクトリは回収されます。ただし、実行中の書き込みとの競合を避けるため、現在の月は残します。レガシーのフラットファイルを削除するのは、そのファイルのタイムスタンプと、中にあるすべてのレコードの両方から、完全に期限切れだと証明できる場合だけです。異なる経過時間のレコードを含むファイルは、書き換えも分割もされません。 何もスイープを開始しないため、CC Safety Net の操作がない間は、期限切れのレコードがディスクに残ることがありますlogs --id は、ディスク上にあるレコードを検索します。削除処理がまだ到達していない場合、保持期間を過ぎたレコードを返すことがあります。

レガシーログの削除

cc-safety-net logs --prune-legacy は、監査ルートにあるレガシーのフラットな *.jsonl ファイルをすべて即時かつ元に戻せない形で削除します。確認プロンプトも --yes フラグもありません。唯一のプレビューは --dry-run で、削除対象の正確なセットを報告し、何も削除しません。対象かどうかはファイルの場所だけで決まります。経過時間、スキーマの有効性、不正な行はすべて関係ありません。
これは保持スイープではありません。保持スイープは、完全に期限切れの場合にのみレガシーファイルを削除します。--prune-legacy は経過時間に関係なく削除します。ネストされたプロジェクトごとのログには入らず、触れません。そのことはコマンド出力にも表示されます。フラグの終了動作と拒否される組み合わせについては、logs --prune-legacyを参照してください。

件数と返されるエントリ

件数は期間全体を対象にします。エントリのリストには上限があるため、2 つの数値が異なることがあります。 logs がログを走査するとき、削除する必要があったすべてのソース、つまり読み取れないディレクトリ、読み取れないファイル、不正なレコードを数えます。標準エラー出力には 1 つの警告 warning: N audit log sources could not be read; these results are incomplete が出ます(N が 1 の場合は source)。パスは表示されません。標準出力と終了コードは変わらないため、--json の出力は解析可能な状態を保ちます。ログディレクトリがない場合は履歴が空であり、ソースの脱落ではないため、警告は出ません。 通常のリストと GUI の期間は、保持期間より前を表示しません。GUI は固定リストではなく保持値から期間の選択肢を導出します。ただし、期限切れのレコードが削除前にディスクに残っている間は、logs --id で直接検索すると返されることがあります。各保持設定で選べる期間については、ダッシュボードを参照してください。

シークレットのマスク

コマンド、セグメント、ツール名、作業ディレクトリは、レコードをシリアライズするにシークレットのマスク処理を通ります。認識された値は <redacted> に置き換えられます。
  • 名前に TOKENSECRETPASSWORDPASSKEYCREDENTIALS を含む環境変数代入
  • データベース接続変数(DATABASE_URLPOSTGRES_URLMYSQL_URLREDIS_URLMONGODB_URL、その他の DSN、URL、URI、接続文字列変数)
  • PEM 秘密鍵ブロック(-----BEGIN ... PRIVATE KEY-----
  • シークレットを含む HTTP ヘッダー(AuthorizationCookieX-API-KEYAPI-KEY
  • URL 資格情報(scheme://user:pass@hostscheme://token@host)および -u user:pass
  • 署名済み URL の署名クエリパラメーター。テキストの先頭、空白、?&;| の後にパラメーター名がある場合に、大文字と小文字を区別せず x-amz-signaturex-goog-signaturesigsignature の値を処理する
  • 固定リストにあるプロバイダートークン形式(ghp_...gho_...xoxb-...npm_...sk_live_...rk_live_...pypi-... など)
  • JWT(eyJ...)と AWS アクセスキー ID(AKIA... / ASIA...
マスクの範囲は限定されています。 これは固定のパターン一覧であり、分類器ではありません。認識できないものはすべてそのまま残ります。絶対パス、プロジェクト名やディレクトリ名、ホスト名、IP アドレス、ユーザー名、チケット ID、ファイル名、一覧にない形式の資格情報などが該当します。reason フィールドは、書き込み時にマスク処理を一切受けません。監査ログは機密性のあるローカルデータとして扱い、Issue やチャットに抜粋を貼り付ける前に必ず内容を確認してください。
GUI が誤検知レポートを送る前に、ホームディレクトリの接頭辞は削除されます。そのほかのパスはレポートに残ることがあります。 パーミッション(ディレクトリは 0700、ファイルは 0600)とローカル保存はアクセスを制限するだけで、ログの内容をマスクするわけでも、そのまま共有して安全な状態にするわけでもありません。

関連ページ

最終更新日 2026年9月3日