ビューワーリクエストでCloudFront FunctionsやLambda@Edgeでタイムゾーンの判定ができるのか確認してみた
ビューワーリクエストでCloudFront FunctionsやLambda@Edgeでタイムゾーンの判定ができるのか気になる
こんにちは、のんピ(@non____97)です。
皆さんはビューワーリクエストでCloudFront FunctionsやLambda@Edgeでタイムゾーンの判定ができるのか気になったことはありますか? 私はあります。
オリジンリクエストをする際でのタイムゾーンの判定は以下のようにCloudFront-Viewer-Time-Zone
を用いることで可能です。
ふと、以下記事で行なっているようなキャッシュキーの整形のためにビューワーリクエストでもタイムゾーンの判定ができるかどうか気になりました。
実際に試してみます。
ちなみに、Lambda@Edgeでタイムゾーンの環境変数はデフォルトUTCです。
TZ– 環境のタイムゾーン(:UTC)。実行環境はNTPを使用してシステムクロックを同期します。
実際に試してみます。
いきなりまとめ
- ビューワーリクエストでCloudFront FunctionsやLambda@Edgeでタイムゾーンの判定をすることはできない
CloudFront Functions
使用するコード
まずはCloudFront Functionsから実行します。
使用するコードは以下のとおりです。
function handler(event) {
const now = new Date();
const timezoneOffset = now.getTimezoneOffset()
const response = {
statusCode: 200,
statusDescription: 'OK',
headers: {
'x-date-now': { value: now.toString() },
'x-timezone-offset': { value: timezoneOffset.toString() }
}
};
return response;
}
こちらを/date/cf2
のビヘイビアでビューワーリクエストで動作するように設定します。
us-east-1のCloudShellから呼び出し
それでは、まずはus-east-1のCloudShellから呼び出しをしてみます。
$ echo $AWS_REGION
us-east-1
$ date
Tue Jul 8 12:55:39 AM UTC 2025
$ cat /etc/localtime
TZif2UTCTZif2UTC
UTC0
$ curl -I https://www.non-97.net/date/cf2
HTTP/2 200
server: CloudFront
date: Tue, 08 Jul 2025 00:57:22 GMT
content-length: 0
x-date-now: Tue Jul 08 2025 00:57:22 GMT+0000
x-timezone-offset: 0
x-cache: FunctionGeneratedResponse from cloudfront
via: 1.1 5084a25d91022b55b5acf281581c6444.cloudfront.net (CloudFront)
x-amz-cf-pop: IAD61-P1
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: UtgBI2zGh2gIzr60Q--eY2Snjy6bUueC1RIEZWxh6fjgkgV_z86x0g==
$ curl -I https://www.non-97.net/date/cf2
HTTP/2 200
server: CloudFront
date: Tue, 08 Jul 2025 00:57:39 GMT
content-length: 0
x-date-now: Tue Jul 08 2025 00:57:39 GMT+0000
x-timezone-offset: 0
x-cache: FunctionGeneratedResponse from cloudfront
via: 1.1 8696978c2d465ffc3a342761ace51d9e.cloudfront.net (CloudFront)
x-amz-cf-pop: IAD61-P1
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: KFfi_Q47Dn_Rhe7qSHFs3jvgFTQfYEl8bemG03Ew4X7tQDdz5MoCDA==
x-timezone-offset
は0であり、タイムゾーンはUTCであることが分かります。
ap-northeast-1のCloudShellから呼び出し
次にap-northeast-1のCloudShellから呼び出しを行います。
$ echo $AWS_REGION
ap-northeast-1
$ date
Tue Jul 8 01:58:58 AM UTC 2025
$ cat /etc/localtime
TZif2UTCTZif2UTC
UTC0
$ curl -I https://www.non-97.net/date/cf2
HTTP/2 200
server: CloudFront
date: Tue, 08 Jul 2025 01:59:07 GMT
content-length: 0
x-date-now: Tue Jul 08 2025 01:59:07 GMT+0000
x-timezone-offset: 0
x-cache: FunctionGeneratedResponse from cloudfront
via: 1.1 b3501c20a49de1b44e6f6541d94742b6.cloudfront.net (CloudFront)
x-amz-cf-pop: NRT12-P9
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: Ny10Mct_j4-UcogaiJueljGeJ-FRDUEQ0dpL0iMZim8wPBQaofpEJg==
$ curl -I https://www.non-97.net/date/cf2
HTTP/2 200
server: CloudFront
date: Tue, 08 Jul 2025 01:59:11 GMT
content-length: 0
x-date-now: Tue Jul 08 2025 01:59:11 GMT+0000
x-timezone-offset: 0
x-cache: FunctionGeneratedResponse from cloudfront
via: 1.1 63e796d5ab2f61effb7a6df6497d49f8.cloudfront.net (CloudFront)
x-amz-cf-pop: NRT12-P9
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: KgeijqU6161GSbcAmy0t5hiGZWLl0bQi3So4A7nj2IN2up0YIS6Iag==
こちらもx-timezone-offset
は0であり、タイムゾーンはUTCであることが分かります。
自端末から呼び出し
私は日本に暮らしています。自端末からも呼び出しをしてみます。
LC_ALL=C date
Tue Jul 8 11:02:03 JST 2025
> curl -I https://www.non-97.net/date/cf2
HTTP/2 200
server: CloudFront
date: Tue, 08 Jul 2025 02:02:31 GMT
content-length: 0
x-date-now: Tue Jul 08 2025 02:02:31 GMT+0000
x-timezone-offset: 0
x-cache: FunctionGeneratedResponse from cloudfront
via: 1.1 d6a8fd11b3bf4867ce673aa444e83f86.cloudfront.net (CloudFront)
x-amz-cf-pop: NRT12-P9
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: g7LUhMyBqpNh9lu-T-kEtgUZ5rwLC-1S0AiZDTejo1Zz6a7sOrkHGw==
> curl -I https://www.non-97.net/date/cf2
HTTP/2 200
server: CloudFront
date: Tue, 08 Jul 2025 02:02:38 GMT
content-length: 0
x-date-now: Tue Jul 08 2025 02:02:38 GMT+0000
x-timezone-offset: 0
x-cache: FunctionGeneratedResponse from cloudfront
via: 1.1 63e796d5ab2f61effb7a6df6497d49f8.cloudfront.net (CloudFront)
x-amz-cf-pop: NRT12-P9
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: 3_HabUaARIPZSGF1-WuA_D1FW7Lzp1NcLqKfDRg-U0D4mLoIfSyM0Q==
今回もx-timezone-offset
は0であり、タイムゾーンはUTCであることが分かります。
ということで、複数のリージョン、端末から実行しても結果が変わらないことからCloudFront FunctionsではタイムゾーンはUTCで固定のようです。
Lambda@Edge
使用するコード
Lambda@Edgeでも試しましょう。使用するコードは以下のとおりです。
export const handler = async (event, context, callback) => {
const now = new Date();
const timezoneOffset = now.getTimezoneOffset();
const response = {
status: '200',
statusDescription: 'OK',
headers: {
'content-type': [
{
key: 'Content-Type',
value: 'application/json'
}
],
'x-date-now': [
{
key: 'X-Date-Now',
value: now.toString()
}
],
'x-timezone-offset': [
{
key: 'X-Timezone-Offset',
value: timezoneOffset.toString()
}
]
}
};
callback(null, response);
};
こちらを/date/lambdaEdge
のビヘイビアでビューワーリクエストで動作するように設定します。
us-east-1のCloudShellから呼び出し
ではus-east-1のCloudShellからの呼び出しを試してみます。
$ date
Tue Jul 8 02:55:11 AM UTC 2025
$ curl -I https://www.non-97.net/date/lambdaEdge
HTTP/2 200
content-type: application/json
content-length: 0
server: CloudFront
date: Tue, 08 Jul 2025 02:55:13 GMT
x-date-now: Tue Jul 08 2025 02:55:13 GMT+0000 (Coordinated Universal Time)
x-timezone-offset: 0
x-cache: LambdaGeneratedResponse from cloudfront
via: 1.1 030b88b6d8d9c6faf056723bb5f16078.cloudfront.net (CloudFront)
x-amz-cf-pop: IAD61-P1
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: HjCnduhM3Sh4q8bjFN-EcIev8vF0qbra64yhnQd5KOrjzq6SuBTwwA==
x-timezone-offset
は0であり、タイムゾーンはUTCであることが分かります。
ap-northeast-1のCloudShellから呼び出し
ap-northeast-1のCloudShellから呼び出しを試します。
$ date
Tue Jul 8 02:55:57 AM UTC 2025
$ curl -I https://www.non-97.net/date/lambdaEdge
HTTP/2 200
content-type: application/json
content-length: 0
server: CloudFront
date: Tue, 08 Jul 2025 02:56:04 GMT
x-date-now: Tue Jul 08 2025 02:56:04 GMT+0000 (Coordinated Universal Time)
x-timezone-offset: 0
x-cache: LambdaGeneratedResponse from cloudfront
via: 1.1 d6a8fd11b3bf4867ce673aa444e83f86.cloudfront.net (CloudFront)
x-amz-cf-pop: NRT12-P9
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: kkhyyWbr31YdV0KAAS7Qlj6EUKvCMenMqFljq9xNsDWW4Q4Z4SjaQw==
こちらもx-timezone-offset
は0であり、タイムゾーンはUTCであることが分かります。
自端末から呼び出し
最後に自端末から呼び出します。
> LC_ALL=C date
Tue Jul 8 13:15:19 JST 2025
> curl -I https://www.non-97.net/date/lambdaEdge
HTTP/2 200
content-type: application/json
content-length: 0
server: CloudFront
date: Tue, 08 Jul 2025 04:15:23 GMT
x-date-now: Tue Jul 08 2025 04:15:23 GMT+0000 (Coordinated Universal Time)
x-timezone-offset: 0
x-cache: LambdaGeneratedResponse from cloudfront
via: 1.1 4b89bcf81ee0cac0bd0f3005a626d42c.cloudfront.net (CloudFront)
x-amz-cf-pop: NRT12-P9
alt-svc: h3=":443"; ma=86400
x-amz-cf-id: _M25GFET2c9TFBHd1J6QR3ZbhSHcdmOgdTs4XQQjTP96IIOiA1Il5g==
やはりx-timezone-offset
は0であり、タイムゾーンはUTCであることが分かります。
ビューワーリクエストでCloudFront FunctionsやLambda@Edgeでタイムゾーンの判定はできない
ビューワーリクエストでCloudFront FunctionsやLambda@Edgeでタイムゾーンの判定はできないことを確認しました。
無難にオリジンリクエストで判定する形が良さそうです。
キャッシュキーについてもCloudFront-Viewer-Country
やCloudFront-Viewer-Time-Zone
といったCloudFront標準のジオロケーションヘッダーを用いてキャッシュをするのが良さそうです。
ビューワーの場所に基づいてキャッシュを設定する
リクエスト元の国に基づいて、オブジェクトの異なるバージョンを CloudFront でキャッシュするには、CloudFront-Viewer-Country ヘッダーをオリジンに転送するように CloudFront を設定します。CloudFront はリクエスト元の IP アドレスを 2 文字の国コードに自動的に変換します。コード順、国順に並べ替えることのできる使いやすい国コードの一覧については、Wikipedia の「ISO 3166-1 alpha-2」の項目を参照してください。
この記事が誰かの助けになれば幸いです。
以上、クラウド事業本部 コンサルティング部の のんピ(@non____97)でした!