2013年3月20日水曜日

S3ってなんじゃ?(S3のログファイルを別アカウントでダウンロード)

S3でWEBホスティングをする場合、アクセスログを別のバケットに出力することができます。
そのS3のアクセスログに別のアカウントからアクセスしてダウンロードなどをしたい場合があります。
今回はその方法を紹介します。

S3のアクセスログを設定にするには、AWSコンソールでS3のバケットの設定をします。


Webホスティングの設定をしていると、上図のように設定することで、memorycraft-logのlogs/以下にこのバケットのアクセスログが出力されます。



このログファイルの一覧をSDK(PHP)を使って別アカウントから取得してみます。
$s3 = new AmazonS3(array('key'=>'別アカウントのアクセスキー','secret'=>'別アカウントのシークレットキー'));
$s3->set_region(AmazonS3::REGION_APAC_NE1);
$objects = $s3->get_object_list($bucket);
echo "objects=".print_r($objects, true);


権限がないため取得できないため、出力もされません
objects=


また、ログファイルを別アカウントでダウンロードしようとすると、、、、
$s3 = new AmazonS3(array('key'=>'別アカウントのアクセスキー','secret'=>'別アカウントのシークレットキー'));
$s3->set_region(AmazonS3::REGION_APAC_NE1);
$res = $s3->get_object('memorycraft-log', 'logs/2013-03-17-05-34-13-347E8EF10D93460B');
print_r($res);


権限がないためアクセスできません。
CFResponse Object
(
    [header] => Array
        (
            [x-amz-request-id] => 8702DF59DF4D6E86
            [x-amz-id-2] => G/Vvv2NzYqTDbI3WAUHgtp2GCqyBQdMoMaivWNii2utRXezRJUxD/hvCOQjBTCGw
            [content-type] => application/xml
            [transfer-encoding] => chunked
            [date] => Tue, 19 Mar 2013 17:44:30 GMT
            [server] => AmazonS3
            [_info] => Array
                (
                    [url] => https://memorycraft-log.s3-ap-northeast-1.amazonaws.com/logs/2013-03-17-05-34-13-347E8EF10D93460B
                    [content_type] => application/xml
                    [http_code] => 403
                    [header_size] => 254
                    [request_size] => 751
                    [filetime] => -1
                    [ssl_verify_result] => 0
                    [redirect_count] => 0
                    [total_time] => 0.644282
                    [namelookup_time] => 0.551464
                    [connect_time] => 0.551971
                    [pretransfer_time] => 0.615103
                    [size_upload] => 0
                    [size_download] => 231
                    [speed_download] => 358
                    [speed_upload] => 0
                    [download_content_length] => -1
                    [upload_content_length] => 0
                    [starttransfer_time] => 0.644058
                    [redirect_time] => 0
                    [certinfo] => Array
                        (
                        )

                    [primary_ip] => 27.0.1.206
                    [redirect_url] => 
                    [method] => GET
                )

            [x-aws-request-url] => https://memorycraft-log.s3-ap-northeast-1.amazonaws.com/logs/2013-03-17-05-34-13-347E8EF10D93460B
            [x-aws-redirects] => 0
            [x-aws-stringtosign] => GET

application/x-www-form-urlencoded
Tue, 19 Mar 2013 17:44:30 GMT
/memorycraft-log/logs/2013-03-17-05-34-13-347E8EF10D93460B
            [x-aws-requestheaders] => Array
                (
                    [Content-Type] => application/x-www-form-urlencoded
                    [Date] => Tue, 19 Mar 2013 17:44:30 GMT
                    [Authorization] => AWS XXXXXXXXXXXXXXXXXX:UocmEFK0Cv4YveXulElQxR2J2cw=
                    [Expect] => 
                )

        )

    [body] => <?xml version="1.0" encoding="UTF-8"?>
<Error><Code>AccessDenied</Code><Message>Access Denied</Message><RequestId>8702DF59DF4D6E86</RequestId><HostId>G/Vvv2NzYqTDbI3WAUHgtp2GCqyBQdMoMaivWNii2utRXezRJUxD/hvCOQjBTCGw</HostId></Error>
    [status] => 403
)



ここで、現状のアクセス権限をみてみます。
バケットは以下のような設定です。
  • memorycraft(バケットオーナー):フルコントロール
  • LogDelivery(AWSのログ出力ユーザー):更新、権限チェック




また、ログファイル自体は以下のようになっています。
  • memorycraft(バケットオーナー):フルコントロール
  • s3-log-service(ファイルオーナー):フルコントロール




このように、通常だとAWSのログサービスとバケットオーナーにしか権限が与えられていないためアクセスできません。


ここで、バケットにSDKから権限を設定してみます。
$target = 'memorycraft-log';
$owner_canonical_id = 'オーナーの標準ユーザーID';
$other_canonical_id = '別アカウントの標準ユーザーID';
$s3 = new AmazonS3(array('key'=>'オーナーのアクセスキー','secret'=>'オーナーのシークレットキー'));
$s3->set_region(AmazonS3::REGION_APAC_NE1);

$res = $s3->set_bucket_acl($target, array(
  array('id' => AmazonS3::USERS_LOGGING,     'permission' => AmazonS3::GRANT_READ_ACP),
  array('id' => AmazonS3::USERS_LOGGING,     'permission' => AmazonS3::GRANT_WRITE),
  array('id' => $other_canonical_id,         'permission' => AmazonS3::GRANT_FULL_CONTROL),
  array('id' => $owner_canonical_id,         'permission' => AmazonS3::GRANT_FULL_CONTROL),
));

ここでいう標準ユーザーIDは、canonical_idとも言い、S3でのリソース共有に使用されるAWSアカウントに紐づく識別子です。標準ユーザーIDはアカウントのセキュリティページで確認できます。



 設定が完了すると、AWSコンソール上では以下のように権限が追加されたことが確認できます。




一覧取得とダウンロードを再度試してみます。

ファイルの一覧はできるようになりました。
objects=Array
(
    [0] => logs/
    [1] => logs/2013-03-17-02-33-50-04A9653054E658C0
    [2] => logs/2013-03-17-02-34-38-B68F986342D3F643
    [3] => logs/2013-03-17-02-37-03-633F736726FEDD7D
    [4] => logs/2013-03-17-03-15-48-4930EA30E66582CB
    [5] => logs/2013-03-17-03-15-49-29960D2BF338C203
    [6] => logs/2013-03-17-03-16-26-ED6062BA31A1B490
    [7] => logs/2013-03-17-05-16-45-99184D52B11E91BA
    [8] => logs/2013-03-17-05-16-58-ADD438AA47F74064
    [9] => logs/2013-03-17-05-29-26-D7BF5ECA4A0EB11C
    [10] => logs/2013-03-17-05-29-56-32C233B0252FF726
    [11] => logs/2013-03-17-05-34-13-347E8EF10D93460B
    [12] => logs/2013-03-17-05-35-02-65E964A6CE7F2809
    [13] => logs/2013-03-17-05-38-17-3C15C22739B25B64
    [14] => logs/2013-03-17-14-29-27-CE3C5D978D0410EC
    [15] => logs/2013-03-18-02-17-28-C2CA7570ADE47218
    [16] => logs/2013-03-19-15-16-34-97BE8A99E16EAB77
    [17] => logs/2013-03-19-15-16-39-80209A13C1DD677A
    [18] => logs/2013-03-19-15-17-03-551FB7D0F64B54AE
    [19] => logs/2013-03-19-15-30-00-3108CB5D1133380D
    [20] => logs/2013-03-19-15-32-53-7866E864159240D4
    [21] => logs/2013-03-19-15-33-15-B5E022E930A4DE0F
    [22] => logs/2013-03-19-15-36-45-F8194516221FF1F4
    [23] => logs/2013-03-19-15-37-26-E8855A5E344B083F
    [24] => logs/2013-03-19-17-15-41-444231C9F7F6FD69
    [25] => logs/2013-03-19-17-16-07-1FE5A409A6EEE3F3
    [26] => logs/2013-03-19-17-16-40-9D477C0727E9CF9F
    [27] => logs/2013-03-19-17-34-22-AB7B385D4C73382E
    [28] => logs/2013-03-19-17-42-05-69E17011ED7FEC05
    [29] => logs/2013-03-19-19-15-26-C806C3AB6A82BABE
    [30] => logs/2013-03-19-19-15-51-C75A28CBEA846E35
    [31] => logs/2013-03-19-19-15-59-01AD1F375E4639C3
    [32] => logs/2013-03-19-19-29-22-573E6302C719D044
    [33] => logs/2013-03-19-19-32-06-6724AB9B33D97F52
    [34] => logs/2013-03-19-19-34-13-60F916D79985BDF0
    [35] => logs/2013-03-19-19-34-37-6A6430488AEB5195
    [36] => logs/2013-03-19-19-38-02-29AF737531B69E29
)


しかしダウンロードはできません。
CFResponse Object
(
    [header] => Array
        (
            [x-amz-request-id] => C6D3DB10776F16FA
            [x-amz-id-2] => owcKsbILBrXmdTdu8XG81Rpe2ozrZmgOniQz5dUlUzH2b5c6TVVg3yEwue8q+QqI
            [content-type] => application/xml
            [transfer-encoding] => chunked
            [date] => Tue, 19 Mar 2013 20:03:25 GMT
            [server] => AmazonS3
            [_info] => Array
                (
                    [url] => https://memorycraft-log.s3-ap-northeast-1.amazonaws.com/logs/2013-03-17-05-34-13-347E8EF10D93460B
                    [content_type] => application/xml
                    [http_code] => 403
                    [header_size] => 254
                    [request_size] => 751
                    [filetime] => -1
                    [ssl_verify_result] => 0
                    [redirect_count] => 0
                    [total_time] => 0.318179
                    [namelookup_time] => 0.206527
                    [connect_time] => 0.209524
                    [pretransfer_time] => 0.277762
                    [size_upload] => 0
                    [size_download] => 231
                    [speed_download] => 726
                    [speed_upload] => 0
                    [download_content_length] => -1
                    [upload_content_length] => 0
                    [starttransfer_time] => 0.317943
                    [redirect_time] => 0
                    [certinfo] => Array
                        (
                        )

                    [primary_ip] => 27.0.1.76
                    [redirect_url] =>
                    [method] => GET
                )

            [x-aws-request-url] => https://memorycraft-log.s3-ap-northeast-1.amazonaws.com/logs/2013-03-17-05-34-13-347E8EF10D93460B
            [x-aws-redirects] => 0
            [x-aws-stringtosign] => GET

application/x-www-form-urlencoded
Tue, 19 Mar 2013 20:03:25 GMT
/memorycraft-log/logs/2013-03-17-05-34-13-347E8EF10D93460B
            [x-aws-requestheaders] => Array
                (
                    [Content-Type] => application/x-www-form-urlencoded
                    [Date] => Tue, 19 Mar 2013 20:03:25 GMT
                    [Authorization] => AWS AKIAIHEOBPDCINSPTZMQ:2unBCNgC8U6OIxpFPOppb5vOF70=
                    [Expect] =>
                )

        )

    [body] => <?xml version="1.0" encoding="UTF-8"?>
<Error><Code>AccessDenied</Code><Message>Access Denied</Message><RequestId>C6D3DB10776F16FA</RequestId><HostId>owcKsbILBrXmdTdu8XG81Rpe2ozrZmgOniQz5dUlUzH2b5c6TVVg3yEwue8q+QqI</HostId></Error>
    [status] => 403
)


これはダウンロード権限がファイルについているためです。
AWSコンソールからロギング設定をすると、S3がログに出力する際のファイル権限が自動で設定されるため、変更できないように見えますが、API経由で設定すると出力時のファイル権限を任意の内容に設定出来ます。

$src = 'myfirst-bucket';
$target = 'memorycraft-log';
$prefix = 'logs/';
$owner_canonical_id = 'オーナーの標準ユーザーID';
$other_canonical_id = '別アカウントの標準ユーザーID';
$s3 = new AmazonS3(array('key'=>'オーナーのアクセスキー','secret'=>'オーナーのシークレットキー'));

$res = $s3->enable_logging($src, $target, $prefix, array(
  'users' => array(
    array('id' => $owner_canonical_id,     'permission' => AmazonS3::GRANT_FULL_CONTROL ),
    array('id' => $other_canonical_id,     'permission' => AmazonS3::GRANT_FULL_CONTROL ),
  )
));


このようにAPI経由で設定したら、設定後に出力されたファイルの権限は以下のようになります。



このファイルを取得をしてみます。

CFResponse Object
(
    [header] => Array
        (
            [x-amz-id-2] => KF+Szr8tu2uvDLpz0DHl8ZNxbUmIqLtwXhJ9TISQvKUQR9x15RUNZzmpRFmfB910
            [x-amz-request-id] => EFE2ACA5DADC8273
            [date] => Tue, 19 Mar 2013 21:02:05 GMT
            [last-modified] => Tue, 19 Mar 2013 19:38:03 GMT
            [etag] => "ada5251bcbd676782e98153cd0cca821"
            [accept-ranges] => bytes
            [content-type] => text/plain
            [content-length] => 304
            [server] => AmazonS3
            [_info] => Array
                (
                    [url] => https://memorycraft-log.s3-ap-northeast-1.amazonaws.com/logs/2013-03-19-19-38-02-29AF737531B69E29
                    [content_type] => text/plain
                    [http_code] => 200
                    [header_size] => 345
                    [request_size] => 751
                    [filetime] => 1363721883
                    [ssl_verify_result] => 0
                    [redirect_count] => 0
                    [total_time] => 0.25437
                    [namelookup_time] => 0.139468
                    [connect_time] => 0.1404
                    [pretransfer_time] => 0.202015
                    [size_upload] => 0
                    [size_download] => 304
                    [speed_download] => 1195
                    [speed_upload] => 0
                    [download_content_length] => 304
                    [upload_content_length] => 0
                    [starttransfer_time] => 0.254312
                    [redirect_time] => 0
                    [certinfo] => Array
                        (
                        )

                    [primary_ip] => 27.0.1.206
                    [redirect_url] => 
                    [method] => GET
                )

            [x-aws-request-url] => https://memorycraft-log.s3-ap-northeast-1.amazonaws.com/logs/2013-03-19-19-38-02-29AF737531B69E29
            [x-aws-redirects] => 0
            [x-aws-stringtosign] => GET

application/x-www-form-urlencoded
Tue, 19 Mar 2013 21:02:04 GMT
/memorycraft-log/logs/2013-03-19-19-38-02-29AF737531B69E29
            [x-aws-requestheaders] => Array
                (
                    [Content-Type] => application/x-www-form-urlencoded
                    [Date] => Tue, 19 Mar 2013 21:02:04 GMT
                    [Authorization] => AWS XXXXXXXXXXXXXXXXXX:qqBlRlhCi9XzHcFE9Guc8J/W0yc=
                    [Expect] => 
                )

        )

    [body] => b00fb3b3fbeb37e2dc44f010cdbeff2c31bc467a2022f00401bf18abbf9e4543 myfirst-bucket [19/Mar/2013:18:22:39 +0000] 10.186.158.41 b00fb3b3fbeb37e2dc44f010cdbeff2c31bc467a2022f00401bf18abbf9e4543 22988F1BD9A4CBA1 REST.GET.LOCATION - "GET /myfirst-bucket?location HTTP/1.1" 200 - 142 - 21 - "-" "S3Console/0.4" -

    [status] => 200
)

無事取得できました!
以上です。