🏸
ALBから渡される認証情報をexpressで取得する
環境
node 16.13.1
express 4.17.3
やりたいこと
ALBとcognitoを連携させて認証認可を実現するケースって多いと思います。
ALBの認証を通過したHTTPアクセスについて、expressで認証済みユーザ情報を引き出したいと思いました。
ex. ALB後段のAPIサーバにて、POSTリクエストを行っているユーザの名前とemailを取得し、DBに合わせて登録する
構成例
実現方法
import { Request } from "express";
const getUserInfo = (req: Request): { name: string; email: string } => {
const oidcData = req.headers["x-amzn-oidc-data"];
if (oidcData && typeof oidcData === "string") {
// JWT形式の文字列からpayloadを取得
const payload = oidcData.split(".")[1];
// payloadをdecodeしてjson形式に変換
const decoded = JSON.parse(Buffer.from(payload, "base64").toString("utf8"));
return { name: decoded.name ?? "", email: decoded.email ?? "" };
} else {
return { name: "", email: "" };
}
};
解説
x-amzn-oidc-dataにユーザ情報がJWT形式で含まれています。
JWTはJSONを単にbase64エンコードしただけのものなので、ペイロード部分をデコードしてあげれば簡単にユーザ情報を取得できます。
# デコード後のペイロード例
{
sub: '3344-abcd',
email_verified: 'false',
email: 'mail@address.com',
username: 'user_name',
exp: 1651818337,
iss: 'https://cognito-idp.ap-northeast-1.amazonaws.com/ap-northeast-1_AAAAA'
}
さいごに
cognitoに限らずAzureADなどのIdPとALBを連携させた場合でも同様に行えるはずです。
ちなみに、x-amzn-oidc-accesstokenもJWT形式で記述されており、デコードすると色々出てきます。
必要に応じて、適切な方から情報を引っ張ってみて下さい
# デコード後のx-amzn-oidc-accesstokenペイロードの例
{
sub: '3344-abcd',
'cognito:groups': [ 'ap-northeast-1_AAAA_pool' ],
iss: 'https://cognito-idp.ap-northeast-1.amazonaws.com/ap-northeast-1_AAAAA',
version: 2,
client_id: 'clientid',
origin_jti: 'aaaa-bb',
token_use: 'access',
scope: 'openid',
auth_time: 1651813462,
exp: 1651820813,
iat: 1651817213,
jti: 'aaaa-bbbbb',
username: 'user-name'
}
また、こちらを応用して「良いね機能」を実現するコンテナベースのバックエンドを作りました。
良かったらこちらも眺めてみて下さい。
Discussion