@quinck/aws-cognito-client
Version:
Provides a user attributes generic cognito client.
195 lines (194 loc) • 7.81 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.CognitoAuthService = void 0;
const client_cognito_identity_provider_1 = require("@aws-sdk/client-cognito-identity-provider");
const auth_service_1 = require("../models/components/auth-service");
const auth_1 = require("../utils/auth");
const errors_1 = require("../utils/errors");
const basic_cognito_service_1 = require("./basic-cognito-service");
class CognitoAuthService extends basic_cognito_service_1.BasicCognitoService {
constructor(config) {
super(config);
const { clientId, userPoolId } = config;
this.clientId = clientId;
this.authManager = tokens => new AuthenticationManager(this.cognitoIdentityProvider, userPoolId, clientId, tokens);
}
completeAuthChallenge(completion, options) {
return this.tryDo(async () => {
return await this.authManager().completeAuthChallenge(completion, options);
});
}
async updateCredentials(updateInfo, token) {
return this.tryDo(async () => {
const { newPassword, oldPassword } = updateInfo;
await this.cognitoIdentityProvider.changePassword({
AccessToken: token.accessToken,
PreviousPassword: oldPassword,
ProposedPassword: newPassword,
});
});
}
async login(userData) {
return this.tryDo(async () => {
const { password, username } = userData;
const result = await this.authManager().adminInitiateAuth({
AuthFlow: client_cognito_identity_provider_1.AuthFlowType.ADMIN_USER_PASSWORD_AUTH,
AuthParameters: {
USERNAME: username,
PASSWORD: password,
},
ClientId: this.clientId,
UserPoolId: this.userPoolId,
});
return result;
});
}
async refresh(token) {
return this.tryDo(async () => {
const loginResult = await this.authManager(token).adminInitiateAuth({
AuthFlow: client_cognito_identity_provider_1.AuthFlowType.REFRESH_TOKEN_AUTH,
ClientId: this.clientId,
UserPoolId: this.userPoolId,
AuthParameters: {
REFRESH_TOKEN: token.refreshToken,
},
});
if ((0, auth_1.isUserToken)(loginResult))
return loginResult;
throw new errors_1.UnauthorizedError();
});
}
async logout(token) {
return this.tryDo(async () => {
await this.cognitoIdentityProvider.globalSignOut({
AccessToken: token.accessToken,
});
});
}
async resendConfirmationLinkByEmail(username) {
return this.tryDo(async () => {
await this.cognitoIdentityProvider.resendConfirmationCode({
ClientId: this.clientId,
Username: username,
});
});
}
async forgotPassword(username) {
return this.tryDo(async () => {
await this.cognitoIdentityProvider.forgotPassword({
ClientId: this.clientId,
Username: username,
});
});
}
async resetPassword(data) {
return this.tryDo(async () => {
await this.cognitoIdentityProvider.confirmForgotPassword({
ClientId: this.clientId,
Username: data.username,
Password: data.newPassword,
ConfirmationCode: data.confirmationCode,
});
});
}
}
exports.CognitoAuthService = CognitoAuthService;
class AuthenticationManager {
constructor(cognitoIdentityProvider, userPoolId, clientId, userTokens = {}) {
this.cognitoIdentityProvider = cognitoIdentityProvider;
this.userPoolId = userPoolId;
this.clientId = clientId;
this.userTokens = userTokens;
}
async adminInitiateAuth(input) {
const output = await this.cognitoIdentityProvider.adminInitiateAuth(input);
return this.handleAdminAuthOutput(output);
}
handleAdminAuthOutput(output) {
const { AuthenticationResult } = output;
if (AuthenticationResult)
return this.parseUserToken(AuthenticationResult);
return this.handleRequiredAuthChallenge(output);
}
handleRequiredAuthChallenge(output) {
const { ChallengeName, ChallengeParameters, Session } = output;
const parameters = {
ChallengeParameters,
Session,
};
const options = { parameters };
const name = this.cognitoChallengeNameToChallengeName(ChallengeName);
return {
authChallenge: { name, options },
};
}
completeAuthChallenge(completion, options) {
switch (completion.name) {
case auth_service_1.AuthChallengeName.CUSTOM_CHALLENGE:
return this._completeAuthChallenge(completion, options);
case auth_service_1.AuthChallengeName.NEW_PASSWORD_REQUIRED:
return this._completeAuthChallenge(completion, options, {
NEW_PASSWORD: completion.newPassword,
});
default:
throw new errors_1.UnauthorizedError();
}
}
async _completeAuthChallenge(completion, options, additionalChallengeResponses) {
const { name, username } = completion;
const ChallengeName = this.challengeNameToCognitoChallengeName(name);
const { ChallengeParameters, Session } = this.parseParameters(options.parameters);
const ChallengeResponses = {
...ChallengeParameters,
...(additionalChallengeResponses ?? {}),
USERNAME: username,
};
const result = await this.cognitoIdentityProvider.adminRespondToAuthChallenge({
ChallengeName,
UserPoolId: this.userPoolId,
ClientId: this.clientId,
Session,
ChallengeResponses,
});
return this.handleAdminAuthOutput(result);
}
challengeNameToCognitoChallengeName(name) {
switch (name) {
case auth_service_1.AuthChallengeName.CUSTOM_CHALLENGE:
return client_cognito_identity_provider_1.ChallengeNameType.CUSTOM_CHALLENGE;
case auth_service_1.AuthChallengeName.NEW_PASSWORD_REQUIRED:
return client_cognito_identity_provider_1.ChallengeNameType.NEW_PASSWORD_REQUIRED;
default:
throw new errors_1.UnauthorizedError();
}
}
cognitoChallengeNameToChallengeName(name) {
switch (name) {
case client_cognito_identity_provider_1.ChallengeNameType.CUSTOM_CHALLENGE:
return auth_service_1.AuthChallengeName.CUSTOM_CHALLENGE;
case client_cognito_identity_provider_1.ChallengeNameType.NEW_PASSWORD_REQUIRED:
return auth_service_1.AuthChallengeName.NEW_PASSWORD_REQUIRED;
default:
throw new errors_1.UnauthorizedError();
}
}
parseParameters(parameters) {
return parameters; // TODO implement real check
}
parseUserToken(authResult) {
if (authResult) {
const { AccessToken, RefreshToken, IdToken } = authResult;
const accessToken = AccessToken;
const idToken = IdToken;
const refreshToken = RefreshToken ?? this.userTokens.refreshToken;
if (accessToken && refreshToken && idToken) {
return {
accessToken,
idToken,
refreshToken,
};
}
}
throw new errors_1.UnauthorizedError();
}
}