【Cognito】API GlobalSignOutとRevokeTokenの違い

GlobalSignOutはそのユーザーに紐づく全てのトークンを無効。
RevokeTokenは指定したリフレッシュトークンに連なるトークンを無効。
動作を見てみる。
ユーザーパスワードでCognitoで認証し、トークンを取得する。
USER_POOL_ID=ap-northeast-1_xxxxxxxx CLIENT_ID=xxxxxxxxxxxxxxxxxxxxxxxxxx USER_EMAIL="adminuser-0@test.com" PASSWORD="Password01" aws cognito-idp admin-initiate-auth \ --user-pool-id ${USER_POOL_ID} \ --client-id ${CLIENT_ID} \ --auth-flow ADMIN_NO_SRP_AUTH \ --auth-parameters "USERNAME=${USER_EMAIL},PASSWORD=${PASSWORD}"
RefreshToken、IdToken、AccessTokenが返る。
{ "ChallengeParameters": {}, "AuthenticationResult": { "AccessToken": "xxx", "ExpiresIn": 300, "TokenType": "Bearer", "RefreshToken": "xxx", "IdToken": "xxx" } }
RefreshTokenのみを取得して環境変数に入れる。
REFRESH_TOKEN=$(aws cognito-idp admin-initiate-auth \ --user-pool-id ${USER_POOL_ID} \ --client-id ${CLIENT_ID} \ --auth-flow ADMIN_NO_SRP_AUTH \ --auth-parameters "USERNAME=${USER_EMAIL},PASSWORD=${PASSWORD}" \ --query "AuthenticationResult.RefreshToken" \ --output text)
RefreshTokenを使ってトークンを再発行する。
aws cognito-idp admin-initiate-auth \ --user-pool-id ${COGNITO_USERPOOL_ID} \ --client-id ${COGNITO_CLIENT_ID} \ --auth-flow REFRESH_TOKEN_AUTH \ --auth-parameters "REFRESH_TOKEN=${REFRESH_TOKEN}" \ --no-cli-pager
IdTokenとRefreshTokenが再発行される。
RefreshTokenを使っているので、RefreshTokenは再発行はされない。
{ "ChallengeParameters": {}, "AuthenticationResult": { "AccessToken": "yyy", "ExpiresIn": 300, "TokenType": "Bearer", "IdToken": "yyy" } }
RevokeTokenを使って指定したRefreshTokenを失効させる。
あらかじめ、2種類のRefreshTokenを発行しておく。
➜ app git:(dev) ✗ REFRESH_TOKEN=$(aws cognito-idp admin-initiate-auth \ --user-pool-id ${USER_POOL_ID} \ --client-id ${CLIENT_ID} \ --auth-flow ADMIN_NO_SRP_AUTH \ --auth-parameters "USERNAME=${USER_EMAIL},PASSWORD=${PASSWORD}" \ --query "AuthenticationResult.RefreshToken" \ --output text) ➜ app git:(dev) ✗ AAA_REFRESH_TOKEN=$(aws cognito-idp admin-initiate-auth \ --user-pool-id ${USER_POOL_ID} \ --client-id ${CLIENT_ID} \ --auth-flow ADMIN_NO_SRP_AUTH \ --auth-parameters "USERNAME=${USER_EMAIL},PASSWORD=${PASSWORD}" \ --query "AuthenticationResult.RefreshToken" \ --output text)
片方のみを失効させる。
aws cognito-idp revoke-token \ --client-id ${CLIENT_ID} \ --token ${REFRESH_TOKEN}
${REFRESH_TOKEN}を使ったトークン再取得は失敗するが、${AAA_REFRESH_TOKEN}は成功している。
➜ app git:(dev) ✗ aws cognito-idp admin-initiate-auth \ --user-pool-id ${COGNITO_USERPOOL_ID} \ --client-id ${COGNITO_CLIENT_ID} \ --auth-flow REFRESH_TOKEN_AUTH \ --auth-parameters "REFRESH_TOKEN=${REFRESH_TOKEN}" \ --no-cli-pager An error occurred (NotAuthorizedException) when calling the AdminInitiateAuth operation: Refresh Token has been revoked ➜ app git:(dev) ✗ ➜ app git:(dev) ✗ aws cognito-idp admin-initiate-auth \ --user-pool-id ${COGNITO_USERPOOL_ID} \ --client-id ${COGNITO_CLIENT_ID} \ --auth-flow REFRESH_TOKEN_AUTH \ --auth-parameters "REFRESH_TOKEN=${AAA_REFRESH_TOKEN}" \ --no-cli-pager { "ChallengeParameters": {}, "AuthenticationResult": { "AccessToken": "yyy", "ExpiresIn": 300, "TokenType": "Bearer", "IdToken": "yyy" } } ➜ app git:(dev) ✗
詰まるところ、指定したRefreshTokenのみを失効させることができた。
GlobalSignOutはどうだろう。
同様に、あらかじめ、2種類のRefreshTokenを発行しておく。
➜ app git:(dev) ✗ REFRESH_TOKEN=$(aws cognito-idp admin-initiate-auth \ --user-pool-id ${USER_POOL_ID} \ --client-id ${CLIENT_ID} \ --auth-flow ADMIN_NO_SRP_AUTH \ --auth-parameters "USERNAME=${USER_EMAIL},PASSWORD=${PASSWORD}" \ --query "AuthenticationResult.RefreshToken" \ --output text) ➜ app git:(dev) ✗ AAA_REFRESH_TOKEN=$(aws cognito-idp admin-initiate-auth \ --user-pool-id ${USER_POOL_ID} \ --client-id ${CLIENT_ID} \ --auth-flow ADMIN_NO_SRP_AUTH \ --auth-parameters "USERNAME=${USER_EMAIL},PASSWORD=${PASSWORD}" \ --query "AuthenticationResult.RefreshToken" \ --output text)
トークンを失効させる。
aws cognito-idp admin-user-global-sign-out \ --user-pool-id ${USER_POOL_ID} \ --username ${USER_EMAIL}
両方のRefreshTokenが失効した。
➜ app git:(dev) ✗ aws cognito-idp admin-initiate-auth \ --user-pool-id ${COGNITO_USERPOOL_ID} \ --client-id ${COGNITO_CLIENT_ID} \ --auth-flow REFRESH_TOKEN_AUTH \ --auth-parameters "REFRESH_TOKEN=${REFRESH_TOKEN}" \ --no-cli-pager An error occurred (NotAuthorizedException) when calling the AdminInitiateAuth operation: Refresh Token has been revoked ➜ app git:(dev) ✗ ➜ app git:(dev) ✗ ➜ app git:(dev) ✗ aws cognito-idp admin-initiate-auth \ --user-pool-id ${COGNITO_USERPOOL_ID} \ --client-id ${COGNITO_CLIENT_ID} \ --auth-flow REFRESH_TOKEN_AUTH \ --auth-parameters "REFRESH_TOKEN=${AAA_REFRESH_TOKEN}" \ --no-cli-pager An error occurred (InvalidParameterException) when calling the AdminInitiateAuth operation: Missing required parameter REFRESH_TOKEN ➜ app git:(dev) ✗
そうなんだろうなと思いつつ、やってみると理解が深まる。
参考
https://dev.classmethod.jp/articles/amazon-cognito-now-supports-targeted-sign-out-through-refresh-token-revocation/