

# AWS のサービス ログをクエリする
<a name="querying-aws-service-logs"></a>

このセクションでは、Amazon Athena を使用して一般的なデータセット (AWS CloudTrail ログ、Amazon CloudFront ログ、Classic Load Balancer ログ、Application Load Balancer ログ、Amazon VPC フローログ、Network Load Balancer ログなど) をクエリするための手順をいくつか紹介します。

このセクションのタスクでは Athena コンソールを使用しますが、[Athena JDBC ドライバー](connect-with-jdbc.md)、[AWS CLI](https://docs.aws.amazon.com/cli/latest/reference/athena/)、または [Amazon Athena API リファレンス](https://docs.aws.amazon.com/athena/latest/APIReference/)などの他のツールを使うこともできます。

Athena での AWS CloudFormation を使用した AWS のサービス のログのテーブル、パーティション、およびクエリ例の自動作成については、AWS Big Dataブログの「[Amazon Athena でのAWS のサービス ログのテーブル作成とクエリの自動化](https://aws.amazon.com/blogs/big-data/automating-aws-service-logs-table-creation-and-querying-them-with-amazon-athena/)」を参照してください。AWS Glue 用の Python ライブラリを使用して、AWS のサービス のログを処理し、Athena でクエリを実行するための共通のフレームワークを作成する方法については、「[Amazon Athena を使用して AWS のサービス のログに対するクエリを簡単に実行する](https://aws.amazon.com/blogs/big-data/easily-query-aws-service-logs-using-amazon-athena/)」を参照してください。

このセクションのトピックでは、Athena と、クエリするデータがが格納される Amazon S3 バケットにアクセスするための適切なアクセス許可が設定済みであることを前提としています。詳細については、[設定、管理、プログラムによるアクセス](setting-up.md)および[はじめに](getting-started.md)を参照してください。

**Topics**
+ [Application Load Balancer](application-load-balancer-logs.md)
+ [エラスティックロードバランシング](elasticloadbalancer-classic-logs.md)
+ [CloudFront](cloudfront-logs.md)
+ [CloudTrail](cloudtrail-logs.md)
+ [Amazon EMR](emr-logs.md)
+ [Global Accelerator](querying-global-accelerator-flow-logs.md)
+ [GuardDuty](querying-guardduty.md)
+ [Network Firewall](querying-network-firewall-logs.md)
+ [Network Load Balancer](networkloadbalancer-classic-logs.md)
+ [Route 53](querying-r53-resolver-logs.md)
+ [Amazon SES](querying-ses-logs.md)
+ [Amazon VPC](vpc-flow-logs.md)
+ [AWS WAF](waf-logs.md)

# Application Load Balancer ログをクエリする
<a name="application-load-balancer-logs"></a>

Application Load Balancer は、Elastic Load Balancing の負荷分散オプションであり、コンテナを使用したマイクロサービスのデプロイメントでのトラフィックの分散を可能にします。Application Load Balancer のログをクエリすることで、トラフィックの送信元、レイテンシー、Elastic Load Balancing インスタンスとバックエンドアプリケーションとの間で転送されるバイト数を確認できます。詳細については、「*Application Load Balancer ユーザーガイド*」の「[Access logs for your Application Load Balancer](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-access-logs.html)」と「[Connection logs for your Application Load Balancer](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-connection-logs.html)」を参照してください。

## 前提条件
<a name="application-load-balancer-logs-prerequisites"></a>
+ [アクセスログ](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-access-logs.html)または[接続ログ](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-connection-logs.html) を有効にして、Application Load Balancer ログを Amazon S3 バケットに保存できるようにします。
+ Athena 用に作成するテーブルを保存するデータベース。データベースを作成するには、Athena または AWS Glue コンソールを使用します。詳細については、本ガイドの「[Athena でデータベースを作成する](creating-databases.md)」または「*AWS Glue デベロッパーガイド*」の「[AWS Glue コンソールでのデータベースの操作](https://docs.aws.amazon.com/glue/latest/dg/console-databases.html)」を参照してください。

**Topics**
+ [前提条件](#application-load-balancer-logs-prerequisites)
+ [ALB アクセスログ用のテーブルを作成する](create-alb-access-logs-table.md)
+ [パーティション射影を使用して Athena で ALB アクセスログ用テーブルを作成する](create-alb-access-logs-table-partition-projection.md)
+ [ALB アクセスログのクエリ例](query-alb-access-logs-examples.md)
+ [ALB 接続ログ用テーブルを作成する](create-alb-connection-logs-table.md)
+ [パーティション射影を使用して Athena で ALB 接続ログ用テーブルを作成する](create-alb-connection-logs-table-partition-projection.md)
+ [ALB 接続ログのクエリ例](query-alb-connection-logs-examples.md)
+ [その他のリソース](application-load-balancer-logs-additional-resources.md)

# ALB アクセスログ用のテーブルを作成する
<a name="create-alb-access-logs-table"></a>

1. 次の `CREATE TABLE` ステートメントをコピーして Athena コンソールのクエリエディタに貼り付け、必要に応じて独自のログエントリ要件に合わせて変更します。Athena コンソールを開始する方法については、「[はじめに](getting-started.md)」を参照してください。`LOCATION` 句内のパスを Amazon S3 アクセスログフォルダの場所に置き換えます。アクセスログファイルの場所に関する詳細については、「*Application Load Balancer ユーザーガイド*」の「[アクセスログファイル](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-access-logs.html#access-log-file-format)」を参照してください。

   各フィールドについては、「*Application Load Balancer のユーザーガイド*」の「[アクセスログのエントリ](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-access-logs.html#access-log-entry-format)」を参照してください。
**注記**  
次の `CREATE TABLE` ステートメントには、最近追加された `classification` 列、`classification_reason` 列、および `conn_trace_id` 列 (「traceability ID」または「TID」) が含まれています。これらのエントリを含まないApplication Load Balancer アクセスログのテーブルを作成するには、`CREATE TABLE` ステートメントから対応する列を削除し、それに応じて正規表現を変更します。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS alb_access_logs (
               type string,
               time string,
               elb string,
               client_ip string,
               client_port int,
               target_ip string,
               target_port int,
               request_processing_time double,
               target_processing_time double,
               response_processing_time double,
               elb_status_code int,
               target_status_code string,
               received_bytes bigint,
               sent_bytes bigint,
               request_verb string,
               request_url string,
               request_proto string,
               user_agent string,
               ssl_cipher string,
               ssl_protocol string,
               target_group_arn string,
               trace_id string,
               domain_name string,
               chosen_cert_arn string,
               matched_rule_priority string,
               request_creation_time string,
               actions_executed string,
               redirect_url string,
               lambda_error_reason string,
               target_port_list string,
               target_status_code_list string,
               classification string,
               classification_reason string,
               conn_trace_id string
               )
               ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.RegexSerDe'
               WITH SERDEPROPERTIES (
               'serialization.format' = '1',
               'input.regex' = 
           '([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*):([0-9]*) ([^ ]*)[:-]([0-9]*) ([-.0-9]*) ([-.0-9]*) ([-.0-9]*) (|[-0-9]*) (-|[-0-9]*) ([-0-9]*) ([-0-9]*) \"([^ ]*) (.*) (- |[^ ]*)\" \"([^\"]*)\" ([A-Z0-9-_]+) ([A-Za-z0-9.-]*) ([^ ]*) \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\" ([-.0-9]*) ([^ ]*) \"([^\"]*)\" \"([^\"]*)\" \"([^ ]*)\" \"([^\\s]+?)\" \"([^\\s]+)\" \"([^ ]*)\" \"([^ ]*)\" ?([^ ]*)? ?( .*)?'
               )
               LOCATION 's3://amzn-s3-demo-bucket/access-log-folder-path/'
   ```
**注記**  
新しい ALB ログフィールドが追加された場合に備えて、将来のログエントリを処理できるように、`input.regex` パラメータの末尾に *`?( .*)?`* パターンを必ず残しておくことをお勧めします。

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `alb_access_logs` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

# パーティション射影を使用して Athena で ALB アクセスログ用テーブルを作成する
<a name="create-alb-access-logs-table-partition-projection"></a>

ALB アクセスログにはパーティションスキームを事前に指定できる既知の構造があるため、Athena のパーティション射影機能を使用することで、クエリの実行時間を短縮し、パーティション管理を自動化することが可能です。新しいデータが追加されると、パーティション射影は新しいパーティションを自動で追加します。このため、`ALTER TABLE ADD PARTITION` を使用してパーティションを手動で追加する必要がなくなります。

以下の `CREATE TABLE` ステートメント例は、単一の AWS リージョンの指定された日付から現在までの ALB アクセスログに、パーティション射影を自動的に使用します。ステートメントは、前のセクションの例に基づいていますが、`PARTITIONED BY` 句および `TBLPROPERTIES` 句を追加して、パーティション射影を有効にしています。`LOCATION` 句および `storage.location.template` 句では、プレースホルダーを ALB アクセスログの Amazon S3 バケットの場所を特定する値に置き換えます。アクセスログファイルの場所に関する詳細については、「*Application Load Balancer ユーザーガイド*」の「[アクセスログファイル](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-access-logs.html#access-log-file-format)」を参照してください。`projection.day.range` では、*2022*/*01*/*01* を使用を開始する日に置き換えます。クエリが正常に実行されると、テーブルをクエリできます。パーティションをロードするのに、`ALTER TABLE ADD PARTITION` を実行する必要はありません。ログファイルの各フィールドに関する詳細については、「[アクセスログのエントリ](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-access-logs.html#access-log-entry-format)」を参照してください。

```
CREATE EXTERNAL TABLE IF NOT EXISTS alb_access_logs (
            type string,
            time string,
            elb string,
            client_ip string,
            client_port int,
            target_ip string,
            target_port int,
            request_processing_time double,
            target_processing_time double,
            response_processing_time double,
            elb_status_code int,
            target_status_code string,
            received_bytes bigint,
            sent_bytes bigint,
            request_verb string,
            request_url string,
            request_proto string,
            user_agent string,
            ssl_cipher string,
            ssl_protocol string,
            target_group_arn string,
            trace_id string,
            domain_name string,
            chosen_cert_arn string,
            matched_rule_priority string,
            request_creation_time string,
            actions_executed string,
            redirect_url string,
            lambda_error_reason string,
            target_port_list string,
            target_status_code_list string,
            classification string,
            classification_reason string,
            conn_trace_id string
            )
            PARTITIONED BY
            (
             day STRING
            )
            ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.RegexSerDe'
            WITH SERDEPROPERTIES (
            'serialization.format' = '1',
            'input.regex' = 
        '([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*):([0-9]*) ([^ ]*)[:-]([0-9]*) ([-.0-9]*) ([-.0-9]*) ([-.0-9]*) (|[-0-9]*) (-|[-0-9]*) ([-0-9]*) ([-0-9]*) \"([^ ]*) (.*) (- |[^ ]*)\" \"([^\"]*)\" ([A-Z0-9-_]+) ([A-Za-z0-9.-]*) ([^ ]*) \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\" ([-.0-9]*) ([^ ]*) \"([^\"]*)\" \"([^\"]*)\" \"([^ ]*)\" \"([^\\s]+?)\" \"([^\\s]+)\" \"([^ ]*)\" \"([^ ]*)\" ?([^ ]*)? ?( .*)?'
            )
            LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/<ACCOUNT-NUMBER>/elasticloadbalancing/<REGION>/'
            TBLPROPERTIES
            (
             "projection.enabled" = "true",
             "projection.day.type" = "date",
             "projection.day.range" = "2022/01/01,NOW",
             "projection.day.format" = "yyyy/MM/dd",
             "projection.day.interval" = "1",
             "projection.day.interval.unit" = "DAYS",
             "storage.location.template" = "s3://amzn-s3-demo-bucket/AWSLogs/<ACCOUNT-NUMBER>/elasticloadbalancing/<REGION>/${day}"
            )
```

パーティション射影の詳細については、「[Amazon Athena でパーティション射影を使用する](partition-projection.md)」を参照してください。

**注記**  
新しい ALB ログフィールドが追加された場合に備えて、将来のログエントリを処理できるように、`input.regex` パラメータの末尾に *?( .\$1)?* パターンを必ず残しておくことをお勧めします。

# ALB アクセスログのクエリ例
<a name="query-alb-access-logs-examples"></a>

次のクエリでは、ロードバランサーで受信し、クライアント IP アドレス別にグループ分けした HTTP GET リクエストの数をカウントします。

```
SELECT COUNT(request_verb) AS
 count,
 request_verb,
 client_ip
FROM alb_access_logs
GROUP BY request_verb, client_ip
LIMIT 100;
```

別のクエリでは、Safari ブラウザのユーザーがアクセスした URL を表示します。

```
SELECT request_url
FROM alb_access_logs
WHERE user_agent LIKE '%Safari%'
LIMIT 10;
```

次のクエリでは、ELB ステータスコードの値が 500 以上であるレコードが表示されます。

```
SELECT * FROM alb_access_logs
WHERE elb_status_code >= 500
```

次の例は、`datetime` でログを解析する方法を示しています。

```
SELECT client_ip, sum(received_bytes) 
FROM alb_access_logs
WHERE parse_datetime(time,'yyyy-MM-dd''T''HH:mm:ss.SSSSSS''Z') 
     BETWEEN parse_datetime('2018-05-30-12:00:00','yyyy-MM-dd-HH:mm:ss') 
     AND parse_datetime('2018-05-31-00:00:00','yyyy-MM-dd-HH:mm:ss') 
GROUP BY client_ip;
```

次のクエリは、指定された日からのすべての ALB アクセスログに対してパーティション射影を使用するテーブルをクエリします。

```
SELECT * 
FROM alb_access_logs 
WHERE day = '2022/02/12'
```

# ALB 接続ログ用テーブルを作成する
<a name="create-alb-connection-logs-table"></a>

1. 次の `CREATE TABLE` サンプルステートメントをコピーして Athena コンソールのクエリエディタに貼り付け、必要に応じて独自のログエントリ要件に合わせて変更します。Athena コンソールを開始する方法については、「[はじめに](getting-started.md)」を参照してください。`LOCATION` 句内のパスを Amazon S3 接続ログフォルダの場所に置き換えます。接続ログファイルの場所に関する詳細については、「*Application Load Balancer ユーザーガイド*」の「[接続ログファイル](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-connection-logs.html#connection-log-file-format)」を参照してください。ログファイルの各フィールドに関する詳細については、「[接続ログエントリ](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-connection-logs.html#connection-log-entry-format)」を参照してください。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS alb_connection_logs (
            time string,
            client_ip string,
            client_port int,
            listener_port int,
            tls_protocol string,
            tls_cipher string,
            tls_handshake_latency double,
            leaf_client_cert_subject string,
            leaf_client_cert_validity string,
            leaf_client_cert_serial_number string,
            tls_verify_status string,
            conn_trace_id string
            ) 
            ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.RegexSerDe'
            WITH SERDEPROPERTIES (
            'serialization.format' = '1',
            'input.regex' =
             '([^ ]*) ([^ ]*) ([0-9]*) ([0-9]*) ([A-Za-z0-9.-]*) ([^ ]*) ([-.0-9]*) \"([^\"]*)\" ([^ ]*) ([^ ]*) ([^ ]*) ?([^ ]*)?( .*)?'
            )
            LOCATION 's3://amzn-s3-demo-bucket/connection-log-folder-path/'
   ```

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `alb_connection_logs` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

# パーティション射影を使用して Athena で ALB 接続ログ用テーブルを作成する
<a name="create-alb-connection-logs-table-partition-projection"></a>

ALB 接続ログにはパーティションスキームを事前に指定できる既知の構造があるため、Athena のパーティション射影機能を使用することで、クエリの実行時間を短縮し、パーティション管理を自動化することが可能です。新しいデータが追加されると、パーティション射影は新しいパーティションを自動で追加します。このため、`ALTER TABLE ADD PARTITION` を使用してパーティションを手動で追加する必要がなくなります。

以下の `CREATE TABLE` ステートメント例は、単一の AWS リージョンの指定された日付から現在までの ALB 接続ログに、パーティション射影を自動的に使用します。ステートメントは、前のセクションの例に基づいていますが、`PARTITIONED BY` 句および `TBLPROPERTIES` 句を追加して、パーティション射影を有効にしています。`LOCATION` 句および `storage.location.template` 句では、プレースホルダーを ALB 接続ログの Amazon S3 バケットの場所を特定する値に置き換えます。接続ログファイルの場所に関する詳細については、「Application Load Balancer ユーザーガイド」の「[接続ログファイル](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-connection-logs.html#connection-log-file-format)」を参照してください。`projection.day.range` では、*2023*/*01*/*01* を使用したい開始日に置き換えます。クエリが正常に実行されると、テーブルをクエリできます。パーティションをロードするのに、`ALTER TABLE ADD PARTITION` を実行する必要はありません。ログファイルの各フィールドに関する詳細については、「[接続ログエントリ](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-connection-logs.html#connection-log-entry-format)」を参照してください。

```
CREATE EXTERNAL TABLE IF NOT EXISTS alb_connection_logs (
         time string,
         client_ip string,
         client_port int,
         listener_port int,
         tls_protocol string,
         tls_cipher string,
         tls_handshake_latency double,
         leaf_client_cert_subject string,
         leaf_client_cert_validity string,
         leaf_client_cert_serial_number string,
         tls_verify_status string,
         conn_trace_id string
         )
            PARTITIONED BY
            (
             day STRING
            )
            ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.RegexSerDe'
            WITH SERDEPROPERTIES (
            'serialization.format' = '1',
            'input.regex' =
             '([^ ]*) ([^ ]*) ([0-9]*) ([0-9]*) ([A-Za-z0-9.-]*) ([^ ]*) ([-.0-9]*) \"([^\"]*)\" ([^ ]*) ([^ ]*) ([^ ]*) ?([^ ]*)?( .*)?'
            )
            LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/<ACCOUNT-NUMBER>/elasticloadbalancing/<REGION>/'
            TBLPROPERTIES
            (
             "projection.enabled" = "true",
             "projection.day.type" = "date",
             "projection.day.range" = "2023/01/01,NOW",
             "projection.day.format" = "yyyy/MM/dd",
             "projection.day.interval" = "1",
             "projection.day.interval.unit" = "DAYS",
             "storage.location.template" = "s3://amzn-s3-demo-bucket/AWSLogs/<ACCOUNT-NUMBER>/elasticloadbalancing/<REGION>/${day}"
            )
```

パーティション射影の詳細については、「[Amazon Athena でパーティション射影を使用する](partition-projection.md)」を参照してください。

# ALB 接続ログのクエリ例
<a name="query-alb-connection-logs-examples"></a>

以下のクエリは、`tls_verify_status` の値が `'Success'` ではなかったオカレンスの数をカウントし、クライアント IP アドレスごとにグループ化します。

```
SELECT DISTINCT client_ip, count() AS count FROM alb_connection_logs
WHERE tls_verify_status != 'Success'
GROUP BY client_ip
ORDER BY count() DESC;
```

以下のクエリは、指定された時間範囲内で `tls_handshake_latency` の値が 2 秒を超えたオカレンスを検索します。

```
SELECT * FROM alb_connection_logs
WHERE 
  (
    parse_datetime(time, 'yyyy-MM-dd''T''HH:mm:ss.SSSSSS''Z') 
    BETWEEN 
    parse_datetime('2024-01-01-00:00:00', 'yyyy-MM-dd-HH:mm:ss') 
    AND 
    parse_datetime('2024-03-20-00:00:00', 'yyyy-MM-dd-HH:mm:ss') 
  ) 
  AND 
    (tls_handshake_latency >= 2.0);
```

# その他のリソース
<a name="application-load-balancer-logs-additional-resources"></a>

ALB ログの使用に関する詳細については、次のリソースを参照してください。
+ 「*AWS ナレッジセンター*」の「[Amazon Athena で Application Load Balancer のアクセスログを分析する方法を教えてください](https://repost.aws/knowledge-center/athena-analyze-access-logs)」。
+ Elastic Load Balancing における HTTP ステータスコードについては、「*Application Load Balancer ユーザーガイド*」の「[Application Load Balancer のトラブルシューティング](https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-troubleshooting.html)」を参照してください。
+ 「*AWS Big Data Blog*」の「[Catalog and analyze Application Load Balancer logs more efficiently with AWS Glue custom classifiers and Amazon Athena](https://aws.amazon.com/blogs/big-data/catalog-and-analyze-application-load-balancer-logs-more-efficiently-with-aws-glue-custom-classifiers-and-amazon-athena/)」。

# Classic Load Balancer ログをクエリする
<a name="elasticloadbalancer-classic-logs"></a>

Classic Load Balancer ログを使用して、Elastic Load Balancing インスタンスおよびバックエンドアプリケーションとの間で送受信されるトラフィックパターンを分析して理解します。トラフィックの送信元、レイテンシー、および転送されたバイト数を確認できます。

Elastic Load Balancing ログを分析する前に、宛先の Amazon S3 バケットでの保存用にそれらを設定します。詳細については、「[Classic Load Balancer のアクセスログの有効化](https://docs.aws.amazon.com/elasticloadbalancing/latest/classic/enable-access-logs.html)」を参照してください。

**Elastic Load Balancing ログのテーブルを作成する**

1. 以下の DDL ステートメントをコピーして Athena コンソール内に貼り付けます。Elastic Load Balancing ログレコードの[構文](https://docs.aws.amazon.com/elasticloadbalancing/latest/classic/access-log-collection.html#access-log-entry-format)をチェックします。以下のクエリを更新して、最新バージョンのレコードのための列と Regex 構文を含めることが必要になる場合があります。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS elb_logs (
    
    timestamp string,
    elb_name string,
    request_ip string,
    request_port int,
    backend_ip string,
    backend_port int,
    request_processing_time double,
    backend_processing_time double,
    client_response_time double,
    elb_response_code string,
    backend_response_code string,
    received_bytes bigint,
    sent_bytes bigint,
    request_verb string,
    url string,
    protocol string,
    user_agent string,
    ssl_cipher string,
    ssl_protocol string
   )
   ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.RegexSerDe'
   WITH SERDEPROPERTIES (
    'serialization.format' = '1',
    'input.regex' = '([^ ]*) ([^ ]*) ([^ ]*):([0-9]*) ([^ ]*)[:-]([0-9]*) ([-.0-9]*) ([-.0-9]*) ([-.0-9]*) (|[-0-9]*) (-|[-0-9]*) ([-0-9]*) ([-0-9]*) \\\"([^ ]*) ([^ ]*) (- |[^ ]*)\\\" (\"[^\"]*\") ([A-Z0-9-]+) ([A-Za-z0-9.-]*)$'
   )
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/AWS_account_ID/elasticloadbalancing/';
   ```

1. `LOCATION` Amazon S3 バケットを変更して、Elastic Load Balancing ログの宛先を指定します。

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `elb_logs` テーブルを登録して、その中のデータをクエリ向けに準備します。詳細については、「[クエリの例](#query-elb-classic-example)」を参照してください。

## クエリの例
<a name="query-elb-classic-example"></a>

以下の例のようなクエリを使用します。この例では、`4XX` または `5XX` エラーレスポンスコードを返したバックエンドアプリケーションサーバーを示しています。`LIMIT` 演算子を使用すると、一度にクエリするログの数を制限できます。

```
SELECT
 timestamp,
 elb_name,
 backend_ip,
 backend_response_code
FROM elb_logs
WHERE backend_response_code LIKE '4%' OR
      backend_response_code LIKE '5%'
LIMIT 100;
```

後続のクエリを使用して、バックエンド IP アドレスと Elastic Load Balancing インスタンス名でグループ分けされたすべてのトランザクションの応答時間を合算します。

```
SELECT sum(backend_processing_time) AS
 total_ms,
 elb_name,
 backend_ip
FROM elb_logs WHERE backend_ip <> ''
GROUP BY backend_ip, elb_name
LIMIT 100;
```

詳細については、「[Athena を使用した S3 のデータの分析](https://aws.amazon.com/blogs/big-data/analyzing-data-in-s3-using-amazon-athena/)」を参照してください。

# Amazon CloudFront ログをクエリする
<a name="cloudfront-logs"></a>

Amazon CloudFront CDN を設定して、ウェブディストリビューションのアクセスログを Amazon Simple Storage Service にエクスポートできます。これらのログを使用して、CloudFront によって提供されるウェブプロパティ全体でのユーザーのサーフィンパターンを調べます。

ログのクエリを開始する前に、使用する CloudFront ディストリビューションでウェブディストリビューションのアクセスログを有効にします。詳細については、「Amazon CloudFront デベロッパーガイド」の「[アクセスログ](https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/AccessLogs.html)」を参照してください。ログを保存する Amazon S3 バケットをメモしておきます。

**Topics**
+ [CloudFront 標準ログ用テーブルを作成する (レガシー)](create-cloudfront-table-standard-logs.md)
+ [Athena で JSON での手動パーティショニングを使用して CloudFront ログ用のテーブルを作成する](create-cloudfront-table-manual-json.md)
+ [Athena で Parquet での手動パーティショニングを使用して CloudFront ログ用のテーブルを作成する](create-cloudfront-table-manual-parquet.md)
+ [Athena で JSON でのパーティショニング射影を使用して CloudFront ログ用のテーブルを作成する](create-cloudfront-table-partition-json.md)
+ [Athena で Parquet でのパーティション射影を使用して CloudFront ログ用のテーブルを作成する](create-cloudfront-table-partition-parquet.md)
+ [CloudFront リアルタイムログ用テーブルを作成する](create-cloudfront-table-real-time-logs.md)
+ [その他のリソース](cloudfront-logs-additional-resources.md)

# CloudFront 標準ログ用テーブルを作成する (レガシー)
<a name="create-cloudfront-table-standard-logs"></a>

**注記**  
次の手順は、CloudFront にあるウェブディストリビューションのアクセスログで機能します。RTMP ディストリビューションのストリーミングログには該当しません。

**CloudFront 標準ログファイルフィールド用のテーブルを作成する**

1. 次の DDL ステートメントの例をコピーして Athena コンソールのクエリエディタに貼り付けます。例のステートメントでは、「Amazon CloudFront デベロッパーガイド」の「[標準ログファイルフィールド](https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/AccessLogs.html#BasicDistributionFileFormat)」セクションに記載されているログファイルフィールドを使用しています。`LOCATION` をログを保存する Simple Storage Service (Amazon S3) バケットに変更します。クエリエディタの使用については、「[はじめに](getting-started.md)」を参照してください。

   このクエリは、フィールドがタブ文字で区切られることを示すために `ROW FORMAT DELIMITED` と `FIELDS TERMINATED BY '\t'` を指定します。`ROW FORMAT DELIMITED` には、Athena がデフォルトで [LazySimpleSerDe](lazy-simple-serde.md) を使用します。列 `date` は Athena の予約語であるため、バックティック (`) を使用してエスケープされています。詳細については、「[クエリで予約キーワードをエスケープする](reserved-words.md)」を参照してください。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS cloudfront_standard_logs (
     `date` DATE,
     time STRING,
     x_edge_location STRING,
     sc_bytes BIGINT,
     c_ip STRING,
     cs_method STRING,
     cs_host STRING,
     cs_uri_stem STRING,
     sc_status INT,
     cs_referrer STRING,
     cs_user_agent STRING,
     cs_uri_query STRING,
     cs_cookie STRING,
     x_edge_result_type STRING,
     x_edge_request_id STRING,
     x_host_header STRING,
     cs_protocol STRING,
     cs_bytes BIGINT,
     time_taken FLOAT,
     x_forwarded_for STRING,
     ssl_protocol STRING,
     ssl_cipher STRING,
     x_edge_response_result_type STRING,
     cs_protocol_version STRING,
     fle_status STRING,
     fle_encrypted_fields INT,
     c_port INT,
     time_to_first_byte FLOAT,
     x_edge_detailed_result_type STRING,
     sc_content_type STRING,
     sc_content_len BIGINT,
     sc_range_start BIGINT,
     sc_range_end BIGINT
   )
   ROW FORMAT DELIMITED 
   FIELDS TERMINATED BY '\t'
   LOCATION 's3://amzn-s3-demo-bucket/'
   TBLPROPERTIES ( 'skip.header.line.count'='2' )
   ```

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `cloudfront_standard_logs` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

## クエリの例
<a name="query-examples-cloudfront-logs"></a>

以下のクエリは、2018 年 6 月 9 日から 6 月 11 日の間に CloudFront によって提供されたバイト数をCに で処理されたバイト数を集計します。date 列名は予約語であるため、二重引用符で囲みます。

```
SELECT SUM(bytes) AS total_bytes
FROM cloudfront_standard_logs
WHERE "date" BETWEEN DATE '2018-06-09' AND DATE '2018-06-11'
LIMIT 100;
```

クエリ結果から重複する行 (重複する空の行など) を削除するには、次の例のように `SELECT DISTINCT` ステートメントを使用します。

```
SELECT DISTINCT * 
FROM cloudfront_standard_logs 
LIMIT 10;
```

# Athena で JSON での手動パーティショニングを使用して CloudFront ログ用のテーブルを作成する
<a name="create-cloudfront-table-manual-json"></a>

**JSON 形式を使用して CloudFront 標準ログファイルフィールド用のテーブルを作成するには**

1. 次の DDL ステートメントの例をコピーして Athena コンソールのクエリエディタに貼り付けます。例のステートメントでは、「Amazon CloudFront デベロッパーガイド」の「[標準ログファイルフィールド](https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/AccessLogs.html#BasicDistributionFileFormat)」セクションに記載されているログファイルフィールドを使用しています。`LOCATION` をログを保存する Simple Storage Service (Amazon S3) バケットに変更します。

   このクエリでは、Athena で JSON フィールドを正しく読み取るために OpenX JSON SerDe を次の SerDe プロパティとともに使用します。

   ```
   CREATE EXTERNAL TABLE `cf_logs_manual_partition_json`(
     `date` string , 
     `time` string , 
     `x-edge-location` string , 
     `sc-bytes` string , 
     `c-ip` string , 
     `cs-method` string , 
     `cs(host)` string , 
     `cs-uri-stem` string , 
     `sc-status` string , 
     `cs(referer)` string , 
     `cs(user-agent)` string , 
     `cs-uri-query` string , 
     `cs(cookie)` string , 
     `x-edge-result-type` string , 
     `x-edge-request-id` string , 
     `x-host-header` string , 
     `cs-protocol` string , 
     `cs-bytes` string , 
     `time-taken` string , 
     `x-forwarded-for` string , 
     `ssl-protocol` string , 
     `ssl-cipher` string , 
     `x-edge-response-result-type` string , 
     `cs-protocol-version` string , 
     `fle-status` string , 
     `fle-encrypted-fields` string , 
     `c-port` string , 
     `time-to-first-byte` string , 
     `x-edge-detailed-result-type` string , 
     `sc-content-type` string , 
     `sc-content-len` string , 
     `sc-range-start` string , 
     `sc-range-end` string )
   ROW FORMAT SERDE 
     'org.openx.data.jsonserde.JsonSerDe' 
   WITH SERDEPROPERTIES ( 
     'paths'='c-ip,c-port,cs(Cookie),cs(Host),cs(Referer),cs(User-Agent),cs-bytes,cs-method,cs-protocol,cs-protocol-version,cs-uri-query,cs-uri-stem,date,fle-encrypted-fields,fle-status,sc-bytes,sc-content-len,sc-content-type,sc-range-end,sc-range-start,sc-status,ssl-cipher,ssl-protocol,time,time-taken,time-to-first-byte,x-edge-detailed-result-type,x-edge-location,x-edge-request-id,x-edge-response-result-type,x-edge-result-type,x-forwarded-for,x-host-header') 
   STORED AS INPUTFORMAT 
     'org.apache.hadoop.mapred.TextInputFormat' 
   OUTPUTFORMAT 
     'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
   LOCATION
     's3://amzn-s3-demo-bucket/'
   ```

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `cf_logs_manual_partition_json` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

## クエリの例
<a name="query-examples-cloudfront-logs-manual-json"></a>

以下のクエリは、2025 年 1 月 15 日に CloudFront によって提供されたバイト数を集計します。

```
SELECT sum(cast("sc-bytes" as BIGINT)) as sc
FROM cf_logs_manual_partition_json
WHERE "date"='2025-01-15'
```

クエリ結果から重複する行 (重複する空の行など) を削除するには、次の例のように `SELECT DISTINCT` ステートメントを使用します。

```
SELECT DISTINCT * FROM cf_logs_manual_partition_json
```

# Athena で Parquet での手動パーティショニングを使用して CloudFront ログ用のテーブルを作成する
<a name="create-cloudfront-table-manual-parquet"></a>

**Parquet 形式を使用して CloudFront 標準ログファイルフィールド用のテーブルを作成するには**

1. 次の DDL ステートメントの例をコピーして Athena コンソールのクエリエディタに貼り付けます。例のステートメントでは、「Amazon CloudFront デベロッパーガイド」の「[標準ログファイルフィールド](https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/AccessLogs.html#BasicDistributionFileFormat)」セクションに記載されているログファイルフィールドを使用しています。

   このクエリでは、Athena で Parquet フィールドを正しく読み取るために ParquetHiveSerDe を次の SerDe プロパティとともに使用します。

   ```
   CREATE EXTERNAL TABLE `cf_logs_manual_partition_parquet`(
     `date` string, 
     `time` string, 
     `x_edge_location` string, 
     `sc_bytes` string, 
     `c_ip` string, 
     `cs_method` string, 
     `cs_host` string, 
     `cs_uri_stem` string, 
     `sc_status` string, 
     `cs_referer` string, 
     `cs_user_agent` string, 
     `cs_uri_query` string, 
     `cs_cookie` string, 
     `x_edge_result_type` string, 
     `x_edge_request_id` string, 
     `x_host_header` string, 
     `cs_protocol` string, 
     `cs_bytes` string, 
     `time_taken` string, 
     `x_forwarded_for` string, 
     `ssl_protocol` string, 
     `ssl_cipher` string, 
     `x_edge_response_result_type` string, 
     `cs_protocol_version` string, 
     `fle_status` string, 
     `fle_encrypted_fields` string, 
     `c_port` string, 
     `time_to_first_byte` string, 
     `x_edge_detailed_result_type` string, 
     `sc_content_type` string, 
     `sc_content_len` string, 
     `sc_range_start` string, 
     `sc_range_end` string)
   ROW FORMAT SERDE 
     'org.apache.hadoop.hive.ql.io.parquet.serde.ParquetHiveSerDe' 
   STORED AS INPUTFORMAT 
     'org.apache.hadoop.hive.ql.io.parquet.MapredParquetInputFormat' 
   OUTPUTFORMAT 
     'org.apache.hadoop.hive.ql.io.parquet.MapredParquetOutputFormat'
   LOCATION
     's3://amzn-s3-demo-bucket/'
   ```

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `cf_logs_manual_partition_parquet` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

## クエリの例
<a name="query-examples-cloudfront-logs-manual-parquet"></a>

以下のクエリは、2025 年 1 月 19 日に CloudFront によって提供されたバイト数を集計します。

```
SELECT sum(cast("sc_bytes" as BIGINT)) as sc
FROM cf_logs_manual_partition_parquet
WHERE "date"='2025-01-19'
```

クエリ結果から重複する行 (重複する空の行など) を削除するには、次の例のように `SELECT DISTINCT` ステートメントを使用します。

```
SELECT DISTINCT * FROM cf_logs_manual_partition_parquet
```

# Athena で JSON でのパーティショニング射影を使用して CloudFront ログ用のテーブルを作成する
<a name="create-cloudfront-table-partition-json"></a>

Athena のパーティション射影機能を使用すると、クエリランタイムを短縮し、パーティション管理を自動化できます。新しいデータが追加されると、パーティション射影は新しいパーティションを自動で追加します。このため、`ALTER TABLE ADD PARTITION` を使用してパーティションを手動で追加する必要がなくなります。

次の CREATE TABLE ステートメント例は、指定した CloudFront 配信から現在までの単一の AWS リージョンの CloudTrail ログでパーティション射影を自動的に使用します。クエリが正常に実行されると、テーブルをクエリできます。

```
CREATE EXTERNAL TABLE `cloudfront_logs_pp`(
  `date` string, 
  `time` string, 
  `x-edge-location` string, 
  `sc-bytes` string, 
  `c-ip` string, 
  `cs-method` string, 
  `cs(host)` string, 
  `cs-uri-stem` string, 
  `sc-status` string, 
  `cs(referer)` string, 
  `cs(user-agent)` string, 
  `cs-uri-query` string, 
  `cs(cookie)` string, 
  `x-edge-result-type` string, 
  `x-edge-request-id` string, 
  `x-host-header` string, 
  `cs-protocol` string, 
  `cs-bytes` string, 
  `time-taken` string, 
  `x-forwarded-for` string, 
  `ssl-protocol` string, 
  `ssl-cipher` string, 
  `x-edge-response-result-type` string, 
  `cs-protocol-version` string, 
  `fle-status` string, 
  `fle-encrypted-fields` string, 
  `c-port` string, 
  `time-to-first-byte` string, 
  `x-edge-detailed-result-type` string, 
  `sc-content-type` string, 
  `sc-content-len` string, 
  `sc-range-start` string, 
  `sc-range-end` string)
  PARTITIONED BY(
         distributionid string,
         year int,
         month int,
         day int,
         hour int )
ROW FORMAT SERDE 
  'org.openx.data.jsonserde.JsonSerDe'
WITH SERDEPROPERTIES ( 
  'paths'='c-ip,c-port,cs(Cookie),cs(Host),cs(Referer),cs(User-Agent),cs-bytes,cs-method,cs-protocol,cs-protocol-version,cs-uri-query,cs-uri-stem,date,fle-encrypted-fields,fle-status,sc-bytes,sc-content-len,sc-content-type,sc-range-end,sc-range-start,sc-status,ssl-cipher,ssl-protocol,time,time-taken,time-to-first-byte,x-edge-detailed-result-type,x-edge-location,x-edge-request-id,x-edge-response-result-type,x-edge-result-type,x-forwarded-for,x-host-header') 
STORED AS INPUTFORMAT 
  'org.apache.hadoop.mapred.TextInputFormat' 
OUTPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION
  's3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_ID/CloudFront/'
TBLPROPERTIES (
  'projection.distributionid.type'='enum',
  'projection.distributionid.values'='E2Oxxxxxxxxxxx',
  'projection.day.range'='01,31', 
  'projection.day.type'='integer', 
  'projection.day.digits'='2', 
  'projection.enabled'='true', 
  'projection.month.range'='01,12', 
  'projection.month.type'='integer', 
  'projection.month.digits'='2', 
  'projection.year.range'='2025,2026', 
  'projection.year.type'='integer', 
  'projection.hour.range'='00,23',
  'projection.hour.type'='integer',
  'projection.hour.digits'='2',
  'storage.location.template'='s3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_ID/CloudFront/${distributionid}/${year}/${month}/${day}/${hour}/')
```

前の例で使用したプロパティに関する考慮事項を次に示します。
+ **テーブル名** – テーブル名 *`cloudfront_logs_pp`* は置き換えることができます。任意の名前に変更できます。
+ **場所** – Amazon S3 バケットを指すように `s3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_ID/` を変更します。
+ **配信 ID** – `projection.distributionid.values` では、カンマで区切って複数の配信 ID を指定できます。例えば、*<distributionID1>*, *<distributionID2>* のように指定します。
+ **年の範囲** – `projection.year.range` でデータに基づいて年の範囲を定義できます。例えば、**2025 や **2026 などの任意の期間に調整できます。
**注記**  
将来の日付 (例: 2025-2040) など、空のパーティションを含めると、クエリのパフォーマンスに影響が生じる可能性があります。ただし、パーティション射影は将来の日付を効果的に処理するように設計されています。最適なパフォーマンスを維持するには、パーティションを慎重に管理し、可能な場合は空のパーティションの過度な使用を避けてください。
+ **保存場所テンプレート** – 次の CloudFront パーティション構造と S3 パスに基づいて `storage.location.template` を正しく更新する必要があります。  
****    
[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/ja_jp/athena/latest/ug/create-cloudfront-table-partition-json.html)

  CloudFront パーティション構造と S3 構造が必要なパターンに一致することを確認したら、`storage.location.template` を次のように更新します。

  ```
  'storage.location.template'='s3://amzn-s3-demo-bucket/AWSLogs/account_id/CloudFront/${distributionid}/folder2/${year}/${month}/${day}/${hour}/folder3/'
  ```
**注記**  
データの正しい保存と取得を保証するには、`storage.location.template` を適切に設定することが重要です。

# Athena で Parquet でのパーティション射影を使用して CloudFront ログ用のテーブルを作成する
<a name="create-cloudfront-table-partition-parquet"></a>

次の CREATE TABLE ステートメント例は、指定した CloudFront 配信から現在までの単一の AWS リージョンの Parquet の CloudTrail ログでパーティション射影を自動的に使用します。クエリが正常に実行されると、テーブルをクエリできます。

```
CREATE EXTERNAL TABLE `cloudfront_logs_parquet_pp`(
`date` string, 
`time` string, 
`x_edge_location` string, 
`sc_bytes` string, 
`c_ip` string, 
`cs_method` string, 
`cs_host` string, 
`cs_uri_stem` string, 
`sc_status` string, 
`cs_referer` string, 
`cs_user_agent` string, 
`cs_uri_query` string, 
`cs_cookie` string, 
`x_edge_result_type` string, 
`x_edge_request_id` string, 
`x_host_header` string, 
`cs_protocol` string, 
`cs_bytes` string, 
`time_taken` string, 
`x_forwarded_for` string, 
`ssl_protocol` string, 
`ssl_cipher` string, 
`x_edge_response_result_type` string, 
`cs_protocol_version` string, 
`fle_status` string, 
`fle_encrypted_fields` string, 
`c_port` string, 
`time_to_first_byte` string, 
`x_edge_detailed_result_type` string, 
`sc_content_type` string, 
`sc_content_len` string, 
`sc_range_start` string, 
`sc_range_end` string)
PARTITIONED BY(
 distributionid string,
 year int,
 month int,
 day int,
 hour int )
ROW FORMAT SERDE 
'org.apache.hadoop.hive.ql.io.parquet.serde.ParquetHiveSerDe' 
STORED AS INPUTFORMAT 
'org.apache.hadoop.hive.ql.io.parquet.MapredParquetInputFormat' 
OUTPUTFORMAT 
'org.apache.hadoop.hive.ql.io.parquet.MapredParquetOutputFormat'
LOCATION
's3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_ID/CloudFront/'
TBLPROPERTIES (
'projection.distributionid.type'='enum',
'projection.distributionid.values'='E3OK0LPUNWWO3',
'projection.day.range'='01,31',
'projection.day.type'='integer',
'projection.day.digits'='2',
'projection.enabled'='true',
'projection.month.range'='01,12',
'projection.month.type'='integer',
'projection.month.digits'='2',
'projection.year.range'='2019,2025',
'projection.year.type'='integer',
'projection.hour.range'='01,12',
'projection.hour.type'='integer',
'projection.hour.digits'='2',
'storage.location.template'='s3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_ID/CloudFront/${distributionid}/${year}/${month}/${day}/${hour}/')
```

前の例で使用したプロパティに関する考慮事項を次に示します。
+ **テーブル名** – テーブル名 *`cloudfront_logs_pp`* は置き換えることができます。任意の名前に変更できます。
+ **場所** – Amazon S3 バケットを指すように `s3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_ID/` を変更します。
+ **配信 ID** – `projection.distributionid.values` では、カンマで区切って複数の配信 ID を指定できます。例えば、*<distributionID1>*, *<distributionID2>* のように指定します。
+ **年の範囲** – `projection.year.range` でデータに基づいて年の範囲を定義できます。例えば、**2025 や **2026 などの任意の期間に調整できます。
**注記**  
将来の日付 (例: 2025-2040) など、空のパーティションを含めると、クエリのパフォーマンスに影響が生じる可能性があります。ただし、パーティション射影は将来の日付を効果的に処理するように設計されています。最適なパフォーマンスを維持するには、パーティションを慎重に管理し、可能な場合は空のパーティションの過度な使用を避けてください。
+ **保存場所テンプレート** – 次の CloudFront パーティション構造と S3 パスに基づいて `storage.location.template` を正しく更新する必要があります。  
****    
[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/ja_jp/athena/latest/ug/create-cloudfront-table-partition-parquet.html)

  CloudFront パーティション構造と S3 構造が必要なパターンに一致することを確認したら、`storage.location.template` を次のように更新します。

  ```
  'storage.location.template'='s3://amzn-s3-demo-bucket/AWSLogs/account_id/CloudFront/${distributionid}/folder2/${year}/${month}/${day}/${hour}/folder3/'
  ```
**注記**  
データの正しい保存と取得を保証するには、`storage.location.template` を適切に設定することが重要です。

# CloudFront リアルタイムログ用テーブルを作成する
<a name="create-cloudfront-table-real-time-logs"></a>

**CloudFront リアルタイムログファイルフィールド用のテーブルを作成する**

1. 次の DDL ステートメントの例をコピーして Athena コンソールのクエリエディタに貼り付けます。ステートメント例では、「Amazon CloudFront 開発者ガイド」の「[Real-time logs](https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/real-time-logs.html)」セクションに記載されているログファイルフィールドを使用しています。`LOCATION` をログを保存する Simple Storage Service (Amazon S3) バケットに変更します。クエリエディタの使用については、「[はじめに](getting-started.md)」を参照してください。

   このクエリは、フィールドがタブ文字で区切られることを示すために `ROW FORMAT DELIMITED` と `FIELDS TERMINATED BY '\t'` を指定します。`ROW FORMAT DELIMITED` には、Athena がデフォルトで [LazySimpleSerDe](lazy-simple-serde.md) を使用します。列 `timestamp` は Athena の予約語であるため、バックティック (`) を使用してエスケープされています。詳細については、「[クエリで予約キーワードをエスケープする](reserved-words.md)」を参照してください。

   以下の例には、利用可能なフィールドのすべてが含まれています。不要なフィールドは、コメントアウトまたは削除することができます。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS cloudfront_real_time_logs ( 
   `timestamp` STRING,
   c_ip STRING,
   time_to_first_byte BIGINT,
   sc_status BIGINT,
   sc_bytes BIGINT,
   cs_method STRING,
   cs_protocol STRING,
   cs_host STRING,
   cs_uri_stem STRING,
   cs_bytes BIGINT,
   x_edge_location STRING,
   x_edge_request_id STRING,
   x_host_header STRING,
   time_taken BIGINT,
   cs_protocol_version STRING,
   c_ip_version STRING,
   cs_user_agent STRING,
   cs_referer STRING,
   cs_cookie STRING,
   cs_uri_query STRING,
   x_edge_response_result_type STRING,
   x_forwarded_for STRING,
   ssl_protocol STRING,
   ssl_cipher STRING,
   x_edge_result_type STRING,
   fle_encrypted_fields STRING,
   fle_status STRING,
   sc_content_type STRING,
   sc_content_len BIGINT,
   sc_range_start STRING,
   sc_range_end STRING,
   c_port BIGINT,
   x_edge_detailed_result_type STRING,
   c_country STRING,
   cs_accept_encoding STRING,
   cs_accept STRING,
   cache_behavior_path_pattern STRING,
   cs_headers STRING,
   cs_header_names STRING,
   cs_headers_count BIGINT,
   primary_distribution_id STRING,
   primary_distribution_dns_name STRING,
   origin_fbl STRING,
   origin_lbl STRING,
   asn STRING
   )
   ROW FORMAT DELIMITED 
   FIELDS TERMINATED BY '\t'
   LOCATION 's3://amzn-s3-demo-bucket/'
   TBLPROPERTIES ( 'skip.header.line.count'='2' )
   ```

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `cloudfront_real_time_logs` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

# その他のリソース
<a name="cloudfront-logs-additional-resources"></a>

Athena を使用した CloudFront ログのクエリについての詳細は、「[AWS ビッグデータブログ](https://aws.amazon.com/blogs/big-data/)」の以下の記事を参照してください。

[Amazon Athena を使用して AWS のサービス ログを簡単にクエリする](https://aws.amazon.com/blogs/big-data/easily-query-aws-service-logs-using-amazon-athena/) (2019 年 5 月 29 日)。

[Amazon CloudFront のアクセスログを大規模に分析する](https://aws.amazon.com/blogs/big-data/analyze-your-amazon-cloudfront-access-logs-at-scale/) (December 21, 2018 年 12 月 21 日)。

[AWS Lambda、Amazon Athena、Amazon Managed Service for Apache Flink を使用して Amazon CloudFront アクセスログを分析するためのサーバーレスアーキテクチャを構築する](https://aws.amazon.com/blogs/big-data/build-a-serverless-architecture-to-analyze-amazon-cloudfront-access-logs-using-aws-lambda-amazon-athena-and-amazon-kinesis-analytics/) (2017 年 5 月 26 日)。

# AWS CloudTrail ログをクエリする
<a name="cloudtrail-logs"></a>

AWS CloudTrail は、Amazon Web Services アカウントの AWS API コールとイベントを記録するサービスです。

CloudTrail ログには、コンソールを含めた AWS のサービス に対して発行された、あらゆる API コールの詳細が記載されます。CloudTrail は暗号化されたログファイルを生成して、それらを Amazon S3 に保存します。詳細については、[AWS CloudTrail ユーザーガイド](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-user-guide.html)を参照してください。

**注記**  
アカウント、リージョン、および日付にわたって CloudTrail イベント情報に対して SQL クエリを実行する場合は、CloudTrail Lake の使用を検討してください。CloudTrail Lakeは、企業からの情報を単一の検索可能なイベントデータストアに集約するトレイルを作成する AWS の代替です。Amazon S3 バケットストレージを使用する代わりに、イベントはデータレイクに保存されるため、より豊富で高速なクエリが可能になります。これを使用して、組織、リージョン間、およびカスタム時間範囲内でイベントを検索する SQL クエリを作成できます。CloudTrail Lake クエリは CloudTrail コンソール自体で実行するため、CloudTrail Lake を使用すると Athena は必要ありません。詳細については、[CloudTrail Lake](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-lake.html) のドキュメントを参照してください。

Athena での CloudTrail ログ の使用は、AWS のサービス のアクティビティに関する分析を強化する手段として優れています。たとえば、クエリを使用して傾向を識別したり、アクティビティを属性 (ソース IP アドレスやユーザーなど) でさらに分離したりできます。

一般的な用途は、セキュリティとコンプライアンスのための運用上のアクティビティの分析に CloudTrail ログを使用することです。詳細な例については、「AWS ビッグデータブログ」の記事「[AWS CloudTrail と Amazon Athena を使用してセキュリティ、コンプライアンス、運用上のアクティビティを分析する方法](https://aws.amazon.com/blogs/big-data/aws-cloudtrail-and-amazon-athena-dive-deep-to-analyze-security-compliance-and-operational-activity/)」を参照してください。

Athena は、ログファイルの `LOCATION` を指定して、Amazon S3 からこれらのログファイルを直接クエリするために使用できます。以下の 2 つの方法のいずれかを実行できます。
+ CloudTrail コンソールから直接 CloudTrailログファイルのテーブルを作成する。
+ Athena コンソールで CloudTrail ログファイルのテーブルを手動で作成する。

**Topics**
+ [CloudTrail ログと Athena テーブルを理解する](create-cloudtrail-table-understanding.md)
+ [CloudTrail ログ用の Athena テーブルを作成するために CloudTrail コンソールを使用する](create-cloudtrail-table-ct.md)
+ [Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する](create-cloudtrail-table.md)
+ [手動パーティショニングを使用して組織全体の証跡用のテーブルを作成する](create-cloudtrail-table-org-wide-trail.md)
+ [パーティション射影を使用して Athena で CloudTrail ログ用テーブルを作成する](create-cloudtrail-table-partition-projection.md)
+ [CloudTrail ログクエリの例](query-examples-cloudtrail-logs.md)

# CloudTrail ログと Athena テーブルを理解する
<a name="create-cloudtrail-table-understanding"></a>

テーブルの作成を開始する前に、CloudTrail、そしてそれがどのようにデータを保存するかについての理解を深めておく必要があります。これは、テーブルを CloudTrail コンソールから作成するか Athena から作成するかにかかわらず、必要なテーブルを作成するために役立ちます。

CloudTrail は、ログを JSON テキストファイルとして、圧縮された gzip 形式 (`*.json.gz`) で保存します。ログファイルの保存先は、証跡のセットアップ方法、AWS リージョン あるいはログを記録する対象のリージョン、その他の要因によって異なります。

ログの保存先、JSON 構造、およびレコードファイルの内容の詳細については、[AWS CloudTrail ユーザーガイド](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-user-guide.html)の以下のトピックを参照してください。
+  [CloudTrail ログファイルの検索](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-find-log-files.html) 
+  [CloudTrail ログファイルの例](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-log-file-examples.html) 
+  [CloudTrail レコードの内容](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-event-reference-record-contents.html)
+  [CloudTrail イベントリファレンス](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-event-reference.html) 

ログを収集して Amazon S3 に保存し、AWS マネジメントコンソール で CloudTrail を有効にします。詳細については、「AWS CloudTrail ユーザーガイド」の「[証跡の作成](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-create-a-trail-using-the-console-first-time.html)」を参照してください。

# CloudTrail ログ用の Athena テーブルを作成するために CloudTrail コンソールを使用する
<a name="create-cloudtrail-table-ct"></a>

CloudTrail コンソールから直接 CloudTrail ログをクエリするために、パーティションされていない Athena テーブルを作成できます。CloudTrail コンソールからの Athena テーブルの作成には、Athena でテーブルを作成するために十分なアクセス許可を持つロールでログインする必要があります。

**注記**  
CloudTrail コンソールを使用して、組織の証跡ログ用の Athena テーブルを作成することはできません。代わりに、Athena コンソールを使用してテーブルを手動で作成し、正しいストレージ場所を指定できるようにします。組織の証跡については、*AWS CloudTrail ユーザーガイド*の「[組織の証跡の作成](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/creating-trail-organization.html)」を参照してください。
+ Athena のためのアクセス許可のセットアップについては、「[設定、管理、プログラムによるアクセス](setting-up.md)」を参照してください。
+ パーティションを含むテーブルの作成については、「[Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する](create-cloudtrail-table.md)」を参照してください。

**CloudTrail コンソールを使用して CloudTrail 証跡用の Athena テーブルを作成する**

1. CloudTrail コンソールの [https://console.aws.amazon.com/cloudtrail/](https://console.aws.amazon.com/cloudtrail/) を開いてください。

1. ナビゲーションペインで [**Event history (イベント履歴)**] を選択してください。

1. [**Athena テーブルを作成**] をクリックします。  
![\[[Create Athena table] (Athena テーブルを作成) をクリックします。\]](http://docs.aws.amazon.com/ja_jp/athena/latest/ug/images/cloudtrail-logs-create-athena-table.png)

1. **[Storage location]** (ストレージの場所) の下矢印を使用して、クエリする証跡のためにログファイルが保存される Amazon S3 バケットを選択します。
**注記**  
証跡に関連付けられているバケットの名前を探すには、CloudTrail のナビゲーションペインで **[Trails]** (証跡) を選択して、証跡の **[S3 bucket]** (S3 バケット) 列を表示します。バケットの Amazon S3 の場所を確認するには、**[S3 bucket]** (S3 バケット) 列でバケットのリンクを選択します。これにより、Amazon S3 コンソールで CloudTrail バケットの場所が開きます。

1. **[テーブルの作成]** を選択します。Amazon S3 バケットの名前が含まれたデフォルトの名前でテーブルが作成されます。

# Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する
<a name="create-cloudtrail-table"></a>

Athena コンソールで、CloudTrail ログファイル用のテーブルを手動で作成してから、Athena でクエリを実行することができます。

**Athena コンソールを使用して CloudTrail 証跡のための Athena テーブルを作成する**

1. 次の DDL ステートメントをコピーして Athena コンソールのクエリエディタに貼り付け、必要に応じて変更します。CloudTrail ログファイルは、公開 API コールの順序付けられたスタックトレースではないため、ログファイルのフィールドは特定の順序では表示されません。

   ```
   CREATE EXTERNAL TABLE cloudtrail_logs (
   eventversion STRING,
   useridentity STRUCT<
                  type:STRING,
                  principalid:STRING,
                  arn:STRING,
                  accountid:STRING,
                  invokedby:STRING,
                  accesskeyid:STRING,
                  username:STRING,
                  onbehalfof: STRUCT<
                       userid: STRING,
                       identitystorearn: STRING>,
     sessioncontext:STRUCT<
       attributes:STRUCT<
                  mfaauthenticated:STRING,
                  creationdate:STRING>,
       sessionissuer:STRUCT<  
                  type:STRING,
                  principalid:STRING,
                  arn:STRING, 
                  accountid:STRING,
                  username:STRING>,
       ec2roledelivery:string,
       webidfederationdata: STRUCT<
                  federatedprovider: STRING,
                  attributes: map<string,string>>
     >
   >,
   eventtime STRING,
   eventsource STRING,
   eventname STRING,
   awsregion STRING,
   sourceipaddress STRING,
   useragent STRING,
   errorcode STRING,
   errormessage STRING,
   requestparameters STRING,
   responseelements STRING,
   additionaleventdata STRING,
   requestid STRING,
   eventid STRING,
   resources ARRAY<STRUCT<
                  arn:STRING,
                  accountid:STRING,
                  type:STRING>>,
   eventtype STRING,
   apiversion STRING,
   readonly STRING,
   recipientaccountid STRING,
   serviceeventdetails STRING,
   sharedeventid STRING,
   vpcendpointid STRING,
   vpcendpointaccountid STRING,
   eventcategory STRING,
   addendum STRUCT<
     reason:STRING,
     updatedfields:STRING,
     originalrequestid:STRING,
     originaleventid:STRING>,
   sessioncredentialfromconsole STRING,
   edgedevicedetails STRING,
   tlsdetails STRUCT<
     tlsversion:STRING,
     ciphersuite:STRING,
     clientprovidedhostheader:STRING>
   )
   PARTITIONED BY (region string, year string, month string, day string)
   ROW FORMAT SERDE 'org.apache.hive.hcatalog.data.JsonSerDe'
   STORED AS INPUTFORMAT 'com.amazon.emr.cloudtrail.CloudTrailInputFormat'
   OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/Account_ID/';
   ```
**注記**  
例に示されている `org.apache.hive.hcatalog.data.JsonSerDe` の使用をお勧めします。`com.amazon.emr.hive.serde.CloudTrailSerde` は存在するものの、現在新しい CloudTrail フィールドの一部を処理しません。

1. (オプション) テーブルに必要のないフィールドをすべて削除します。特定の列のセットのみを読み込む必要がある場合は、テーブル定義で他の列を除外できます。

1. クエリするログデータが含まれる Amazon S3 バケットをポイントするように `s3://amzn-s3-demo-bucket/AWSLogs/Account_ID/` を変更します。例では、特定のアカウントに関するログの `LOCATION` 値を使用していますが、目的に応じた保存先を指定できます。以下に例を示します。
   + 複数のアカウントのデータを分析するには、`LOCATION` を元の設定に戻し、`AWSLogs` を使用してすべての `LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/'` を分析対称にします。
   + 特定の日付、アカウント、リージョンのデータを分析するには、`LOCATION 's3://amzn-s3-demo-bucket/123456789012/CloudTrail/us-east-1/2016/03/14/'.` を使用します。
   + 管理イベントの代わりにネットワークアクティビティデータを分析するには、`LOCATION` 句の `/CloudTrail/` を `/CloudTrail-NetworkActivity/` に置き換えます。

   オブジェクト階層の最上位レベルを使用することで、Athena を使用したクエリの実行時に最大の柔軟性が提供されます。

1. フィールドが正しく表示されていることを確認します。CloudTrail レコード内のフィールドの完全なリストに関する詳細については、「[CloudTrail レコードの内容](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-event-reference-record-contents.html)」を参照してください。

   ステップ 1 の `CREATE TABLE` ステートメント例では、[Hive JSON SerDe](hive-json-serde.md) を使用します。この例では、フィールド `requestparameters`、`responseelements`、および `additionaleventdata` は、クエリでタイプ `STRING` としてリストされていますが、JSON で使用される `STRUCT` データ型です。そのため、これらのフィールドからデータを取得するには、`JSON_EXTRACT` 関数を使用します。詳細については、「[文字列から JSON データを抽出する](extracting-data-from-JSON.md)」を参照してください。パフォーマンスを向上させるために、この例では、AWS リージョン、年、月、日に基づいてデータをパーティションしています。

1. Athena コンソールで `CREATE TABLE` ステートメントを実行します。

1. 以下の例のように、[ALTER TABLE ADD PARTITION](alter-table-add-partition.md) コマンドを使用してパーティションをロードすることで、データをクエリできるようにします。

   ```
   ALTER TABLE table_name ADD 
      PARTITION (region='us-east-1',
                 year='2019',
                 month='02',
                 day='01')
      LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/Account_ID/CloudTrail/us-east-1/2019/02/01/'
   ```

# 手動パーティショニングを使用して組織全体の証跡用のテーブルを作成する
<a name="create-cloudtrail-table-org-wide-trail"></a>

Athena で組織全体の CloudTrail ログファイル用のテーブルを作成するには、「[Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する](create-cloudtrail-table.md)」(Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する) の手順に従います。ただし、次の手順に記載されている変更を加えてください。

**組織全体の CloudTrail ログ用の Athena テーブルを作成するには**

1. 次の例のように、`CREATE TABLE` ステートメントで、組織 ID が含まれるように `LOCATION` 句を変更します。

   ```
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/organization_id/'
   ```

1. 次の例のように、`PARTITIONED BY` 句で、アカウント ID のエントリを文字列として追加します。

   ```
   PARTITIONED BY (account string, region string, year string, month string, day string)
   ```

   次の例は、結合された結果を示しています。

   ```
   ...
   
   PARTITIONED BY (account string, region string, year string, month string, day string) 
   ROW FORMAT SERDE 'org.apache.hive.hcatalog.data.JsonSerDe'
   STORED AS INPUTFORMAT 'com.amazon.emr.cloudtrail.CloudTrailInputFormat'
   OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/organization_id/Account_ID/CloudTrail/'
   ```

1. 次の例のように、`ALTER TABLE` ステートメントの `ADD PARTITION` 句には、アカウント ID を含めます。

   ```
   ALTER TABLE table_name ADD
   PARTITION (account='111122223333',
   region='us-east-1',
   year='2022',
   month='08',
   day='08')
   ```

1. 次の例のように、`ALTER TABLE` ステートメントの `LOCATION` 句には、追加する組織 ID、アカウント ID、パーティションを含めます。

   ```
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/organization_id/Account_ID/CloudTrail/us-east-1/2022/08/08/'
   ```

   次の例では、`ALTER TABLE` ステートメントは結合された結果を示します。

   ```
   ALTER TABLE table_name ADD
   PARTITION (account='111122223333',
   region='us-east-1',
   year='2022',
   month='08',
   day='08')
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/organization_id/111122223333/CloudTrail/us-east-1/2022/08/08/'
   ```

大規模な組織では、この方法を使用して各組織アカウント ID のパーティションを手動で追加および維持するのは面倒である可能性があることに留意してください。このようなシナリオでは、Athena ではなく CloudTrail Lake の利用を検討してください。このようなシナリオにおいて CloudTrail Lake を利用することには、次の利点があります:
+ 組織全体のログを自動的に集約する
+ パーティションまたは Athena テーブルの設定やメンテナンスが不要
+ クエリが CloudTrail コンソールで直接実行される
+ SQL 互換のクエリ言語を使用する

詳細については、「AWS CloudTrail ユーザーガイド」の「[AWS CloudTrail Lake の使用](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-lake.html)」を参照してください。

# パーティション射影を使用して Athena で CloudTrail ログ用テーブルを作成する
<a name="create-cloudtrail-table-partition-projection"></a>

CloudTrail ログには事前に指定できるパーティションスキームを持つ既知の構造があるため、Athena のパーティション射影機能を使用することで、クエリランタイムを短縮し、パーティション管理を自動化できます。新しいデータが追加されると、パーティション射影は新しいパーティションを自動で追加します。このため、`ALTER TABLE ADD PARTITION` を使用してパーティションを手動で追加する必要がなくなります。

次の `CREATE TABLE` ステートメント例では、指定した日付から現在までの単一の AWS リージョン リージョンの CloudTrail ログで、パーティション射影を自動的に使用しています。`LOCATION` 句と `storage.location.template` 句では、*bucket*、*account-id*、および *aws-region* の各プレースホルダーを、対応する同等の値に置き換えます。`projection.timestamp.range` では、*2020*/*01*/*01* を使用を開始する日に置き換えます。クエリが正常に実行されると、テーブルをクエリできます。パーティションをロードするのに、`ALTER TABLE ADD PARTITION` を実行する必要はありません。

```
CREATE EXTERNAL TABLE cloudtrail_logs_pp(
    eventversion STRING,
    useridentity STRUCT<
        type: STRING,
        principalid: STRING,
        arn: STRING,
        accountid: STRING,
        invokedby: STRING,
        accesskeyid: STRING,
        username: STRING,
        onbehalfof: STRUCT<
             userid: STRING,
             identitystorearn: STRING>,
        sessioncontext: STRUCT<
            attributes: STRUCT<
                mfaauthenticated: STRING,
                creationdate: STRING>,
            sessionissuer: STRUCT<
                type: STRING,
                principalid: STRING,
                arn: STRING,
                accountid: STRING,
                username: STRING>,
            ec2roledelivery:string,
            webidfederationdata: STRUCT<
                federatedprovider: STRING,
                attributes: map<string,string>>
        >
    >,
    eventtime STRING,
    eventsource STRING,
    eventname STRING,
    awsregion STRING,
    sourceipaddress STRING,
    useragent STRING,
    errorcode STRING,
    errormessage STRING,
    requestparameters STRING,
    responseelements STRING,
    additionaleventdata STRING,
    requestid STRING,
    eventid STRING,
    readonly STRING,
    resources ARRAY<STRUCT<
        arn: STRING,
        accountid: STRING,
        type: STRING>>,
    eventtype STRING,
    apiversion STRING,
    recipientaccountid STRING,
    serviceeventdetails STRING,
    sharedeventid STRING,
    vpcendpointid STRING,
    vpcendpointaccountid STRING,
    eventcategory STRING,
    addendum STRUCT<
      reason:STRING,
      updatedfields:STRING,
      originalrequestid:STRING,
      originaleventid:STRING>,
    sessioncredentialfromconsole STRING,
    edgedevicedetails STRING,
    tlsdetails STRUCT<
      tlsversion:STRING,
      ciphersuite:STRING,
      clientprovidedhostheader:STRING>
  )
PARTITIONED BY (
   `timestamp` string)
ROW FORMAT SERDE 'org.apache.hive.hcatalog.data.JsonSerDe'
STORED AS INPUTFORMAT 'com.amazon.emr.cloudtrail.CloudTrailInputFormat'
OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION
  's3://amzn-s3-demo-bucket/AWSLogs/account-id/CloudTrail/aws-region'
TBLPROPERTIES (
  'projection.enabled'='true', 
  'projection.timestamp.format'='yyyy/MM/dd', 
  'projection.timestamp.interval'='1', 
  'projection.timestamp.interval.unit'='DAYS', 
  'projection.timestamp.range'='2020/01/01,NOW', 
  'projection.timestamp.type'='date', 
  'storage.location.template'='s3://amzn-s3-demo-bucket/AWSLogs/account-id/CloudTrail/aws-region/${timestamp}')
```

パーティション射影の詳細については、「[Amazon Athena でパーティション射影を使用する](partition-projection.md)」を参照してください。

# CloudTrail ログクエリの例
<a name="query-examples-cloudtrail-logs"></a>

以下の例は、CloudTrail イベントログ向けに作成されたテーブルから、匿名化された (署名されていない) すべてのリクエストを返すクエリの一部を示しています。このクエリは、`useridentity.accountid` が匿名で `useridentity.arn` が指定されていないリクエストを選択します。

```
SELECT *
FROM cloudtrail_logs
WHERE 
    eventsource = 's3.amazonaws.com' AND 
    eventname in ('GetObject') AND 
    useridentity.accountid = 'anonymous' AND 
    useridentity.arn IS NULL AND
    requestparameters LIKE '%[your bucket name ]%';
```

詳細については、「AWS Big·Data·Blog」(ビッグデータブログ) の記事「[AWS CloudTrail と Amazon Athena を使用して、セキュリティ、コンプライアンス、運用上のアクティビティを分析する](https://aws.amazon.com/blogs/big-data/aws-cloudtrail-and-amazon-athena-dive-deep-to-analyze-security-compliance-and-operational-activity/)」を参照してください。

## CloudTrail ログのネストされたフィールドをクエリする
<a name="cloudtrail-logs-nested-fields"></a>

`userIdentity` および `resources` フィールドはネストされたデータ型であるため、それらのクエリには特別な処理が必要です。

`userIdentity` オブジェクトは、ネストされた `STRUCT` 型で構成されています。以下の例にあるように、これらは、フィールドを区切るためにドットを使用してクエリすることができます。

```
SELECT 
    eventsource, 
    eventname,
    useridentity.sessioncontext.attributes.creationdate,
    useridentity.sessioncontext.sessionissuer.arn
FROM cloudtrail_logs
WHERE useridentity.sessioncontext.sessionissuer.arn IS NOT NULL
ORDER BY eventsource, eventname
LIMIT 10
```

`resources` フィールドは `STRUCT` オブジェクトの配列です。これらの配列では、`CROSS JOIN UNNEST` を使用して配列のネストを解除し、そのオブジェクトをクエリできるようにします。

以下の例は、リソース ARN が `example/datafile.txt` で終わるすべての行を返します。読みやすさのために、[replace](https://prestodb.io/docs/current/functions/string.html#replace) 関数が ARN から初期の `arn:aws:s3:::` サブストリングを削除します。

```
SELECT 
    awsregion,
    replace(unnested.resources_entry.ARN,'arn:aws:s3:::') as s3_resource,
    eventname,
    eventtime,
    useragent
FROM cloudtrail_logs t
CROSS JOIN UNNEST(t.resources) unnested (resources_entry)
WHERE unnested.resources_entry.ARN LIKE '%example/datafile.txt'
ORDER BY eventtime
```

以下の例は、`DeleteBucket` のイベントをクエリします。このクエリは、バケットの名前とバケットが属するアカウント ID を `resources` オブジェクトから抽出します。

```
SELECT 
    awsregion,
    replace(unnested.resources_entry.ARN,'arn:aws:s3:::') as deleted_bucket,
    eventtime AS time_deleted,
    useridentity.username, 
    unnested.resources_entry.accountid as bucket_acct_id 
FROM cloudtrail_logs t
CROSS JOIN UNNEST(t.resources) unnested (resources_entry)
WHERE eventname = 'DeleteBucket'
ORDER BY eventtime
```

ネスト解除の詳細については、「[配列をフィルタリングする](filtering-arrays.md)」を参照してください。

## CloudTrail ログのクエリに関するヒント
<a name="tips-for-querying-cloudtrail-logs"></a>

CloudTrail ログデータを調査する際には、次を考慮してください。
+ ログをクエリする前に、ログテーブルが「[Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する](create-cloudtrail-table.md)」に示している内容と同じになっていることを確認します。これが最初のテーブルではない場合は、コマンド `DROP TABLE cloudtrail_logs` を使用して既存のテーブルを削除します。
+ 既存のテーブルを削除した後、再作成します。詳細については、「[Athena で手動パーティショニングを使用して CloudTrail ログ用のテーブルを作成する](create-cloudtrail-table.md)」を参照してください。

  Athena クエリのフィールドが正しく表示されていることを確認します。CloudTrail レコード内のフィールドの完全なリストについては、「[CloudTrail レコードの内容](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-event-reference-record-contents.html)」を参照してください。

  クエリ内のフィールドが JSON 形式 (`STRUCT` など) である場合は、JSON からデータを抽出します。詳細については、「[文字列から JSON データを抽出する](extracting-data-from-JSON.md)」を参照してください。

  CloudTrail テーブルに対してクエリを発行するためのいくつかの提案事項:
+ 最初に、どの ユーザーが、どの送信元 IP アドレスから API オペレーションを呼び出したかを確認します。
+ 次の基本的な SQL クエリをテンプレートとして使用します。このクエリを Athena コンソールに貼り付けて実行します。

  ```
  SELECT
   useridentity.arn,
   eventname,
   sourceipaddress,
   eventtime
  FROM cloudtrail_logs
  LIMIT 100;
  ```
+ クエリを修正して、データをさらに詳しく調べます。
+ パフォーマンスを強化するには、`LIMIT` 句を追加して、指定したサブセットの行のみが返るようにします。

# Amazon EMR ログをクエリする
<a name="emr-logs"></a>

Amazon EMR と、Amazon EMR で実行されるビッグデータアプリケーションは、ログファイルを生成します。ログファイルは[プライマリノード](https://docs.aws.amazon.com/emr/latest/ManagementGuide/emr-master-core-task-nodes.html)に書き込まれます。ログファイルを自動的に Amazon S3 にアーカイブするように Amazon EMR を設定することもできます。Amazon Athena を使用してこれらのログをクエリし、アプリケーションとクラスターのイベントと傾向を特定することができます。Amazon EMR のログファイルのタイプと、それらの Amazon S3 への保存に関する詳細については、「Amazon EMR マネジメントガイド」の「[ログファイルを表示する](https://docs.aws.amazon.com/emr/latest/ManagementGuide/emr-manage-view-web-log-files.html)」を参照してください。

**Topics**
+ [Amazon EMR ログファイルに基づいて、基本的なテーブルを作成およびクエリする](emr-create-table.md)
+ [Amazon EMR ログに基づいて、パーティショニングされたテーブルを作成およびクエリする](emr-create-table-partitioned.md)

# Amazon EMR ログファイルに基づいて、基本的なテーブルを作成およびクエリする
<a name="emr-create-table"></a>

以下の例は、`s3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6/elasticmapreduce/` に保存されたログファイルに基づいて、基本的なテーブル `myemrlogs` を作成します。以下の例で使用されている Amazon S3 の場所は、リージョン *us-west-2* で Amazon Web Services アカウント *123456789012* によって作成された EMR クラスターのデフォルトでのログの場所のパターンを反映しています。カスタムの場所を使用する場合、パターンは s3://amzn-s3-demo-bucket/*ClusterID* です。

パーティション化されたテーブルを作成してクエリのパフォーマンスを向上させ、データ転送を削減できる可能性のある方法については、「[Amazon EMR ログに基づいて、パーティショニングされたテーブルを作成およびクエリする](emr-create-table-partitioned.md)」を参照してください。

```
CREATE EXTERNAL TABLE `myemrlogs`(
  `data` string COMMENT 'from deserializer')
ROW FORMAT DELIMITED  
FIELDS TERMINATED BY '|'
LINES TERMINATED BY '\n'
STORED AS INPUTFORMAT 
  'org.apache.hadoop.mapred.TextInputFormat' 
OUTPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION
  's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6'
```

## クエリの例
<a name="emr-example-queries-basic"></a>

次の例のクエリは、前の例で作成した `myemrlogs` テーブルに対して実行できます。

**Example – ERROR、WARN、INFO、EXCEPTION、FATAL、または DEBUG の発生に関するステップログのクエリ**  

```
SELECT data,
        "$PATH"
FROM "default"."myemrlogs"
WHERE regexp_like("$PATH",'s-86URH188Z6B1')
        AND regexp_like(data, 'ERROR|WARN|INFO|EXCEPTION|FATAL|DEBUG') limit 100;
```

**Example – ERROR、WARN、INFO、EXCEPTION、FATAL、または DEBUG に関する特定のインスタンスログ i-00b3c0a839ece0a9c のクエリ**  

```
SELECT "data",
        "$PATH" AS filepath
FROM "default"."myemrlogs"
WHERE regexp_like("$PATH",'i-00b3c0a839ece0a9c')
        AND regexp_like("$PATH",'state')
        AND regexp_like(data, 'ERROR|WARN|INFO|EXCEPTION|FATAL|DEBUG') limit 100;
```

**Example – ERROR、WARN、INFO、EXCEPTION、FATAL、または DEBUG に関する Presto アプリケーションログのクエリ**  

```
SELECT "data",
        "$PATH" AS filepath
FROM "default"."myemrlogs"
WHERE regexp_like("$PATH",'presto')
        AND regexp_like(data, 'ERROR|WARN|INFO|EXCEPTION|FATAL|DEBUG') limit 100;
```

**Example – ERROR、WARN、INFO、EXCEPTION、FATAL、または DEBUG に関する Namenode アプリケーションログのクエリ**  

```
SELECT "data",
        "$PATH" AS filepath
FROM "default"."myemrlogs"
WHERE regexp_like("$PATH",'namenode')
        AND regexp_like(data, 'ERROR|WARN|INFO|EXCEPTION|FATAL|DEBUG') limit 100;
```

**Example – ERROR、WARN、INFO、EXCEPTION、FATAL、または DEBUG に関する日付と時間でのすべてのログのクエリ**  

```
SELECT distinct("$PATH") AS filepath
FROM "default"."myemrlogs"
WHERE regexp_like("$PATH",'2019-07-23-10')
        AND regexp_like(data, 'ERROR|WARN|INFO|EXCEPTION|FATAL|DEBUG') limit 100;
```

# Amazon EMR ログに基づいて、パーティショニングされたテーブルを作成およびクエリする
<a name="emr-create-table-partitioned"></a>

これらの例は、Athena テーブルを作成するためのものと同じログの場所を使用しますが、テーブルがパーティション分割された後、パーティションがログの場所ごとに作成されます。詳細については、「[データのパーティション化](partitions.md)」を参照してください。

次のクエリは、`mypartitionedemrlogs` という名前のパーティション化されたテーブルを作成します。

```
CREATE EXTERNAL TABLE `mypartitionedemrlogs`(
  `data` string COMMENT 'from deserializer')
 partitioned by (logtype string)
ROW FORMAT DELIMITED  
FIELDS TERMINATED BY '|'
LINES TERMINATED BY '\n'
STORED AS INPUTFORMAT 
  'org.apache.hadoop.mapred.TextInputFormat' 
OUTPUTFORMAT 
 'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION 's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6'
```

以下のクエリステートメントは、次に Amazon S3 で Amazon EMR が作成する異なるログタイプのサブディレクトリに基づいて、テーブルパーティションを作成します。

```
ALTER TABLE mypartitionedemrlogs ADD
     PARTITION (logtype='containers')
     LOCATION 's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6/containers/'
```

```
ALTER TABLE mypartitionedemrlogs ADD
     PARTITION (logtype='hadoop-mapreduce')
     LOCATION 's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6/hadoop-mapreduce/'
```

```
ALTER TABLE mypartitionedemrlogs ADD
     PARTITION (logtype='hadoop-state-pusher')
     LOCATION 's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6/hadoop-state-pusher/'
```

```
ALTER TABLE mypartitionedemrlogs ADD
     PARTITION (logtype='node')
     LOCATION 's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6/node/'
```

```
ALTER TABLE mypartitionedemrlogs ADD
     PARTITION (logtype='steps')
     LOCATION 's3://aws-logs-123456789012-us-west-2/elasticmapreduce/j-2ABCDE34F5GH6/steps/'
```

パーティションを作成したら、テーブルで `SHOW PARTITIONS` クエリを実行して、以下を確認します。

```
SHOW PARTITIONS mypartitionedemrlogs;
```

## クエリの例
<a name="emr-example-queries-partitioned"></a>

以下の例は、上記の例で作成されたテーブルとパーティションを使用する特定のログエントリに対するクエリを示しています。

**Example – ERROR または WARN に関するコンテナパーティション内のアプリケーション application\$11561661818238\$10002 ログのクエリ**  

```
SELECT data,
        "$PATH"
FROM "default"."mypartitionedemrlogs"
WHERE logtype='containers'
        AND regexp_like("$PATH",'application_1561661818238_0002')
        AND regexp_like(data, 'ERROR|WARN') limit 100;
```

**Example – ジョブ job\$11561661818238\$10004 と Failed Reduces に関する Hadoop-Mapreduce パーティションのクエリ**  

```
SELECT data,
        "$PATH"
FROM "default"."mypartitionedemrlogs"
WHERE logtype='hadoop-mapreduce'
        AND regexp_like(data,'job_1561661818238_0004|Failed Reduces') limit 100;
```

**Example – クエリ ID 056e0609-33e1-4611-956c-7a31b42d2663 に関するノードパーティションでの Hive ログのクエリ**  

```
SELECT data,
        "$PATH"
FROM "default"."mypartitionedemrlogs"
WHERE logtype='node'
        AND regexp_like("$PATH",'hive')
        AND regexp_like(data,'056e0609-33e1-4611-956c-7a31b42d2663') limit 100;
```

**Example – アプリケーション 1567660019320\$10001\$101\$1000001 に関するノードパーティションでの Resourcemanager ログのクエリ**  

```
SELECT data,
        "$PATH"
FROM "default"."mypartitionedemrlogs"
WHERE logtype='node'
        AND regexp_like(data,'resourcemanager')
        AND regexp_like(data,'1567660019320_0001_01_000001') limit 100
```

# AWS Global Accelerator フローログをクエリする
<a name="querying-global-accelerator-flow-logs"></a>

AWS Global Accelerator を使用して、ネットワークトラフィックを AWS グローバルネットワーク経由で最適なエンドポイントに転送するアクセラレーターを作成できます。Global Accelerator の詳細については、「[AWS Global Accelerator とは?](https://docs.aws.amazon.com/global-accelerator/latest/dg/what-is-global-accelerator.html)」を参照してください。

Global Accelerator フローログは、アクセラレーター内のネットワークインターフェイス間で送受信される IP アドレストラフィックに関する情報の取得を可能にします。フローログデータは Amazon S3 にパブリッシュされ、そこでデータを取得して表示できます。詳細については、「[AWS Global Accelerator のフローログ](https://docs.aws.amazon.com/global-accelerator/latest/dg/monitoring-global-accelerator.flow-logs.html)」を参照してください。

Athena を使用して、Amazon S3 内の Global Accelerator フローログの場所を指定するテーブルを作成することによって、フローログをクエリすることができます。

**Global Accelerator フローログのテーブルを作成する**

1. 以下の DDL ステートメントをコピーして Athena コンソール内に貼り付けます。このクエリでは、*ROW FORMAT DELIMITED* を指定し、[SerDe](serde-reference.md) の指定は省略します。この場合、クエリでは [`LazySimpleSerDe`](lazy-simple-serde.md) が使用されます。このクエリでは、フィールドはスペースで終了します。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS aga_flow_logs (
     version string,
     account string,
     acceleratorid string,
     clientip string,
     clientport int,
     gip string,
     gipport int,
     endpointip string,
     endpointport int,
     protocol string,
     ipaddresstype string,
     numpackets bigint,
     numbytes int,
     starttime int,
     endtime int,
     action string,
     logstatus string,
     agasourceip string,
     agasourceport int,
     endpointregion string,
     agaregion string,
     direction string,
     vpc_id string,
     reject_reason string
   )
   PARTITIONED BY (dt string)
   ROW FORMAT DELIMITED
   FIELDS TERMINATED BY ' '
   LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/account_id/globalaccelerator/region/'
   TBLPROPERTIES ("skip.header.line.count"="1");
   ```

1. ログデータが含まれる Amazon S3 バケットをポイントするように `LOCATION` 値を変更します。

   ```
   's3://amzn-s3-demo-bucket/prefix/AWSLogs/account_id/globalaccelerator/region_code/'
   ```

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `aga_flow_logs` テーブルを登録し、そのデータをクエリに使用できるようにします。

1. 次のサンプルクエリのように、パーティションを作成してデータを読み取ります。このクエリは、指定日の 1 つのパーティションを作成します。日付と場所のプレースホルダーを置き換えます。

   ```
   ALTER TABLE aga_flow_logs
   ADD PARTITION (dt='YYYY-MM-dd')
   LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/account_id/globalaccelerator/region_code/YYYY/MM/dd';
   ```

## AWS Global Accelerator フローログのクエリ例
<a name="querying-global-accelerator-flow-logs-examples"></a>

**Example – 特定のエッジロケーションを通過するリクエストをリストする**  
以下のクエリ例は、LHR エッジロケーションを通過するリクエストをリストします。`LIMIT` 演算子を使用すると、一度にクエリするログの数を制限できます。  

```
SELECT 
  clientip, 
  agaregion, 
  protocol, 
  action 
FROM 
  aga_flow_logs 
WHERE 
  agaregion LIKE 'LHR%' 
LIMIT 
  100;
```

**Example – HTTPS リクエストの大部分の受信するエンドポイント IP アドレスをリストする**  
最大数の HTTPS リクエストを受信しているエンドポイント IP アドレスを確認するには、次のクエリを使用します。このクエリは、HTTPS ポート 443 で受信したパケット数をカウントし、送信先 IP アドレス別にグループ分けして、上位 10 の IP アドレスを返します。  

```
SELECT 
  SUM(numpackets) AS packetcount, 
  endpointip 
FROM 
  aga_flow_logs 
WHERE 
  endpointport = 443 
GROUP BY 
  endpointip 
ORDER BY 
  packetcount DESC 
LIMIT 
  10;
```

# Amazon GuardDuty の検出結果をクエリする
<a name="querying-guardduty"></a>

[Amazon GuardDuty](https://aws.amazon.com/guardduty/) は、AWS 環境内での不正または悪質である可能性がある予期しないアクティビティを識別するために役立つ、セキュリティをモニタリングするサービスです。悪意のある可能性がある予期しないアクティビティが検出されると、GuardDuty がストレージと分析のために Amazon S3 にエクスポートできるセキュリティ[結果](https://docs.aws.amazon.com/guardduty/latest/ug/guardduty_findings.html)を生成します。結果を Amazon S3 にエクスポートしたら、Athena を使用してそれらをクエリできます。この記事は、GuardDutyの 結果用のテーブルを Athena で作成し、それらをクエリする方法を説明します。

Amazon GuardDuty の詳細については、「[Amazon GuardDuty ユーザーガイド](https://docs.aws.amazon.com/guardduty/latest/ug/)」を参照してください。

## 前提条件
<a name="querying-guardduty-prerequisites"></a>
+ Amazon S3 に結果をエクスポートするための GuardDuty 機能を有効にします。ステップについては、「Amazon GuardDuty ユーザーガイド」の「[結果のエクスポート](https://docs.aws.amazon.com/guardduty/latest/ug/guardduty_exportfindings.html)」を参照してください。

## GuardDuty の検出結果のために Athena でテーブルを作成する
<a name="querying-guardduty-creating-a-table-in-athena-for-guardduty-findings"></a>

Athena から GuardDuty の結果をクエリするには、結果用のテーブルを作成する必要があります。

**GuardDuty の結果のために Athena でテーブルをで作成する**

1. [https://console.aws.amazon.com/athena/](https://console.aws.amazon.com/athena/home) で Athena コンソールを開きます。

1. 以下の DDL ステートメントを Athena コンソール内に貼り付けます。`LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/account-id/GuardDuty/'` の値を、Amazon S3 にある GuardDuty の結果にポイントするように変更します。

   ```
   CREATE EXTERNAL TABLE `gd_logs` (
     `schemaversion` string,
     `accountid` string,
     `region` string,
     `partition` string,
     `id` string,
     `arn` string,
     `type` string,
     `resource` string,
     `service` string,
     `severity` string,
     `createdat` string,
     `updatedat` string,
     `title` string,
     `description` string)
   ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe'
    LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/account-id/GuardDuty/'
    TBLPROPERTIES ('has_encrypted_data'='true')
   ```
**注記**  
SerDe では、各 JSON ドキュメントが、レコード内のフィールドを区切る行終端文字なしの、1 行のテキストに収まっていることを想定しています。JSON テキストがプリティプリント形式の場合、テーブルを作成した後にクエリを実行しようとすると、以下のようなエラーメッセージが表示される場合があります。「HIVE\$1CURSOR\$1ERROR: Row is not a valid JSON Object」、または「HIVE\$1CURSOR\$1ERROR: JsonParseException: Unexpected end-of-input: expected close marker for OBJECT」。詳細については、GitHub の OpenX SerDe のドキュメントで「[JSON Data Files](https://github.com/rcongiu/Hive-JSON-Serde#json-data-files)」(JSON データファイル) を参照してください。

1. Athena コンソールでクエリを実行して、`gd_logs` テーブルを登録します。クエリが完了すると、結果は Athena からクエリを実行できる状態になります。

## クエリの例
<a name="querying-guardduty-examples"></a>

以下の例は、Athena から GuardDuty の 結果をクエリする方法を示しています。

**Example – DNS データの流出**  
以下のクエリは、DNS クエリを介してデータを流出している可能性がある Amazon EC2 インスタンスに関する情報を返します。  

```
SELECT
    title,
    severity,
    type,
    id AS FindingID,
    accountid,
    region,
    createdat,
    updatedat,
    json_extract_scalar(service, '$.count') AS Count,
    json_extract_scalar(resource, '$.instancedetails.instanceid') AS InstanceID,
    json_extract_scalar(service, '$.action.actiontype') AS DNS_ActionType,
    json_extract_scalar(service, '$.action.dnsrequestaction.domain') AS DomainName,
    json_extract_scalar(service, '$.action.dnsrequestaction.protocol') AS protocol,
    json_extract_scalar(service, '$.action.dnsrequestaction.blocked') AS blocked
FROM gd_logs
WHERE type = 'Trojan:EC2/DNSDataExfiltration'
ORDER BY severity DESC
```

**Example – 不正な IAM ユーザーアクセス**  
以下のクエリは、すべてのリージョンからの IAM プリンシパルに関するすべての `UnauthorizedAccess:IAMUser` 結果タイプを返します。  

```
SELECT title,
         severity,
         type,
         id,
         accountid,
         region,
         createdat,
         updatedat,
         json_extract_scalar(service, '$.count') AS Count, 
         json_extract_scalar(resource, '$.accesskeydetails.username') AS IAMPrincipal, 
         json_extract_scalar(service,'$.action.awsapicallaction.api') AS APIActionCalled
FROM gd_logs
WHERE type LIKE '%UnauthorizedAccess:IAMUser%' 
ORDER BY severity desc;
```

## GuardDuty の結果のクエリに関するヒント
<a name="querying-guardduty-tips"></a>

クエリを作成するときは、次の点に注意してください。
+ ネストされた JSON フィールドからデータを抽出するには、Presto `json_extract` 関数、または `json_extract_scalar` 関数を使用します。詳細については、「[文字列から JSON データを抽出する](extracting-data-from-JSON.md)」(JSON からデータを抽出する) を参照してください。
+ JSON フィールドのすべての文字が小文字であることを確認します。
+  クエリ結果のダウンロードについては、「[Athena コンソールを使用してクエリ結果ファイルをダウンロードする](saving-query-results.md)」を参照してください。

# AWS Network Firewall ログをクエリする
<a name="querying-network-firewall-logs"></a>

AWS Network Firewall は、Amazon Virtual Private Cloud インスタンスに不可欠なネットワーク保護をデプロイするために使用できるマネージドサービスです。AWS Network Firewall は AWS Firewall Manager と連携するため、AWS Network Firewall ルールに基づいてポリシーを構築して、VPC とアカウント全体に集中的に適用できます。の詳細については、「AWS Network Firewall」を参照してください。。[AWS Network Firewall](https://aws.amazon.com/network-firewall/)

ファイアウォールのステートフルルールエンジンに転送するトラフィックの AWS Network Firewall ログの記録を設定できます。ログを記録すると、ステートフルエンジンがパケットを受信した時間、パケットに関する詳細情報、パケットに対して実行されたステートフルルールアクションなど、ネットワークトラフィックに関する詳細情報が得られます。ログは、設定したログ送信先に公開され、そこでログを取得して表示できます。詳細については、「AWS Network Firewall デベロッパーガイド」の「[AWS Network Firewallからのネットワークトラフィックのログ記録](https://docs.aws.amazon.com/network-firewall/latest/developerguide/firewall-logging.html)」を参照してください。

**Topics**
+ [アラートログのテーブルを作成およびクエリする](querying-network-firewall-logs-sample-alert-logs-table.md)
+ [NetFlow ログ用のテーブルを作成およびクエリする](querying-network-firewall-logs-sample-netflow-logs-table.md)

# アラートログのテーブルを作成およびクエリする
<a name="querying-network-firewall-logs-sample-alert-logs-table"></a>

1. 次のサンプル DDL ステートメントをアラートログの構造に合わせて変更します。ステートメントを更新して、最新バージョンのログの列を含めることが必要になる場合があります。詳細については、「AWS Network Firewall デベロッパーガイド」の「[ファイアウォールログの内容](https://docs.aws.amazon.com/network-firewall/latest/developerguide/firewall-logging.html#firewall-logging-contents)」を参照してください。

   ```
   CREATE EXTERNAL TABLE network_firewall_alert_logs (
     firewall_name string,
     availability_zone string,
     event_timestamp string,
     event struct<
       timestamp:string,
       flow_id:bigint,
       event_type:string,
       src_ip:string,
       src_port:int,
       dest_ip:string,
       dest_port:int,
       proto:string,
       app_proto:string,
       sni:string,
       tls_inspected:boolean,
       tls_error:struct<
         error_message:string>,
       revocation_check:struct<
         leaf_cert_fpr:string,
         status:string,
         action:string>,
       alert:struct<
         alert_id:string,
         alert_type:string,
         action:string,
         signature_id:int,
         rev:int,
         signature:string,
         category:string,
         severity:int,
         rule_name:string,
         alert_name:string,
         alert_severity:string,
         alert_description:string,
         file_name:string,
         file_hash:string,
         packet_capture:string,
         reference_links:array<string>
       >, 
       src_country:string, 
       dest_country:string, 
       src_hostname:string, 
       dest_hostname:string, 
       user_agent:string, 
       url:string
      >
   )
    ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe'
    LOCATION 's3://amzn-s3-demo-bucket/path_to_alert_logs_folder/';
   ```

1. `LOCATION` 句を変更して Amazon S3 のログ用のフォルダを指定します。

1. Athena クエリエディタで `CREATE TABLE` クエリを実行します。クエリが完了すると、Athena は `network_firewall_alert_logs` テーブルを登録し、テーブルがポイントするデータをクエリできる状態にします。

## クエリの例
<a name="querying-network-firewall-logs-alert-log-sample-query"></a>

このセクションのサンプルアラートログクエリでは、TLS 検査が実行されたイベントのうち、重大度が 2 以上のアラートを含むものがフィルタリングされます。

このクエリでは、エイリアスを使用して、その列が属する `struct` を示す出力列の見出しを作成します。例えば、`event.alert.category` フィールドの列見出しは、単なる `category` ではなく `event_alert_category` になります。列名をさらにカスタマイズするには、好みに合わせてエイリアスを変更します。例えば、アンダースコアやその他の区切り文字を使用して `struct` 名とフィールド名を区切ることができます。

テーブル定義とクエリ結果に含めるフィールドに基づいて、列名と `struct` 参照を必ず変更してください。

```
SELECT 
  firewall_name,
  availability_zone,
  event_timestamp,
  event.timestamp AS event_timestamp,
  event.flow_id AS event_flow_id,
  event.event_type AS event_type,
  event.src_ip AS event_src_ip,
  event.src_port AS event_src_port,
  event.dest_ip AS event_dest_ip,
  event.dest_port AS event_dest_port,
  event.proto AS event_protol,
  event.app_proto AS event_app_proto,
  event.sni AS event_sni,
  event.tls_inspected AS event_tls_inspected,
  event.tls_error.error_message AS event_tls_error_message,
  event.revocation_check.leaf_cert_fpr AS event_revocation_leaf_cert,
  event.revocation_check.status AS event_revocation_check_status,
  event.revocation_check.action AS event_revocation_check_action,
  event.alert.alert_id AS event_alert_alert_id,
  event.alert.alert_type AS event_alert_alert_type,
  event.alert.action AS event_alert_action,
  event.alert.signature_id AS event_alert_signature_id,
  event.alert.rev AS event_alert_rev,
  event.alert.signature AS event_alert_signature,
  event.alert.category AS event_alert_category,
  event.alert.severity AS event_alert_severity,
  event.alert.rule_name AS event_alert_rule_name,
  event.alert.alert_name AS event_alert_alert_name,
  event.alert.alert_severity AS event_alert_alert_severity,
  event.alert.alert_description AS event_alert_alert_description,
  event.alert.file_name AS event_alert_file_name,
  event.alert.file_hash AS event_alert_file_hash,
  event.alert.packet_capture AS event_alert_packet_capture,
  event.alert.reference_links AS event_alert_reference_links,
  event.src_country AS event_src_country,
  event.dest_country AS event_dest_country,
  event.src_hostname AS event_src_hostname,
  event.dest_hostname AS event_dest_hostname,
  event.user_agent AS event_user_agent,
  event.url AS event_url
FROM 
  network_firewall_alert_logs 
WHERE 
  event.alert.severity >= 2
  AND event.tls_inspected = true 
LIMIT 10;
```

# NetFlow ログ用のテーブルを作成およびクエリする
<a name="querying-network-firewall-logs-sample-netflow-logs-table"></a>

1. 次の DDL ステートメントのサンプルを Netflow ログの構造に合わせて変更します。ステートメントを更新して、最新バージョンのログの列を含めることが必要になる場合があります。詳細については、「AWS Network Firewall デベロッパーガイド」の「[ファイアウォールログの内容](https://docs.aws.amazon.com/network-firewall/latest/developerguide/firewall-logging.html#firewall-logging-contents)」を参照してください。

   ```
   CREATE EXTERNAL TABLE network_firewall_netflow_logs (
     firewall_name string,
     availability_zone string,
     event_timestamp string,
     event struct<
       timestamp:string,
       flow_id:bigint,
       event_type:string,
       src_ip:string,
       src_port:int,
       dest_ip:string,
       dest_port:int,
       proto:string,
       app_proto:string,
       tls_inspected:boolean,
       netflow:struct<
         pkts:int,
         bytes:bigint,
         start:string,
         `end`:string,
         age:int,
         min_ttl:int,
         max_ttl:int,
         tcp_flags:struct<
           syn:boolean,
           fin:boolean,
           rst:boolean,
           psh:boolean,
           ack:boolean,
           urg:boolean
           >
         >
       >
   )
   ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe' 
   LOCATION 's3://amzn-s3-demo-bucket/path_to_netflow_logs_folder/';
   ```

1. `LOCATION` 句を変更して Amazon S3 のログ用のフォルダを指定します。

1. Athena クエリエディタで `CREATE TABLE` クエリを実行します。クエリが完了すると、Athena は `network_firewall_netflow_logs` テーブルを登録し、テーブルがポイントするデータをクエリできる状態にします。

## クエリの例
<a name="querying-network-firewall-logs-netflow-log-sample-query"></a>

このセクションのサンプル Netflow ログクエリでは、TLS 検査が実行されたイベントがフィルタリングされます。

このクエリでは、エイリアスを使用して、その列が属する `struct` を示す出力列の見出しを作成します。例えば、`event.netflow.bytes` フィールドの列見出しは、単なる `bytes` ではなく `event_netflow_bytes` になります。列名をさらにカスタマイズするには、好みに合わせてエイリアスを変更します。例えば、アンダースコアやその他の区切り文字を使用して `struct` 名とフィールド名を区切ることができます。

テーブル定義とクエリ結果に含めるフィールドに基づいて、列名と `struct` 参照を必ず変更してください。

```
SELECT
  event.src_ip AS event_src_ip,
  event.dest_ip AS event_dest_ip,
  event.proto AS event_proto,
  event.app_proto AS event_app_proto,
  event.tls_inspected AS event_tls_inspected,
  event.netflow.pkts AS event_netflow_pkts,
  event.netflow.bytes AS event_netflow_bytes,
  event.netflow.tcp_flags.syn AS event_netflow_tcp_flags_syn 
FROM network_firewall_netflow_logs 
WHERE event.tls_inspected = true
```

# Network Load Balancer のログをクエリする
<a name="networkloadbalancer-classic-logs"></a>

Athena を使用して、Network Load Balancer からのログを分析および処理します。これらのログは、Network Load Balancer に送信された Transport Layer Security (TLS) リクエストに関する詳細情報を受け取ります。これらのアクセスログを使用して、トラフィックパターンを分析し、問題のトラブルシューティングを行うことができます。

Network Load Balancer のアクセスログを分析する前に、ログを宛先の Amazon S3 バケットに保存するためにログを設定します。詳細および各 Network Load Balancer アクセスログエントリの詳細については、「[Network Load Balancer のアクセスログ](https://docs.aws.amazon.com/elasticloadbalancing/latest/network/load-balancer-access-logs.html)」を参照してください。

**Network Load Balancer ログのテーブルを作成する**

1. 以下の DDL ステートメントをコピーして Athena コンソール内に貼り付けます。Network Load Balancer ログレコードの[構文](https://docs.aws.amazon.com/elasticloadbalancing/latest/network/load-balancer-access-logs.html#access-log-file-format)をチェックします。ログレコードに対応する列と正規表現を含めるために、必要に応じてステートメントを更新します。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS nlb_tls_logs (
               type string,
               version string,
               time string,
               elb string,
               listener_id string,
               client_ip string,
               client_port int,
               target_ip string,
               target_port int,
               tcp_connection_time_ms double,
               tls_handshake_time_ms double,
               received_bytes bigint,
               sent_bytes bigint,
               incoming_tls_alert int,
               cert_arn string,
               certificate_serial string,
               tls_cipher_suite string,
               tls_protocol_version string,
               tls_named_group string,
               domain_name string,
               alpn_fe_protocol string,
               alpn_be_protocol string,
               alpn_client_preference_list string,
               tls_connection_creation_time string
               )
               ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.RegexSerDe'
               WITH SERDEPROPERTIES (
               'serialization.format' = '1',
               'input.regex' = 
               '([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*):([0-9]*) ([^ ]*):([0-9]*) ([-.0-9]*) ([-.0-9]*) ([-0-9]*) ([-0-9]*) ([-0-9]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ([^ ]*) ?([^ ]*)?( .*)?'
               )
               LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/AWS_account_ID/elasticloadbalancing/region';
   ```

1. `LOCATION` の Simple Storage Service (Amazon S3) バケットを変更して、Network Load Balancer ログの宛先を指定します。

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `nlb_tls_logs` テーブルを登録して、その中のデータをクエリ向けに準備します。

## クエリの例
<a name="query-nlb-example"></a>

証明書の使用回数を確認するには、次の例のようなクエリを使用します。

```
SELECT count(*) AS 
         ct,
         cert_arn
FROM "nlb_tls_logs"
GROUP BY  cert_arn;
```

次のクエリでは、1.3 より前の TLS バージョンを使用しているユーザーの数を表示します。

```
SELECT tls_protocol_version,
         COUNT(tls_protocol_version) AS 
         num_connections,
         client_ip
FROM "nlb_tls_logs"
WHERE tls_protocol_version < 'tlsv13'
GROUP BY tls_protocol_version, client_ip;
```

次のクエリを使用して、TLS ハンドシェイクに長い時間がかかっている接続を特定します。

```
SELECT *
FROM "nlb_tls_logs"
ORDER BY  tls_handshake_time_ms DESC 
LIMIT 10;
```

次のクエリは、過去 30 日間にネゴシエートされた TLS プロトコルのバージョンと暗号化スイートを特定し、その数をカウントするために使用します。

```
SELECT tls_cipher_suite,
         tls_protocol_version,
         COUNT(*) AS ct
FROM "nlb_tls_logs"
WHERE from_iso8601_timestamp(time) > current_timestamp - interval '30' day
        AND NOT tls_protocol_version = '-'
GROUP BY tls_cipher_suite, tls_protocol_version
ORDER BY ct DESC;
```

# Amazon Route 53 Resolver クエリログをクエリする
<a name="querying-r53-resolver-logs"></a>

Amazon Route 53 Resolver クエリログ用の Athena テーブルを作成して、それらを Athena からクエリできます。

Route 53 Resolver のクエリロギングは、VPC 内のリソースによって行われた DNS クエリ、インバウンドリゾルバーエンドポイントを使用するオンプレミスリソース、再帰的な DNS 解決にアウトバウンドリゾルバーエンドポイントを使用するクエリ、およびドメインリストをブロック、許可、またはモニタリングするために Route 53 Resolver DNS ファイアウォールルールを使用するクエリをログ記録するためのものです。Resolver クエリログ記録の詳細については、*Amazon Route 53 デベロッパーガイド*の「[Resolver query logging](https://docs.aws.amazon.com/Route53/latest/DeveloperGuide/resolver-query-logs.html)」を参照してください。ログにある各フィールドについては、「Amazon Route 53 デベロッパーガイド」の「[Resolver クエリログに表示される値](https://docs.aws.amazon.com/Route53/latest/DeveloperGuide/resolver-query-logs-format.html)」を参照してください。

**Topics**
+ [Resolver クエリログ用のテーブルを作成する](querying-r53-resolver-logs-creating-the-table.md)
+ [パーティション射影を使用する](querying-r53-resolver-logs-partitioning-example.md)
+ [クエリの例](querying-r53-resolver-logs-example-queries.md)

# Resolver クエリログ用のテーブルを作成する
<a name="querying-r53-resolver-logs-creating-the-table"></a>

Athena コンソールのクエリエディタを使用して、Route 53 Resolver クエリログ用のテーブルを作成してクエリできます。

**Route 53 Resolver クエリログ用の Athena テーブルを作成してクエリする**

1. [https://console.aws.amazon.com/athena/](https://console.aws.amazon.com/athena/home) で Athena コンソールを開きます。

1. Athena クエリエディタに以下の `CREATE TABLE` ステートメントを入力します。`LOCATION` 句の値を、Simple Storage Service (Amazon S3) の Resolver ログの場所に対応する値に置き換えます。

   ```
   CREATE EXTERNAL TABLE r53_rlogs (
     version string,
     account_id string,
     region string,
     vpc_id string,
     query_timestamp string,
     query_name string,
     query_type string,
     query_class
       string,
     rcode string,
     answers array<
       struct<
         Rdata: string,
         Type: string,
         Class: string>
       >,
     srcaddr string,
     srcport int,
     transport string,
     srcids struct<
       instance: string,
       resolver_endpoint: string
       >,
     firewall_rule_action string,
     firewall_rule_group_id string,
     firewall_domain_list_id string
    )
        
   ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe'
   LOCATION 's3://amzn-s3-demo-bucket/AWSLogs/aws_account_id/vpcdnsquerylogs/{vpc-id}/'
   ```

   Resolver クエリログデータは JSON 形式であるため、CREATE TABLE ステートメントは [JSON SerDe ライブラリ](json-serde.md)を使用してデータを分析します。
**注記**  
SerDe では、各 JSON ドキュメントが、レコード内のフィールドを区切る行終端文字なしの、1 行のテキストに収まっていることを想定しています。JSON テキストがプリティプリント形式の場合、テーブルを作成した後にクエリを実行しようとすると、以下のようなエラーメッセージが表示される場合があります。「HIVE\$1CURSOR\$1ERROR: Row is not a valid JSON Object」、または「HIVE\$1CURSOR\$1ERROR: JsonParseException: Unexpected end-of-input: expected close marker for OBJECT」。詳細については、GitHub の OpenX SerDe のドキュメントで「[JSON Data Files](https://github.com/rcongiu/Hive-JSON-Serde#json-data-files)」(JSON データファイル) を参照してください。

1. **[Run query]** (クエリの実行) を選択します。ステートメントが `r53_rlogs` という名前の Athena テーブルを作成します。このテーブルの列は Resolver ログデータの各フィールドを表します。

1. Athena コンソールのクエリエディタで以下のクエリを実行して、テーブルが作成されたことを検証します。

   ```
   SELECT * FROM "r53_rlogs" LIMIT 10
   ```

# パーティション射影を使用する
<a name="querying-r53-resolver-logs-partitioning-example"></a>

次の例は、パーティション射影を使用し、VPC と日付で分割された Resolver クエリログの `CREATE TABLE` ステートメントを示しています。パーティション射影の詳細については、「[Amazon Athena でパーティション射影を使用する](partition-projection.md)」を参照してください。

```
CREATE EXTERNAL TABLE r53_rlogs (
  version string,
  account_id string,
  region string,
  vpc_id string,
  query_timestamp string,
  query_name string,
  query_type string,
  query_class string,
  rcode string,
  answers array<
    struct<
      Rdata: string,
      Type: string,
      Class: string>
    >,
  srcaddr string,
  srcport int,
  transport string,
  srcids struct<
    instance: string,
    resolver_endpoint: string
    >,
  firewall_rule_action string,
  firewall_rule_group_id string,
  firewall_domain_list_id string
)
PARTITIONED BY (
`date` string,
`vpc` string
)
ROW FORMAT SERDE      'org.openx.data.jsonserde.JsonSerDe'
STORED AS INPUTFORMAT 'org.apache.hadoop.mapred.TextInputFormat'
OUTPUTFORMAT          'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION              's3://amzn-s3-demo-bucket/route53-query-logging/AWSLogs/aws_account_id/vpcdnsquerylogs/'
TBLPROPERTIES(
'projection.enabled' = 'true',
'projection.vpc.type' = 'enum',
'projection.vpc.values' = 'vpc-6446ae02',
'projection.date.type' = 'date',
'projection.date.range' = '2023/06/26,NOW',
'projection.date.format' = 'yyyy/MM/dd',
'projection.date.interval' = '1',
'projection.date.interval.unit' = 'DAYS',
'storage.location.template' = 's3://amzn-s3-demo-bucket/route53-query-logging/AWSLogs/aws_account_id/vpcdnsquerylogs/${vpc}/${date}/'
)
```

# クエリの例
<a name="querying-r53-resolver-logs-example-queries"></a>

以下の例は、Resolver クエリログで Athena から実行できるクエリをいくつか説明しています。

## 例 1 – ログを降順の query\$1timestamp 順にクエリする
<a name="querying-r53-resolver-logs-example-1-query-logs-in-descending-query_timestamp-order"></a>

以下のクエリは、`query_timestamp` 順で降順にログ結果を表示します。

```
SELECT * FROM "r53_rlogs"
ORDER BY query_timestamp DESC
```

## 例 2 – 指定された開始時刻と終了時刻の範囲内でログをクエリする
<a name="querying-r53-resolver-logs-example-2-query-logs-within-specified-start-and-end-times"></a>

以下のクエリは、2020 年 9 月 24 日の午前 0 時から午前 8 時の間のログをクエリします。開始時刻と終了時刻は、独自の要件に従って置き換えます。

```
SELECT query_timestamp, srcids.instance, srcaddr, srcport, query_name, rcode
FROM "r53_rlogs"
WHERE (parse_datetime(query_timestamp,'yyyy-MM-dd''T''HH:mm:ss''Z')
     BETWEEN parse_datetime('2020-09-24-00:00:00','yyyy-MM-dd-HH:mm:ss') 
     AND parse_datetime('2020-09-24-00:08:00','yyyy-MM-dd-HH:mm:ss'))
ORDER BY query_timestamp DESC
```

## 例 3 – 指定された DNS クエリ名パターンに基づいてログをクエリする
<a name="querying-r53-resolver-logs-example-3-query-logs-based-on-a-specified-dns-query-name-pattern"></a>

以下のクエリは、クエリ名に文字列「example.com」が含まれたレコードを選択します。

```
SELECT query_timestamp, srcids.instance, srcaddr, srcport, query_name, rcode, answers
FROM "r53_rlogs"
WHERE query_name LIKE '%example.com%'
ORDER BY query_timestamp DESC
```

## 例 4 – 応答のないログリクエストをクエリする
<a name="querying-r53-resolver-logs-example-4-query-log-requests-with-no-answer"></a>

以下のクエリは、リクエストが応答を受け取らなかったログエントリを選択します。

```
SELECT query_timestamp, srcids.instance, srcaddr, srcport, query_name, rcode, answers
FROM "r53_rlogs"
WHERE cardinality(answers) = 0
```

## 例 5 – 特定の回答が含まれるログをクエリする
<a name="querying-r53-resolver-logs-example-5-query-logs-with-a-specific-answer"></a>

以下のクエリは、`answer.Rdata` 値に指定された IP アドレスがあるログを表示します。

```
SELECT query_timestamp, srcids.instance, srcaddr, srcport, query_name, rcode, answer.Rdata
FROM "r53_rlogs"
CROSS JOIN UNNEST(r53_rlogs.answers) as st(answer)
WHERE answer.Rdata='203.0.113.16';
```

# Amazon SES イベントログをクエリする
<a name="querying-ses-logs"></a>

Amazon Athena を使用して、[Amazon Simple Email Service](https://aws.amazon.com/ses/) (Amazon SES) イベントログをクエリできます。

Amazon SES は、ユーザー独自の E メールアドレスとドメインを使用して E メールを送受信するための、簡単でコスト効率の高い方法を提供する E メールプラットフォームです。イベント、メトリクス、および統計を使用して、Amazon SES 送信アクティビティをきめ細かいレベルでモニタリングできます。

ユーザー定義の特性に基づいて、Amazon SES イベントを [Amazon CloudWatch](https://aws.amazon.com/cloudwatch/)、[Amazon Data Firehose](https://aws.amazon.com/kinesis/data-firehose/)、または [Amazon Simple Notification Service](https://aws.amazon.com/sns/) に発行できます。Amazon S3 で情報を保存した後、Amazon Athena からクエリを実行できます。

Amazon SES イベントログデータでビューを作成し、ネストされた配列をフラット化する手順を含む Amazon SES ログの Athena `CREATE TABLE` ステートメントの例については、AWS ブログ記事「[Analyzing Amazon SES event data with AWS Analytics Services](https://aws.amazon.com/blogs/messaging-and-targeting/analyzing-amazon-ses-event-data-with-aws-analytics-services/)」の「Step 3: Using Amazon Athena to query the SES event logs」を参照してください。

# Amazon VPC フローログをクエリする
<a name="vpc-flow-logs"></a>

Amazon Virtual Private Cloud フローログは、VPC 内のネットワークインターフェイス間で送受信される IP トラフィックに関する情報をキャプチャします。このログを使用してネットワークトラフィックのパターンを調査し、VPC ネットワーク全体の脅威やリスクを特定します。

Amazon VPC フローログのクエリを実行するには、2 つの方法があります。

****
+ **Amazon VPC コンソール** — Amazon VPC コンソールの Athena 統合機能を使用して、パーティションを含む Athena データベース、ワークグループ、およびフローログテーブルを作成する CloudFormation テンプレートを生成します。テンプレートでは、[事前定義されたフローログのクエリ](https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs-athena.html#predefined-queries)のセットも作成します。これは、VPC を通過するトラフィックに関するインサイトの取得に使用できます。

  このアプローチの詳細については、「*Amazon VPC ユーザーガイド*」の「[Amazon Athena を使用したフローログのクエリ](https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs-athena.html)」を参照してください。
+ **Amazon Athena コンソール** — Athena コンソールでテーブルやクエリを直接作成します。詳細については、引き続きこのページを参照してください。

Athena でログのクエリを開始する前に、[VPC フローログを有効化](https://docs.aws.amazon.com/AmazonVPC/latest/UserGuide/flow-logs.html)し、それらが Amazon S3 バケットに保存されるように設定します。ログを作成したら、それを数分間実行していくらかのデータを収集します。ログは、Athena で直接クエリできる GZIP 圧縮形式で作成されます。

VPC フローログの作成時に、フローログで返すフィールドおよびフィールドが表示される順序を指定する際は、カスタム形式を使用できます。フローログレコード詳細については、「*Amazon VPC ユーザーガイド*」の「[フローログレコード](https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs.html#flow-log-records)」を参照してください。

## 考慮事項と制限事項
<a name="vpc-flow-logs-common-considerations"></a>

Athena で Amazon VPC フローログのテーブルを作成する際は、次の点に注意してください。
+ デフォルトでは、Parquet は名前で列にアクセスします。詳細については、「[スキーマの更新を処理する](handling-schema-updates-chapter.md)」を参照してください。
+ Athena の列名には、フローログレコードの名前を使用します。Athena スキーマの列名は、Amazon VPC フローログのフィールド名と完全に一致する必要があります。ただし、これらには次の違いがあります。
  + Amazon VPC のログフィールド名のハイフンは、Athena の列名ではアンダースコアに置き換えられます。Athena のデータベース名、テーブル名、および列名で使用できる文字については、「[データベース、テーブル、列に名前を付ける](tables-databases-columns-names.md)」を参照してください。
  + バックティックで囲むことで、Athena で[予約されたキーワード](reserved-words.md)であるフローログのレコード名をエスケープします。
+ VPC フローログは AWS アカウント 固有です。ログファイルを Amazon S3 に発行すると、Amazon VPC が Amazon S3 で作成するパスには、フローログの作成に使用された AWS アカウント の ID が含まれます。詳細については、「*Amazon VPC ユーザーガイド*」の「[フローログを Amazon S3 に発行する](https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs-s3.html)」を参照してください。

**Topics**
+ [考慮事項と制限事項](#vpc-flow-logs-common-considerations)
+ [Amazon VPC フローログのテーブルを作成し、クエリする](vpc-flow-logs-create-table-statement.md)
+ [Apache Parquet 形式でフローログのテーブルを作成する](vpc-flow-logs-parquet.md)
+ [パーティション射影を使用して Amazon VPC フローログのテーブルを作成およびクエリする](vpc-flow-logs-partition-projection.md)
+ [パーティション射影を使用して Apache Parquet 形式でフローログのテーブルを作成する](vpc-flow-logs-partition-projection-parquet-example.md)
+ [その他のリソース](query-examples-vpc-logs-additional-resources.md)

# Amazon VPC フローログのテーブルを作成し、クエリする
<a name="vpc-flow-logs-create-table-statement"></a>

次の手順では、Amazon VPC フローログ用の Amazon VPC テーブルを作成します。カスタム形式でフローログを作成する場合は、フローログの作成時に指定したフィールドと一致するフィールドを、それらに指定したものと同じ順序で使用してテーブルを作成します。

**Amazon VPC フローログ用の Athena テーブルを作成するには**

1. [考慮事項と制限事項](vpc-flow-logs.md#vpc-flow-logs-common-considerations) セクションのガイドラインに従って、次のような DDL ステートメントを Athena コンソールクエリエディタに入力します。サンプルステートメントは、「[フローログレコード](https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs.html#flow-log-records)」に記載されているように、Amazon VPC フローログのバージョン 2 から 5 の列を持つテーブルを作成します。異なる列のセットまたは列の順序を使用する場合は、必要に応じてステートメントを変更します。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS `vpc_flow_logs` (
     version int,
     account_id string,
     interface_id string,
     srcaddr string,
     dstaddr string,
     srcport int,
     dstport int,
     protocol bigint,
     packets bigint,
     bytes bigint,
     start bigint,
     `end` bigint,
     action string,
     log_status string,
     vpc_id string,
     subnet_id string,
     instance_id string,
     tcp_flags int,
     type string,
     pkt_srcaddr string,
     pkt_dstaddr string,
     region string,
     az_id string,
     sublocation_type string,
     sublocation_id string,
     pkt_src_aws_service string,
     pkt_dst_aws_service string,
     flow_direction string,
     traffic_path int
   )
   PARTITIONED BY (`date` date)
   ROW FORMAT DELIMITED
   FIELDS TERMINATED BY ' '
   LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/{account_id}/vpcflowlogs/{region_code}/'
   TBLPROPERTIES ("skip.header.line.count"="1");
   ```

   次の点に注意してください。
   + このクエリは `ROW FORMAT DELIMITED` を指定し、SerDe の指定が省略されます。これは、クエリが [CSV、TSV、カスタム区切りファイル用の Lazy Simple SerDe](lazy-simple-serde.md) を使用しているということです。このクエリでは、フィールドはスペースで終了します。
   + `PARTITIONED BY` 句は、`date` 型を使用します。これにより、クエリで数学演算子を使用して、特定の日付より古いものまたは新しいものを選択できます。
**注記**  
`date` は DDL ステートメントの予約済みキーワードであるため、バックティック文字でエスケープされます。詳細については、「[クエリで予約キーワードをエスケープする](reserved-words.md)」を参照してください。
   + 異なるカスタム形式の VPC フローログの場合、フローログの作成時に指定したフィールドと一致するようにフィールドを変更します。

1. ログデータが含まれる Amazon S3 バケットをポイントするように `LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/{account_id}/vpcflowlogs/{region_code}/'` を変更します。

1. Athena コンソールでクエリを実行します。クエリが完了すると、Athena が `vpc_flow_logs` テーブルを登録し、その中のデータに対してクエリを発行できるように準備します。

1. 次のサンプルクエリのように、パーティションを作成してデータを読み取れるようにします。このクエリは、指定日の 1 つのパーティションを作成します。必要に応じて、日付と場所のプレースホルダーを置き換えます。
**注記**  
このクエリは、指定日に対して単一のパーティションのみを作成します。プロセスを自動化するには、このクエリを実行し、この方法で `year/month/day` にパーティションを作成するスクリプトを使用するか、[パーティション射影](vpc-flow-logs-partition-projection.md)を指定する `CREATE TABLE` ステートメントを使用します。

   ```
   ALTER TABLE vpc_flow_logs
   ADD PARTITION (`date`='YYYY-MM-dd')
   LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/{account_id}/vpcflowlogs/{region_code}/YYYY/MM/dd';
   ```

## vpc\$1flow\$1logs テーブルのクエリ例
<a name="query-examples-vpc-logs"></a>

Athena コンソールのクエリエディタを使用して、作成したテーブルで SQL ステートメントを実行します。クエリを保存したり、以前のクエリを表示したり、クエリ結果を CSV 形式でダウンロードできます。次の例では、`vpc_flow_logs` をテーブルの名前に置き換えます。また、要件に応じて列の値やその他の変数を変更します。

次のクエリ例では、指定された日付に対して最大 100 のフローログを一覧表示します。

```
SELECT * 
FROM vpc_flow_logs 
WHERE date = DATE('2020-05-04') 
LIMIT 100;
```

次のクエリは、すべての拒否された TCP 接続を一覧表示します。新しく作成した日付パーティション列 `date` を使用して、該当イベントが発生した週の曜日を抽出します。

```
SELECT day_of_week(date) AS
  day,
  date,
  interface_id,
  srcaddr,
  action,
  protocol
FROM vpc_flow_logs
WHERE action = 'REJECT' AND protocol = 6
LIMIT 100;
```

最大数の HTTPS リクエストを受信しているサーバーを確認するには、次のクエリを使用します。HTTPS ポート 443 で受信したパケット数をカウントし、送信先 IP アドレス別にグループ分けして、過去 1 週間の上位 10 のサーバーを返します。

```
SELECT SUM(packets) AS
  packetcount,
  dstaddr
FROM vpc_flow_logs
WHERE dstport = 443 AND date > current_date - interval '7' day
GROUP BY dstaddr
ORDER BY packetcount DESC
LIMIT 10;
```

# Apache Parquet 形式でフローログのテーブルを作成する
<a name="vpc-flow-logs-parquet"></a>

次の手順では、Apache Parquet 形式で Amazon VPC フローログ用の Amazon VPC テーブルを作成します。

**Parquet 形式で Amazon VPC フローログ用の Athena テーブルを作成するには**

1. [考慮事項と制限事項](vpc-flow-logs.md#vpc-flow-logs-common-considerations) セクションのガイドラインに従って、次のような DDL ステートメントを Athena コンソールクエリエディタに入力します。サンプルステートメントは、「[フローログレコード](https://docs.aws.amazon.com/vpc/latest/userguide/flow-logs.html#flow-log-records)」に記載されているように、1 時間ごとに Hive パーティションされる Parquet 形式で Amazon VPC フローログのバージョン 2 から 5 の列を持つテーブルを作成します。1 時間ごとのパーティションがない場合は、`PARTITIONED BY` 句から `hour` を削除します。

   ```
   CREATE EXTERNAL TABLE IF NOT EXISTS vpc_flow_logs_parquet (
     version int,
     account_id string,
     interface_id string,
     srcaddr string,
     dstaddr string,
     srcport int,
     dstport int,
     protocol bigint,
     packets bigint,
     bytes bigint,
     start bigint,
     `end` bigint,
     action string,
     log_status string,
     vpc_id string,
     subnet_id string,
     instance_id string,
     tcp_flags int,
     type string,
     pkt_srcaddr string,
     pkt_dstaddr string,
     region string,
     az_id string,
     sublocation_type string,
     sublocation_id string,
     pkt_src_aws_service string,
     pkt_dst_aws_service string,
     flow_direction string,
     traffic_path int
   )
   PARTITIONED BY (
     `aws-account-id` string,
     `aws-service` string,
     `aws-region` string,
     `year` string, 
     `month` string, 
     `day` string,
     `hour` string
   )
   ROW FORMAT SERDE 
     'org.apache.hadoop.hive.ql.io.parquet.serde.ParquetHiveSerDe'
   STORED AS INPUTFORMAT 
     'org.apache.hadoop.hive.ql.io.parquet.MapredParquetInputFormat' 
   OUTPUTFORMAT 
     'org.apache.hadoop.hive.ql.io.parquet.MapredParquetOutputFormat'
   LOCATION
     's3://amzn-s3-demo-bucket/prefix/AWSLogs/'
   TBLPROPERTIES (
     'EXTERNAL'='true', 
     'skip.header.line.count'='1'
     )
   ```

1. ログデータが含まれる Amazon S3 パスをポイントするようにサンプル `LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/'` を変更します。

1. Athena コンソールでクエリを実行します。

1. Hive 互換形式のデータの場合、Athena コンソールで次のコマンドを実行して、メタストアの Hive パーティションを更新およびロードします。クエリが完了すると、`vpc_flow_logs_parquet` テーブルでデータをクエリできます。

   ```
   MSCK REPAIR TABLE vpc_flow_logs_parquet
   ```

   Hive 互換データを使用していない場合は、[ALTER TABLE ADD PARTITION](alter-table-add-partition.md) を実行してパーティションをロードします。

Athena を使用して、Parquet 形式の Amazon VPC フローログをクエリする方法については、「*AWS ビッグデータブログ*」の「[Apache Parquet 形式の VPC フローログを使用して、ネットワーク分析のパフォーマンスを最適化し、そのコストを削減する](https://aws.amazon.com/blogs/big-data/optimize-performance-and-reduce-costs-for-network-analytics-with-vpc-flow-logs-in-apache-parquet-format/)」を参照してください。

# パーティション射影を使用して Amazon VPC フローログのテーブルを作成およびクエリする
<a name="vpc-flow-logs-partition-projection"></a>

次のような `CREATE TABLE` ステートメントを使用してテーブルを作成およびパーティションし、[パーティション射影](partition-projection.md)を使用してパーティションを自動的に入力します。サンプルのテーブル名 `test_table_vpclogs` をそのテーブルの名前に置き換えます。Amazon VPC ログデータが含まれている Amazon S3 バケットを指定するように `LOCATION` 句を編集します。

次は、非 Hive スタイルのパーティション形式で配信される VPC フローログ用の `CREATE TABLE` ステートメントです。この例では、マルチアカウント集計が可能です。複数のアカウントからの VPC フローログを 1 つの Amazon S3 バケットに集中管理する場合は、アカウント ID を Amazon S3 パスに入力する必要があります。

```
CREATE EXTERNAL TABLE IF NOT EXISTS test_table_vpclogs (
  version int,
  account_id string,
  interface_id string,
  srcaddr string,
  dstaddr string,
  srcport int,
  dstport int,
  protocol bigint,
  packets bigint,
  bytes bigint,
  start bigint,
  `end` bigint,
  action string,
  log_status string,
  vpc_id string,
  subnet_id string,
  instance_id string,
  tcp_flags int,
  type string,
  pkt_srcaddr string,
  pkt_dstaddr string,
  az_id string,
  sublocation_type string,
  sublocation_id string,
  pkt_src_aws_service string,
  pkt_dst_aws_service string,
  flow_direction string,
  traffic_path int
)
PARTITIONED BY (accid string, region string, day string)
ROW FORMAT DELIMITED
FIELDS TERMINATED BY ' '
LOCATION '$LOCATION_OF_LOGS'
TBLPROPERTIES
(
"skip.header.line.count"="1",
"projection.enabled" = "true",
"projection.accid.type" = "enum",
"projection.accid.values" = "$ACCID_1,$ACCID_2",
"projection.region.type" = "enum",
"projection.region.values" = "$REGION_1,$REGION_2,$REGION_3",
"projection.day.type" = "date",
"projection.day.range" = "$START_RANGE,NOW",
"projection.day.format" = "yyyy/MM/dd",
"storage.location.template" = "s3://amzn-s3-demo-bucket/AWSLogs/${accid}/vpcflowlogs/${region}/${day}"
)
```

## test\$1table\$1vpclogs のクエリ例
<a name="query-examples-vpc-logs-pp"></a>

次のクエリ例では、前述の `CREATE TABLE` ステートメントで作成された `test_table_vpclogs` のクエリを実行します。クエリの `test_table_vpclogs` を独自のテーブルの名前で置き換えます。また、要件に応じて列の値やその他の変数を変更します。

指定された期間の最初の 100 個のアクセスログエントリを時系列順に返すには、次のようなクエリを実行します。

```
SELECT *
FROM test_table_vpclogs
WHERE day >= '2021/02/01' AND day < '2021/02/28'
ORDER BY day ASC
LIMIT 100
```

指定された期間に上位 10 個の HTTP パケットを受信したサーバーを表示するには、次のようなクエリを実行します。このクエリは、HTTPS ポート 443 で受信したパケット数をカウントし、送信先 IP アドレス別にグループ分けして、過去 1 週間の上位 10 エントリを返します。

```
SELECT SUM(packets) AS packetcount, 
       dstaddr
FROM test_table_vpclogs
WHERE dstport = 443
  AND day >= '2021/03/01'
  AND day < '2021/03/31'
GROUP BY dstaddr
ORDER BY packetcount DESC
LIMIT 10
```

指定された期間内に作成されたログを返すには、次のようなクエリを実行します。

```
SELECT interface_id,
       srcaddr,
       action,
       protocol,
       to_iso8601(from_unixtime(start)) AS start_time,
       to_iso8601(from_unixtime("end")) AS end_time
FROM test_table_vpclogs
WHERE DAY >= '2021/04/01'
  AND DAY < '2021/04/30'
```

指定された期間の送信元 IP アドレスのアクセスログを返すには、次のようなクエリを実行します。

```
SELECT *
FROM test_table_vpclogs
WHERE srcaddr = '10.117.1.22'
  AND day >= '2021/02/01'
  AND day < '2021/02/28'
```

すべての拒否された TCP 接続を一覧表示するには、次のようなクエリを実行します。

```
SELECT day,
       interface_id,
       srcaddr,
       action,
       protocol
FROM test_table_vpclogs
WHERE action = 'REJECT' AND protocol = 6 AND day >= '2021/02/01' AND day < '2021/02/28'
LIMIT 10
```

`10.117` で始まる IP アドレス範囲のアクセスログを返すには、次のようなクエリを実行します。

```
SELECT *
FROM test_table_vpclogs
WHERE split_part(srcaddr,'.', 1)='10'
  AND split_part(srcaddr,'.', 2) ='117'
```

特定の時間範囲内の送信先 IP アドレスのアクセスログを返すには、次のようなクエリを実行します。

```
SELECT *
FROM test_table_vpclogs
WHERE dstaddr = '10.0.1.14'
  AND day >= '2021/01/01'
  AND day < '2021/01/31'
```

# パーティション射影を使用して Apache Parquet 形式でフローログのテーブルを作成する
<a name="vpc-flow-logs-partition-projection-parquet-example"></a>

次の VPC フローログのパーティション射影 `CREATE TABLE` ステートメントは Apache Parquet 形式であり、Hive と互換性がなく、曜日ではなく時間と日付でパーティショニングされています。サンプルのテーブル名 `test_table_vpclogs_parquet` をそのテーブルの名前に置き換えます。Amazon VPC ログデータが含まれている Amazon S3 バケットを指定するように `LOCATION` 句を編集します。

```
CREATE EXTERNAL TABLE IF NOT EXISTS test_table_vpclogs_parquet (
  version int,
  account_id string,
  interface_id string,
  srcaddr string,
  dstaddr string,
  srcport int,
  dstport int,
  protocol bigint,
  packets bigint,
  bytes bigint,
  start bigint,
  `end` bigint,
  action string,
  log_status string,
  vpc_id string,
  subnet_id string,
  instance_id string,
  tcp_flags int,
  type string,
  pkt_srcaddr string,
  pkt_dstaddr string,
  az_id string,
  sublocation_type string,
  sublocation_id string,
  pkt_src_aws_service string,
  pkt_dst_aws_service string,
  flow_direction string,
  traffic_path int
)
PARTITIONED BY (region string, date string, hour string)
ROW FORMAT SERDE
'org.apache.hadoop.hive.ql.io.parquet.serde.ParquetHiveSerDe'
STORED AS INPUTFORMAT
'org.apache.hadoop.hive.ql.io.parquet.MapredParquetInputFormat'
OUTPUTFORMAT
'org.apache.hadoop.hive.ql.io.parquet.MapredParquetOutputFormat'
LOCATION 's3://amzn-s3-demo-bucket/prefix/AWSLogs/{account_id}/vpcflowlogs/'
TBLPROPERTIES (
"EXTERNAL"="true",
"skip.header.line.count" = "1",
"projection.enabled" = "true",
"projection.region.type" = "enum",
"projection.region.values" = "us-east-1,us-west-2,ap-south-1,eu-west-1",
"projection.date.type" = "date",
"projection.date.range" = "2021/01/01,NOW",
"projection.date.format" = "yyyy/MM/dd",
"projection.hour.type" = "integer",
"projection.hour.range" = "00,23",
"projection.hour.digits" = "2",
"storage.location.template" = "s3://amzn-s3-demo-bucket/prefix/AWSLogs/${account_id}/vpcflowlogs/${region}/${date}/${hour}"
)
```

# その他のリソース
<a name="query-examples-vpc-logs-additional-resources"></a>

Athena を使用して VPC フローログを分析する方法の詳細については、次の「AWS Big Data Blog」の記事を参照してください。
+ [ポイントアンドクリック Amazon Athena インテグレーションを使用した VPC フローログの分析](https://aws.amazon.com/blogs/networking-and-content-delivery/analyze-vpc-flow-logs-with-point-and-click-amazon-athena-integration/) 
+ [Amazon Athena および Quick を使用した VPC フローログの分析](https://aws.amazon.com/blogs/big-data/analyzing-vpc-flow-logs-using-amazon-athena-and-amazon-quicksight/)
+ [Apache Parquet 形式の VPC フローログでパフォーマンスを最適化し、ネットワーク分析のコストを削減する](https://aws.amazon.com/blogs/big-data/optimize-performance-and-reduce-costs-for-network-analytics-with-vpc-flow-logs-in-apache-parquet-format/)

# AWS WAF ログをクエリする
<a name="waf-logs"></a>

AWS WAF は、保護されたウェブアプリケーションがクライアントから受信する HTTP および HTTPS リクエストを監視して制御できるようにするウェブアプリケーションファイアウォールです。AWS WAF ウェブアクセスコントロールリスト (ACL) 内のルールを設定することにより、ウェブリクエストの処理方法を定義します。その後、ウェブアプリケーションにウェブ ACL を関連付けて保護します。AWS WAF で保護できるウェブアプリケーションリソースの例には、Amazon CloudFront ディストリビューション、Amazon API Gateway REST API、Application Load Balancers などがあります。AWS WAF の詳細については、「*AWS WAF デベロッパーガイド*」の「[AWS WAF](https://docs.aws.amazon.com/waf/latest/developerguide/waf-chapter.html)」を参照してください。

AWS WAF ログには、AWS WAF が AWS リソースからリクエストを受信した時間、このリクエストの詳細、各リクエストが適合したルールに対するアクションなど、ウェブ ACL によって分析されたトラフィックに関する情報が含まれます。

AWS WAF ウェブ ACL を設定して、複数の宛先のいずれかにログを発行し、そこでクエリを実行して表示できます。ウェブ ACL ログの設定および AWS WAF ログの内容の詳細については、「*AWS WAF デベロッパーガイド*」の「[AWS WAF ウェブ ACL トラフィックのログ](https://docs.aws.amazon.com/waf/latest/developerguide/logging.html)」を参照してください。

Athena を利用して脅威検出と潜在的なセキュリティ攻撃に関するインサイトを得るために AWS WAF ログを分析する方法については、AWS ネットワークとコンテンツ配信のブログ記事「[How to use Amazon Athena queries to analyze AWS WAF logs and provide the visibility needed for threat detection](https://aws.amazon.com/blogs/networking-and-content-delivery/how-to-use-amazon-athena-queries-to-analyze-aws-waf-logs-and-provide-the-visibility-needed-for-threat-detection/)」を参照してください。

AWS WAF ログを中央データレイクリポジトリに集約して、それらを Athena でクエリする方法の例については、「AWS ビッグデータブログ」のブログ記事「[Analyzing AWS WAF logs with OpenSearch Service, Amazon Athena, and Quick](https://aws.amazon.com/blogs/big-data/analyzing-aws-waf-logs-with-amazon-es-amazon-athena-and-amazon-quicksight/)」を参照してください。

このトピックでは、パーティション射影、手動パーティショニング、およびパーティショニングを使用しない `CREATE TABLE` ステートメントの例を示します。

**注記**  
このトピックの `CREATE TABLE` ステートメントは、v1 および v2 AWS WAF ログの両方に使用できます。v1 では、`webaclid` フィールドに ID が含まれます。v2 では、`webaclid` フィールドに完全な ARN が含まれます。ここでの `CREATE TABLE` ステートメントは、`string` データ型を使用して、アグノスティックにこのコンテンツを取り扱います。

**Topics**
+ [パーティション射影を使用して Athena で AWS WAF S3 ログ用テーブルを作成する](create-waf-table-partition-projection.md)
+ [手動パーティショニングを使用して Athena で AWS WAF S3 ログ用テーブルを作成する](create-waf-table-manual-partition.md)
+ [パーティショニングなしで AWS WAF ログのテーブルを作成する](create-waf-table.md)
+ [AWS WAF ログのクエリ例](query-examples-waf-logs.md)

# パーティション射影を使用して Athena で AWS WAF S3 ログ用テーブルを作成する
<a name="create-waf-table-partition-projection"></a>

AWS WAF ログには、パーティションスキームを事前に指定できる既知の構造があるため、Athena の[パーティション射影](partition-projection.md)機能を使用することで、クエリランタイムを短縮し、パーティション管理を自動化することが可能です。新しいデータが追加されると、パーティション射影は新しいパーティションを自動で追加します。このため、`ALTER TABLE ADD PARTITION` を使用してパーティションを手動で追加する必要がなくなります。

次の `CREATE TABLE` ステートメント例では、指定された日付から現在までの 4 つの異なる AWS WAF リージョンの AWS ログで、パーティション射影を自動的に使用しています。この例の `PARTITION BY` 句は地域と日付でパーティショニングしますが、要件に応じてこれを変更できます。ログ出力と一致するように、必要に応じてフィールドを変更します。`LOCATION` および `storage.location.template` 句では、*amzn-s3-demo-bucket* と *AWS\$1ACCOUNT\$1NUMBER* の各プレースホルダーを AWS WAF ログの Amazon S3 バケットの場所を特定する値に置き換えます。`projection.day.range` では、*2021*/*01*/*01* を使用を開始する日に置き換えます。クエリが正常に実行されると、テーブルをクエリできます。パーティションをロードするのに、`ALTER TABLE ADD PARTITION` を実行する必要はありません。

```
CREATE EXTERNAL TABLE `waf_logs_partition_projection`(
  `timestamp` bigint, 
  `formatversion` int, 
  `webaclid` string, 
  `terminatingruleid` string, 
  `terminatingruletype` string, 
  `action` string, 
  `terminatingrulematchdetails` array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>, 
  `httpsourcename` string, 
  `httpsourceid` string, 
  `rulegrouplist` array<struct<rulegroupid:string,terminatingrule:struct<ruleid:string,action:string,rulematchdetails:array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>>,nonterminatingmatchingrules:array<struct<ruleid:string,action:string,overriddenaction:string,rulematchdetails:array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>,challengeresponse:struct<responsecode:string,solvetimestamp:string>,captcharesponse:struct<responsecode:string,solvetimestamp:string>>>,excludedrules:string>>, 
  `ratebasedrulelist` array<struct<ratebasedruleid:string,limitkey:string,maxrateallowed:int>>, 
  `nonterminatingmatchingrules` array<struct<ruleid:string,action:string,rulematchdetails:array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>,challengeresponse:struct<responsecode:string,solvetimestamp:string>,captcharesponse:struct<responsecode:string,solvetimestamp:string>>>, 
  `requestheadersinserted` array<struct<name:string,value:string>>, 
  `responsecodesent` string, 
  `httprequest` struct<clientip:string,country:string,headers:array<struct<name:string,value:string>>,uri:string,args:string,httpversion:string,httpmethod:string,requestid:string,fragment:string,scheme:string,host:string>,
  `labels` array<struct<name:string>>, 
  `captcharesponse` struct<responsecode:string,solvetimestamp:string,failurereason:string>, 
  `challengeresponse` struct<responsecode:string,solvetimestamp:string,failurereason:string>, 
  `ja3fingerprint` string, 
  `ja4fingerprint` string, 
  `oversizefields` string, 
  `requestbodysize` int, 
  `requestbodysizeinspectedbywaf` int)
  PARTITIONED BY ( 
   `log_time` string)
ROW FORMAT SERDE 
  'org.openx.data.jsonserde.JsonSerDe' 
STORED AS INPUTFORMAT 
  'org.apache.hadoop.mapred.TextInputFormat' 
OUTPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION
  's3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_NUMBER/WAFLogs/cloudfront/testui/'
TBLPROPERTIES (
 'projection.enabled'='true',
  'projection.log_time.format'='yyyy/MM/dd/HH/mm',
  'projection.log_time.interval'='1',
  'projection.log_time.interval.unit'='minutes',
  'projection.log_time.range'='2025/01/01/00/00,NOW',
  'projection.log_time.type'='date',
  'storage.location.template'='s3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_NUMBER/WAFLogs/cloudfront/testui/${log_time}')
```

**注記**  
この例にある `LOCATION` 句のパスの形式は標準ですが、実装した AWS WAF 設定によって異なる場合があります。例えば、次の例の AWS WAF ログパスは CloudFront 分散用です。  

```
s3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_NUMBER/WAFLogs/cloudfront/cloudfronyt/2025/01/01/00/00/
```
AWS WAF ログテーブルの作成またはクエリ中に問題が発生した場合は、ログデータの場所を確定するか、[サポート までお問い合わせください](https://console.aws.amazon.com/support/home/)。

パーティション射影の詳細については、「[Amazon Athena でパーティション射影を使用する](partition-projection.md)」を参照してください。

# 手動パーティショニングを使用して Athena で AWS WAF S3 ログ用テーブルを作成する
<a name="create-waf-table-manual-partition"></a>

このセクションでは、手動パーティショニングを使用して AWS WAF ログのテーブルを作成する方法について説明します。

`LOCATION` および `storage.location.template` 句では、*amzn-s3-demo-bucket* と *AWS\$1ACCOUNT\$1NUMBER* の各プレースホルダーを AWS WAF ログの Amazon S3 バケットの場所を特定する値に置き換えます。

```
CREATE EXTERNAL TABLE `waf_logs_manual_partition`(
  `timestamp` bigint, 
  `formatversion` int, 
  `webaclid` string, 
  `terminatingruleid` string, 
  `terminatingruletype` string, 
  `action` string, 
  `terminatingrulematchdetails` array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>, 
  `httpsourcename` string, 
  `httpsourceid` string, 
  `rulegrouplist` array<struct<rulegroupid:string,terminatingrule:struct<ruleid:string,action:string,rulematchdetails:array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>>,nonterminatingmatchingrules:array<struct<ruleid:string,action:string,overriddenaction:string,rulematchdetails:array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>,challengeresponse:struct<responsecode:string,solvetimestamp:string>,captcharesponse:struct<responsecode:string,solvetimestamp:string>>>,excludedrules:string>>, 
  `ratebasedrulelist` array<struct<ratebasedruleid:string,limitkey:string,maxrateallowed:int>>, 
  `nonterminatingmatchingrules` array<struct<ruleid:string,action:string,rulematchdetails:array<struct<conditiontype:string,sensitivitylevel:string,location:string,matcheddata:array<string>>>,challengeresponse:struct<responsecode:string,solvetimestamp:string>,captcharesponse:struct<responsecode:string,solvetimestamp:string>>>, 
  `requestheadersinserted` array<struct<name:string,value:string>>, 
  `responsecodesent` string, 
  `httprequest` struct<clientip:string,country:string,headers:array<struct<name:string,value:string>>,uri:string,args:string,httpversion:string,httpmethod:string,requestid:string,fragment:string,scheme:string,host:string>, 
  `labels` array<struct<name:string>>, 
  `captcharesponse` struct<responsecode:string,solvetimestamp:string,failurereason:string>, 
  `challengeresponse` struct<responsecode:string,solvetimestamp:string,failurereason:string>, 
  `ja3fingerprint` string, 
  `ja4fingerprint` string, 
  `oversizefields` string, 
  `requestbodysize` int, 
  `requestbodysizeinspectedbywaf` int)
  PARTITIONED BY ( `year` string, `month` string, `day` string, `hour` string, `min` string)
ROW FORMAT SERDE 
  'org.openx.data.jsonserde.JsonSerDe' 
STORED AS INPUTFORMAT 
  'org.apache.hadoop.mapred.TextInputFormat' 
OUTPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
LOCATION
  's3://amzn-s3-demo-bucket/AWSLogs/AWS_ACCOUNT_NUMBER/WAFLogs/cloudfront/webacl/'
```

# パーティショニングなしで AWS WAF ログのテーブルを作成する
<a name="create-waf-table"></a>

このセクションでは、パーティショニングまたはパーティション射影を使用せずに AWS WAF ログのテーブルを作成する方法について説明します。

**注記**  
パフォーマンスおよびコスト上の理由により、クエリにパーティション化されていないスキーマを使用することは推奨されません。詳細については、「AWS Big Data Blog」の「[Amazon Athena のパフォーマンスチューニング Tips トップ 10](https://aws.amazon.com/blogs/big-data/top-10-performance-tuning-tips-for-amazon-athena/)」を参照してください。

**AWS WAF テーブルを作成するには**

1. 次の DDL ステートメントをコピーして Athena コンソール内に貼り付けます。ログ出力と一致するように、必要に応じてフィールドを変更します。ログを保存するバケットに対応するように Amazon S3 バケットの `LOCATION` を変更します。

   このクエリでは、[OpenX JSON SerDe](openx-json-serde.md) を使用します。
**注記**  
SerDe では、各 JSON ドキュメントが、レコード内のフィールドを区切る行終端文字なしの、1 行のテキストに収まっていることを想定しています。JSON テキストがプリティプリント形式の場合、テーブルを作成した後にクエリを実行しようとすると、以下のようなエラーメッセージが表示される場合があります。「HIVE\$1CURSOR\$1ERROR: Row is not a valid JSON Object」、または「HIVE\$1CURSOR\$1ERROR: JsonParseException: Unexpected end-of-input: expected close marker for OBJECT」。詳細については、GitHub の OpenX SerDe のドキュメントで「[JSON Data Files](https://github.com/rcongiu/Hive-JSON-Serde#json-data-files)」(JSON データファイル) を参照してください。

   ```
   CREATE EXTERNAL TABLE `waf_logs`(
     `timestamp` bigint,
     `formatversion` int,
     `webaclid` string,
     `terminatingruleid` string,
     `terminatingruletype` string,
     `action` string,
     `terminatingrulematchdetails` array <
                                       struct <
                                           conditiontype: string,
                                           sensitivitylevel: string,
                                           location: string,
                                           matcheddata: array < string >
                                             >
                                        >,
     `httpsourcename` string,
     `httpsourceid` string,
     `rulegrouplist` array <
                         struct <
                             rulegroupid: string,
                             terminatingrule: struct <
                                                 ruleid: string,
                                                 action: string,
                                                 rulematchdetails: array <
                                                                      struct <
                                                                          conditiontype: string,
                                                                          sensitivitylevel: string,
                                                                          location: string,
                                                                          matcheddata: array < string >
                                                                             >
                                                                       >
                                                   >,
                             nonterminatingmatchingrules: array <
                                                                 struct <
                                                                     ruleid: string,
                                                                     action: string,
                                                                     overriddenaction: string,
                                                                     rulematchdetails: array <
                                                                                          struct <
                                                                                              conditiontype: string,
                                                                                              sensitivitylevel: string,
                                                                                              location: string,
                                                                                              matcheddata: array < string >
                                                                                                 >
                                                                      >,
                                                                     challengeresponse: struct <
                                                                               responsecode: string,
                                                                               solvetimestamp: string
                                                                                 >,
                                                                     captcharesponse: struct <
                                                                               responsecode: string,
                                                                               solvetimestamp: string
                                                                                 >
                                                                       >
                                                                >,
                             excludedrules: string
                               >
                          >,
   `ratebasedrulelist` array <
                            struct <
                                ratebasedruleid: string,
                                limitkey: string,
                                maxrateallowed: int
                                  >
                             >,
     `nonterminatingmatchingrules` array <
                                       struct <
                                           ruleid: string,
                                           action: string,
                                           rulematchdetails: array <
                                                                struct <
                                                                    conditiontype: string,
                                                                    sensitivitylevel: string,
                                                                    location: string,
                                                                    matcheddata: array < string >
                                                                       >
                                                                >,
                                           challengeresponse: struct <
                                                               responsecode: string,
                                                               solvetimestamp: string
                                                                >,
                                           captcharesponse: struct <
                                                               responsecode: string,
                                                               solvetimestamp: string
                                                                >
                                             >
                                        >,
     `requestheadersinserted` array <
                                   struct <
                                       name: string,
                                       value: string
                                         >
                                    >,
     `responsecodesent` string,
     `httprequest` struct <
                       clientip: string,
                       country: string,
                       headers: array <
                                   struct <
                                       name: string,
                                       value: string
                                         >
                                    >,
                       uri: string,
                       args: string,
                       httpversion: string,
                       httpmethod: string,
                       requestid: string
                         >,
     `labels` array <
                  struct <
                      name: string
                        >
                   >,
     `captcharesponse` struct <
                           responsecode: string,
                           solvetimestamp: string,
                           failureReason: string
                             >,
     `challengeresponse` struct <
                           responsecode: string,
                           solvetimestamp: string,
                           failureReason: string
                           >,
     `ja3Fingerprint` string,
     `oversizefields` string,
     `requestbodysize` int,
     `requestbodysizeinspectedbywaf` int
   )
   ROW FORMAT SERDE 'org.openx.data.jsonserde.JsonSerDe'
   STORED AS INPUTFORMAT 'org.apache.hadoop.mapred.TextInputFormat'
   OUTPUTFORMAT 'org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat'
   LOCATION 's3://amzn-s3-demo-bucket/prefix/'
   ```

1. Athena コンソールのクエリエディタで `CREATE EXTERNAL TABLE` ステートメントを実行します。これで `waf_logs` テーブルが登録され、その中のデータを Athena からのクエリに使用できるようになります。

# AWS WAF ログのクエリ例
<a name="query-examples-waf-logs"></a>

このセクションの多くのクエリ例では、前に作成したパーティション射影テーブルを使用します。また、要件に応じて例のテーブル名、列の値、その他の変数を変更します。クエリのパフォーマンスを改善してコストを削減するには、フィルター条件にパーティション列を追加します。

**Topics**
+ [カウントリファラー、IP アドレス、一致ルール](query-examples-waf-logs-count.md)
+ [日付と時刻を使用してクエリする](query-examples-waf-logs-date-time.md)
+ [ブロックされたリクエストまたはアドレスをクエリする](query-examples-waf-logs-blocked-requests.md)

# カウントリファラー、IP アドレス、一致ルール
<a name="query-examples-waf-logs-count"></a>

このセクションの例では、対象となるログ項目のカウントをクエリします。
+ [Count the number of referrers that contain a specified term](#waf-example-count-referrers-with-specified-term)
+ [Count all matched IP addresses in the last 10 days that have matched excluded rules](#waf-example-count-matched-ip-addresses)
+ [Group all counted managed rules by the number of times matched](#waf-example-group-managed-rules-by-times-matched)
+ [Group all counted custom rules by number of times matched](#waf-example-group-custom-rules-by-times-matched)

**Example – 指定された用語を含むリファラーの数を計上する**  
次のクエリは、指定された日付範囲内での「amazon」という用語を含むリファラーの数を計上します。  

```
WITH test_dataset AS 
  (SELECT header FROM waf_logs
    CROSS JOIN UNNEST(httprequest.headers) AS t(header) WHERE "date" >= '2021/03/01'
    AND "date" < '2021/03/31')
SELECT COUNT(*) referer_count 
FROM test_dataset 
WHERE LOWER(header.name)='referer' AND header.value LIKE '%amazon%'
```

**Example – 一致する除外ルールがある、過去 10 日間のすべての一致した IP アドレスを計上する**  
次のクエリは、IP アドレスがルールグループ内の除外ルールに一致した過去 10 日間の回数を計上します。  

```
WITH test_dataset AS 
  (SELECT * FROM waf_logs 
    CROSS JOIN UNNEST(rulegrouplist) AS t(allrulegroups))
SELECT 
  COUNT(*) AS count, 
  "httprequest"."clientip", 
  "allrulegroups"."excludedrules",
  "allrulegroups"."ruleGroupId"
FROM test_dataset 
WHERE allrulegroups.excludedrules IS NOT NULL AND from_unixtime(timestamp/1000) > now() - interval '10' day
GROUP BY "httprequest"."clientip", "allrulegroups"."ruleGroupId", "allrulegroups"."excludedrules"
ORDER BY count DESC
```

**Example – カウントされたすべてのマネージドルールをマッチした回数でグループ化する**  
2022 年 10 月 27 日より前にウェブ ACL 設定でルールグループのルールアクションをカウントに設定した場合、AWS WAF はウェブ ACL JSON 内のオーバーライドを `excludedRules` として保存しました。これで、ルールをカウントにオーバーライドする JSON 設定が `ruleActionOverrides` 設定に追加されました。詳しくは、「*AWS WAF デベロッパーガイド*」の「[ルールグループのアクションオーバーライド](https://docs.aws.amazon.com/waf/latest/developerguide/web-acl-rule-group-override-options.html)」をご覧ください。新しいログ構造からカウントモードのマネージドルールを抽出するには、次の例のように、`excludedRules` フィールドの代わりに `ruleGroupList` セクションの `nonTerminatingMatchingRules` をクエリします。  

```
SELECT
 count(*) AS count,
 httpsourceid,
 httprequest.clientip,
 t.rulegroupid, 
 t.nonTerminatingMatchingRules
FROM "waf_logs" 
CROSS JOIN UNNEST(rulegrouplist) AS t(t) 
WHERE action <> 'BLOCK' AND cardinality(t.nonTerminatingMatchingRules) > 0 
GROUP BY t.nonTerminatingMatchingRules, action, httpsourceid, httprequest.clientip, t.rulegroupid 
ORDER BY "count" DESC 
Limit 50
```

**Example – カウントされたすべてのカスタムルールをマッチした回数でグループ化する**  
次のクエリは、カウントされたすべてのカスタムルールをマッチした回数でグループ化します。  

```
SELECT
  count(*) AS count,
         httpsourceid,
         httprequest.clientip,
         t.ruleid,
         t.action
FROM "waf_logs" 
CROSS JOIN UNNEST(nonterminatingmatchingrules) AS t(t) 
WHERE action <> 'BLOCK' AND cardinality(nonTerminatingMatchingRules) > 0 
GROUP BY t.ruleid, t.action, httpsourceid, httprequest.clientip 
ORDER BY "count" DESC
Limit 50
```

カスタムルールとマネージドルールグループのログの場所については、「*AWS WAF デベロッパーガイド*」の「[モニタリングとチューニング](https://docs.aws.amazon.com/waf/latest/developerguide/web-acl-testing-activities.html)」を参照してください。

# 日付と時刻を使用してクエリする
<a name="query-examples-waf-logs-date-time"></a>

このセクションの例には、日付と時刻の値を使用するクエリが含まれています。
+ [Return the timestamp field in human-readable ISO 8601 format](#waf-example-return-human-readable-timestamp)
+ [Return records from the last 24 hours](#waf-example-return-records-last-24-hours)
+ [Return records for a specified date range and IP address](#waf-example-return-records-date-range-and-ip)
+ [For a specified date range, count the number of IP addresses in five minute intervals](#waf-example-count-ip-addresses-in-date-range)
+ [Count the number of X-Forwarded-For IP in the last 10 days](#waf-example-count-x-forwarded-for-ip)

**Example – 人が読み込み可能な ISO 8601 形式のタイムスタンプフィールドを返す**  
次のクエリは、`from_unixtime` および `to_iso8601` 関数を使用して、`timestamp` フィールドを人が読み込み可能な ISO 8601 形式 (例えば、`1576280412771` ではなく `2019-12-13T23:40:12.000Z` ) で返します。このクエリは、HTTP ソース名、ソース ID、およびリクエストも返します。  

```
SELECT to_iso8601(from_unixtime(timestamp / 1000)) as time_ISO_8601,
       httpsourcename,
       httpsourceid,
       httprequest
FROM waf_logs
LIMIT 10;
```

**Example – 過去 24 時間のレコードを返す**  
次のクエリは、`WHERE` 句でフィルターを使用して、過去 24 時間のレコードに関する HTTP ソース名、HTTP ソース ID、および HTTP リクエストフィールドを返します。  

```
SELECT to_iso8601(from_unixtime(timestamp/1000)) AS time_ISO_8601, 
       httpsourcename, 
       httpsourceid, 
       httprequest 
FROM waf_logs
WHERE from_unixtime(timestamp/1000) > now() - interval '1' day
LIMIT 10;
```

**Example – 指定された日付範囲と IP アドレスのレコードを返す**  
次のクエリは、指定されたクライアント IP アドレスの指定された日付範囲内のレコードをリストします。  

```
SELECT * 
FROM waf_logs 
WHERE httprequest.clientip='53.21.198.66' AND "date" >= '2021/03/01' AND "date" < '2021/03/31'
```

**Example – 指定された日付範囲について、5 分間隔で IP アドレスの数を計上する**  
次のクエリは、特定の日付範囲について、5 分間隔で IP アドレスの数を計上します。  

```
WITH test_dataset AS 
  (SELECT 
     format_datetime(from_unixtime((timestamp/1000) - ((minute(from_unixtime(timestamp / 1000))%5) * 60)),'yyyy-MM-dd HH:mm') AS five_minutes_ts,
     "httprequest"."clientip" 
     FROM waf_logs 
     WHERE "date" >= '2021/03/01' AND "date" < '2021/03/31')
SELECT five_minutes_ts,"clientip",count(*) ip_count 
FROM test_dataset 
GROUP BY five_minutes_ts,"clientip"
```

**Example – 過去 10 日間の X-Forwarded-For IP の数をカウントする**  
次のクエリは、リクエストヘッダーをフィルタリングし、過去 10 日間の X-Forwarded-For IP の数をカウントします。  

```
WITH test_dataset AS
  (SELECT header
   FROM waf_logs
   CROSS JOIN UNNEST (httprequest.headers) AS t(header)
   WHERE from_unixtime("timestamp"/1000) > now() - interval '10' DAY) 
SELECT header.value AS ip,
       count(*) AS COUNT 
FROM test_dataset 
WHERE header.name='X-Forwarded-For' 
GROUP BY header.value 
ORDER BY COUNT DESC
```

日付関数と時刻関数の詳細については、Trino ドキュメントの「[Date and Time Functions and Operators](https://trino.io/docs/current/functions/datetime.html)」(日付と時刻の関数と演算子) を参照してください。

# ブロックされたリクエストまたはアドレスをクエリする
<a name="query-examples-waf-logs-blocked-requests"></a>

このセクションの例では、ブロックされたリクエストまたはアドレスをクエリします。
+ [Extract the top 100 IP addresses blocked by a specified rule type](#waf-example-extract-top-100-blocked-ip-by-rule)
+ [Count the number of times a request from a specified country has been blocked](#waf-example-count-request-blocks-from-country)
+ [Count the number of times a request has been blocked, grouping by specific attributes](#waf-example-count-request-blocks-by-attribute)
+ [Count the number of times a specific terminating rule ID has been matched](#waf-example-count-terminating-rule-id-matches)
+ [Retrieve the top 100 IP addresses blocked during a specified date range](#waf-example-top-100-ip-addresses-blocked-for-date-range)

**Example – 指定されたルールタイプによってブロックされた上位 100 個の IP アドレスを抽出する**  
次のクエリは、指定した日付範囲内で `RATE_BASED` 終了ルールによってブロックされた上位 100 個の IP アドレスを抽出し、計上します。  

```
SELECT COUNT(httpRequest.clientIp) as count,
httpRequest.clientIp
FROM waf_logs
WHERE terminatingruletype='RATE_BASED' AND action='BLOCK' and "date" >= '2021/03/01'
AND "date" < '2021/03/31'
GROUP BY httpRequest.clientIp
ORDER BY count DESC
LIMIT 100
```

**Example – 指定された国からのリクエストがブロックされた回数を計上する**  
次のクエリは、アイルランド (IE) に属し、`RATE_BASED` 終了ルールによってブロックされた IP アドレスからリクエストが到着した回数を数えます。  

```
SELECT 
  COUNT(httpRequest.country) as count, 
  httpRequest.country 
FROM waf_logs
WHERE 
  terminatingruletype='RATE_BASED' AND 
  httpRequest.country='IE'
GROUP BY httpRequest.country
ORDER BY count
LIMIT 100;
```

**Example – リクエストがブロックされた回数を計上し、特定の属性でグループ化する**  
次のクエリは、リクエストがブロックされた回数をカウントし、結果を WebACL、RuleId、ClientIP、および HTTP リクエスト URI によってグループ化します。  

```
SELECT 
  COUNT(*) AS count,
  webaclid,
  terminatingruleid,
  httprequest.clientip,
  httprequest.uri
FROM waf_logs
WHERE action='BLOCK'
GROUP BY webaclid, terminatingruleid, httprequest.clientip, httprequest.uri
ORDER BY count DESC
LIMIT 100;
```

**Example – 特定の終了ルール ID が一致した回数を計上する**  
次のクエリは、特定の終了ルール ID が (`WHERE terminatingruleid='e9dd190d-7a43-4c06-bcea-409613d9506e'`) に一致した回数を計上します。その結果を WebACL、Action、ClientIP、および HTTP Request URI によってグループ化します。  

```
SELECT 
  COUNT(*) AS count,
  webaclid,
  action,
  httprequest.clientip,
  httprequest.uri
FROM waf_logs
WHERE terminatingruleid='e9dd190d-7a43-4c06-bcea-409613d9506e'
GROUP BY webaclid, action, httprequest.clientip, httprequest.uri
ORDER BY count DESC
LIMIT 100;
```

**Example – 指定した日付範囲内でブロックされた上位 100 個の IP アドレスを取得する**  
次のクエリは、指定された日付範囲内でブロックされた上位 100 個の IP アドレスを抽出します。このクエリは、IP アドレスがブロックされた回数もリストします。  

```
SELECT "httprequest"."clientip", "count"(*) "ipcount", "httprequest"."country"
FROM waf_logs
WHERE "action" = 'BLOCK' and "date" >= '2021/03/01'
AND "date" < '2021/03/31'
GROUP BY "httprequest"."clientip", "httprequest"."country"
ORDER BY "ipcount" DESC limit 100
```

Amazon S3 のクエリについては、以下のトピックを参照してください。
+ AWS ナレッジセンターの「[Athena を使用して Amazon S3 サーバーのアクセスログを分析するにはどうすればよいですか?](https://aws.amazon.com/premiumsupport/knowledge-center/analyze-logs-athena/)」
+ 「Amazon Simple Storage Service ユーザーガイド」の「[Amazon Athena を使用してリクエストのアクセスログをクエリする](https://docs.aws.amazon.com/AmazonS3/latest/dev/using-s3-access-logs-to-identify-requests.html#querying-s3-access-logs-for-requests)」
+ Amazon Simple Storage Service ユーザーガイドの「[AWS CloudTrail を使用した Amazon S3 リクエストの識別](https://docs.aws.amazon.com/AmazonS3/latest/dev/cloudtrail-request-identification.html)」