概要
アプリケーションのログに、メールアドレスや患者番号のような個人情報・医療情報がうっかり出力されてしまうことがあります。ログはアプリケーションの開発者や運用担当者など多くの人が見るため、気づかないまま残しておくと、見せてはいけない人にまで情報が見えてしまいます。
Amazon CloudWatch Logs の データ保護ポリシー を使うと、ロググループに取り込まれるログから機密データを検出し、マスク(伏せ字)にできます。機密データが見つかると、CloudWatch に LogEventsWithFindings メトリクスが送られるので、これに CloudWatch アラームを付ければ、機密データがログに出たことを通知できます。
この記事では、データ保護ポリシーの仕組み、マネージドデータ識別子とカスタムデータ識別子の違い、マスクを外して見るための権限、Amazon Macie や Amazon GuardDuty との違いを整理します。実践では、ロググループにデータ保護ポリシーを設定し、メールアドレスと患者番号を含むログがマスクされることを確かめてから、LogEventsWithFindings にアラームを付けて、アラーム状態になるところまでを確認します。

クラウドおさる猿山の当番日誌に、うっかりバナナ倉庫の合言葉を書いてしまう猿がいるのでござる。書かれた瞬間に墨で塗り、長老に知らせる仕組みを CloudWatch Logs で作るでござるよ。
この記事のメリット
- CloudWatch Logs のデータ保護ポリシーで、ログの機密データがいつ・どう検出されマスクされるかを説明できるようになる
- マネージドデータ識別子とカスタムデータ識別子を使い分けられるようになる
LogEventsWithFindingsメトリクスにアラームを付けて、機密データの出力を通知できるようになる- Amazon Macie・Amazon GuardDuty・メトリクスフィルターとの違いを整理し、ログの機密データ対策に合う手段を選べるようになる
執筆者とキャラクター紹介
執筆者:土肥(とひ)
株式会社ジェニュインの代表であり元エンジニア。これまでオンプレミスと AWS 環境のインフラ業務を担当。AWS 認定資格の学習で得た知識を、ハンズオンとともに解説するのが得意。直近では新人の教育も行っており、これから技術を学ぶ方が納得できる解説を心がけています。基礎編・Cloud Practitioner の記事では、解説役としても登場します。


クラウドおさる



はじめましてでござる。弊猿はクラウドおさる。IT インフラが異常に発達した猿山から、雲に乗って地上の AWS を学びに降りてきたのでござる。



基礎編や Cloud Practitioner の記事では、とひさんに素朴な疑問をぶつける役でござるな。Security - Specialty などの記事では、要所でワンポイントや注意点をひとこと添えるでござる。



猿山にもデータセンターや監視当番があって、地上で起きることはだいたい猿山にも同じ仕組みがあるのでござる。例え話がつい猿山に寄るのは、弊猿の癖でござる。
技術解説
データ保護ポリシーとは
データ保護ポリシーは、CloudWatch Logs のロググループに取り込まれるログイベントから機密データを 監査(検出) し、マスク するための設定です。
| 項目 | 内容 |
|---|---|
| 設定の範囲 | 1 つのロググループ、またはアカウント全体(既存と今後作るロググループのすべて) |
| ロググループごとの数 | 1 つ。1 つのポリシーで複数のデータ識別子を指定できる |
| 対象のログクラス | 標準ログクラスと低頻度アクセスログクラスの両方 |
| 検出・マスクのタイミング | ロググループに取り込まれるとき。ポリシーを設定する前に取り込まれたログはマスクされない |
| マスクされる場所 | ログイベントの表示、CloudWatch Logs Insights、メトリクスフィルター、サブスクリプションフィルターなど、すべての出力先 |
アカウント全体のポリシーと、ロググループ単位のポリシーの両方があるときは、両方が適用されます。どちらかで指定したデータ識別子は、すべて検出・マスクされます。



墨で塗られるのは、ポリシーを掛けた後に書かれた日誌だけでござる。すでに書かれてしまった分は塗られぬので、気づいた時点で過去のログの扱いも別に考える必要があるのでござるぞ。
データ識別子
何を機密データとみなすかは、データ識別子 で指定します。
| 種類 | 内容 |
|---|---|
| マネージドデータ識別子 | AWS が用意したもの。認証情報(AWS シークレットアクセスキーなど)、財務情報(クレジットカード番号など)、個人を特定できる情報(PII。メールアドレス、運転免許証番号など)、保護対象保健情報(PHI。健康保険や医療の識別番号など)、デバイス識別子(IP アドレスなど)の 5 つのカテゴリがある |
| カスタムデータ識別子 | 自分で名前と正規表現を指定する。社員番号や患者番号のような、組織固有の形式を検出できる。1 つのポリシーに 10 個まで、正規表現は 200 文字まで |
マネージドデータ識別子の検出には、パターンマッチングと機械学習モデルが使われます。種類によっては、データの近くに特定のキーワード(例: 健康保険請求番号なら hicn など)があることも検出の条件になります。PHI の識別子は米国・EU・英国・カナダなど特定の国や地域の番号を対象にしているので、国内の医療機関で使う患者番号のような独自の形式は、カスタムデータ識別子で検出します。
関係のないデータ識別子をたくさん選ぶと、誤検出が増える可能性があります。ログに出る可能性があるデータに絞って選ぶことが推奨されています。



世の中に広く通じる合言葉はマネージドデータ識別子、猿山だけの札番号はカスタムデータ識別子、と分けて考えるとよいのでござるな。
マスクを外して見るには
マスクされた元のデータを見られるのは、logs:Unmask の権限を持つユーザーだけです。AWS 管理ポリシー CloudWatchLogsFullAccess には logs:Unmask が含まれています。権限を持つユーザーは、ログストリームの表示で「表示」→「マスク解除」を選ぶか、CloudWatch Logs Insights のクエリで unmask(@message) を使うと、元の値を確認できます。ログを見る人の多くには logs:Unmask を渡さず、調査が必要な担当者だけに渡す、という分け方ができます。
検出を通知する
機密データが検出されると、AWS/Logs 名前空間に LogEventsWithFindings メトリクス(機密データに一致したログイベントの数。統計は Sum)が送られます。このメトリクスは無料で、CloudWatch アラーム・グラフ・ダッシュボードで使えます。アラームの条件を「合計が 1 以上」にして、アクションで SNS トピックに通知すれば、ログに機密データが出たことをすぐに知れます。
検出の詳細(どのデータ識別子に、どのログイベントが一致したか)が欲しい場合は、ポリシーの監査結果の送信先として、CloudWatch Logs のロググループ、Amazon Data Firehose、Amazon S3 を指定できます。送信先を指定しなくても、マスクとメトリクスの送信は行われます。


ほかのサービスとの違い
| サービス・機能 | CloudWatch Logs の機密データ対策に使えるか |
|---|---|
| CloudWatch Logs のデータ保護ポリシー | 使える。取り込み時に検出・マスクし、LogEventsWithFindings でアラームを付けられる |
| Amazon Macie | Amazon S3 に保存されたデータの機密データを検出するサービス。CloudWatch Logs のロググループは対象外 |
| Amazon GuardDuty | AWS アカウントやワークロードへの脅威(不審な API 呼び出しや通信など)を検出するサービス。ログの中身の機密データは探さない |
| メトリクスフィルター | ログのパターンに一致した件数をメトリクスにできるが、パターンは自分で書く必要があり、マスクはしない |
実践
医療系アプリのログを想定したロググループ /soa/clinic-app に、メールアドレス(マネージドデータ識別子)と患者番号(カスタムデータ識別子)を検出・マスクするデータ保護ポリシーを設定します。CloudShell からテスト用のログを送ってマスクされることを確かめ、LogEventsWithFindings メトリクスに付けたアラームがアラーム状態になることを確認します。
前提条件
- リージョン:
ap-northeast-1(東京) - 以下のリソースが作成済みであること
まだ用意していない場合は、「作り方の参考」の記事の手順で作れます。リソース名は、この記事の名前に読み替えてください。
| リソース種別 | リソース名 | 内容 | 作り方の参考 |
|---|---|---|---|
| CloudWatch Logs ロググループ | /soa/clinic-app | 医療系アプリのログの出力先(標準ログクラス) | ─ |
| SNS トピック | soa-sensitive-data-alerts | アラームの通知先(標準トピック) | Amazon SNS でトピックを作成しメッセージを配信する |
※ この記事では、通知がトピックに届くところまでを扱います。メールなどで受け取るには、トピックにサブスクリプションを追加します。
作成するリソース一覧
| リソース種別 | リソース名 | 用途 |
|---|---|---|
| データ保護ポリシー | (/soa/clinic-app に設定) | メールアドレスと患者番号の検出・マスク |
| カスタムデータ識別子 | PatientId | 患者番号(PT- に続く 8 桁の数字)を検出する |
| ログストリーム | test-01 | テスト用のログの送り先 |
| CloudWatch アラーム | soa-sensitive-data-alarm | LogEventsWithFindings が 1 以上になったら通知 |
手順 1: データ保護ポリシーを作る
AWS マネジメントコンソールにログインし、リージョンが ap-northeast-1(東京)であることを確認します。上部の検索バーに CloudWatch と入力し、「CloudWatch」を選択します。
左側ナビゲーションの「ログ」→「ロググループ」を選択し、/soa/clinic-app を選択します。「アクション」→「データ保護ポリシーを作成」を選択します。「データ保護ロググループポリシー」の作成画面が開くので、以下を設定します。
- マネージドデータ識別子: 「データ識別子を選択」を開き、
EmailAddressで絞り込んで「EmailAddress」を選択 - 「カスタムデータ識別子を追加」をクリックし、名前:
PatientId、正規表現:PT-[0-9]{8}を入力 - 監査結果の送信先: どれも選択しない


「データ保護をアクティブ化」をクリックします。ロググループの詳細の「データ保護」タブで、ポリシーが有効になり、2 つのデータ識別子が設定されていることを確認します。
手順 2: 機密データを含むログを送る
コンソール下部の「CloudShell」をクリックして CloudShell を開き、次のコマンドを実行します。ログストリーム test-01 を作り、患者番号とメールアドレスを含むログと、含まないログを 1 件ずつ送ります。
LG=/soa/clinic-app
aws logs create-log-stream --log-group-name "$LG" --log-stream-name test-01
now=$(date +%s%3N)
aws logs put-log-events --log-group-name "$LG" --log-stream-name test-01 --log-events \
"[{\"timestamp\":$now,\"message\":\"reservation created patient=PT-20261021 contact=banana.taro@example.com\"},{\"timestamp\":$now,\"message\":\"reservation list loaded count=3\"}]"コマンドが rejectedLogEventsInfo のエラーを返さずに終わることを確認します。
手順 3: ログがマスクされたことを確かめる
CloudWatch のコンソールに戻り、/soa/clinic-app の「ログストリーム」タブで test-01 を選択します。1 件目のログでは、患者番号とメールアドレスの部分が * で伏せられています。2 件目のログはそのまま表示されています。


画面右上の「表示」→「マスク解除」を選ぶと、元の値が表示されます。いまログインしているユーザーが logs:Unmask の権限を持っているためです。



同じログでも、logs:Unmask を持たぬ者には墨塗りしか見えないのでござる。日誌を読む猿と、墨を剥がせる猿を分けておけるのでござるな。
手順 4: LogEventsWithFindings メトリクスを確かめる
左側ナビゲーションの「メトリクス」→「クラシックメトリクス」を選択します。「参照」タブで「Logs」→「DataProtectionOperation, LogGroupName」を選択し、LogGroupName が /soa/clinic-app の LogEventsWithFindings の行にチェックを入れます。メトリクスはロググループごと(ディメンション LogGroupName)に出ます。ログを送ってから表示されるまで 2 分ほどかかります。
「グラフ化したメトリクス」タブで、統計を「合計」、期間を「1 分」に変更します。既定の「平均」「5 分」のままだと「データがありません」と表示されることがあります。手順 2 で送った時刻に、値が 1 のデータポイントが表示されます。送ったログは 2 件ですが、機密データを含むログイベントは 1 件なので、値は 1 です。


手順 5: アラームを作る
「グラフ化したメトリクス」タブで、LogEventsWithFindings の行の「アクション」列にあるベルのアイコン(「アラームを作成」)をクリックします。「メトリクスと条件の指定」が、名前空間・ディメンションの入った状態で開きます。以下を設定します。
- 統計:
合計 - 期間:
1 分 - 条件: しきい値の種類「静的」、「LogEventsWithFindings が」「以上」(既定では選ばれていません)、「…よりも」に
1


「次へ」をクリックし、「通知」で以下を設定します。
- アラーム状態トリガー: 「アラーム状態」
- SNS トピックの選択: 「既存の SNS トピックを選択」の入力欄に
soa-sensitive-data-alertsと入力し、候補から選択
「次へ」をクリックし、アラーム名に soa-sensitive-data-alarm と入力します。「次へ」をクリックし、確認画面で「アラームの作成」をクリックします。
手順 6: アラーム状態になることを確かめる
CloudShell に戻り、もう一度機密データを含むログを送ります。
now=$(date +%s%3N)
aws logs put-log-events --log-group-name "$LG" --log-stream-name test-01 --log-events \
"[{\"timestamp\":$now,\"message\":\"reservation updated patient=PT-20261022 contact=banana.jiro@example.com\"}]"CloudWatch のコンソールで左側ナビゲーションの「アラーム」→「すべてのアラーム」を選択します。数分待つと、soa-sensitive-data-alarm の状態が「アラーム状態」に変わります。アラームを選択して「履歴」タブを開くと、状態の変化と、SNS トピックへのアクションが実行されたことを確認できます。この実践ではトピックにサブスクリプションを付けていないため、アラーム一覧の「アクション」列に警告が表示されますが、動作には影響しません。実際の運用では、トピックに通知先(メールやチャットなど)をサブスクライブしておきます。


まとめ
| やりたいこと | 使う設定・サービス |
|---|---|
| ログの機密データを取り込み時に検出・マスクする | CloudWatch Logs のデータ保護ポリシー |
| 一般的な機密データ(メールアドレス、クレジットカード番号など)を検出する | マネージドデータ識別子 |
| 組織固有の形式(患者番号、社員番号など)を検出する | カスタムデータ識別子(正規表現) |
| 機密データがログに出たら通知する | LogEventsWithFindings メトリクスのアラーム → SNS |
| マスクされた元の値を見る | logs:Unmask の権限(「マスク解除」や unmask(@message)) |
| S3 に保存されたデータの機密データを見つける | Amazon Macie |
- データ保護ポリシーはロググループ単位かアカウント全体に設定し、取り込み時に検出・マスクする。設定前のログはマスクされない
- マスクは Logs Insights やメトリクスフィルター、サブスクリプションフィルターなど、すべての出力先に効く
LogEventsWithFindingsはAWS/Logs名前空間の無料のメトリクスで、アラームの元にできる- Macie は S3 のデータが対象、GuardDuty は脅威の検出で、どちらも CloudWatch Logs のログの機密データ検出には使わない



「CloudWatch Logs のログに個人情報や医療情報が出たら知らせたい」と聞いたら、データ保護ポリシーと LogEventsWithFindings のアラームでござる。S3 担当の Macie や、侵入者担当の GuardDuty と取り違えぬよう、見張る場所で覚えるでござるよ。
参照先
- 機密性の高いログデータをマスキングで保護する – Amazon CloudWatch Logs
- 1 つのロググループ用のデータ保護ポリシーを作成する – Amazon CloudWatch Logs
- データをマスクせずに表示する – Amazon CloudWatch Logs
- 保護対象保健情報 (PHI) – Amazon CloudWatch Logs
- 個人を特定できる情報 (PII) – Amazon CloudWatch Logs
- カスタムデータ識別子 – Amazon CloudWatch Logs
- CloudWatch メトリクスによるモニタリング – Amazon CloudWatch Logs
- Amazon CloudWatch でのアラームの使用 – Amazon CloudWatch
- Amazon Macie とは – Amazon Macie
- Amazon GuardDuty とは – Amazon GuardDuty
















