import { DynamoDB , SNS } from "aws-sdk" ; import { randomBytes } from "crypto" ; /**
 * Verification context
 */ export type VerificationContext = "register" | "reset" ; /**
 * Verification code
 */ export interface VerificationCode { id : string ; context : VerificationContext ; subject : string ; expires : number ; } internal export class Verification { param dynamodb param sns public constructor ( protected dynamodb = new DynamoDB . DocumentClient ( { apiVersion : "2012-08-10" } ) , protected sns = new SNS ( { apiVersion : "2010-03-31" } ) ) { } param context param subject return public async issue ( context , subject ) { const code = { id : randomBytes ( 16 ) . toString ( "hex" ) , context , subject , expires : Math . floor ( Date . now ( ) / 1000 ) + 60 * 60 * 24 } ; await Promise . all ( [ this . dynamodb . put ( { TableName : process . env . DYNAMODB_TABLE ! , Item : code } ) . promise ( ) , this . sns . publish ( { TopicArn : process . env . SNS_TOPIC_ARN ! , Message : JSON . stringify ( code ) } ) . promise ( ) ] ) ; return code ; } param context param id return public async claim ( context , id ) { const { Attributes } = await this . dynamodb . delete ( { TableName : process . env . DYNAMODB_TABLE ! , Key : { id } , ReturnValues : "ALL_OLD" } ) . promise ( ) ; const code = Attributes as VerificationCode ; if ( ! code || code . context !== context ) throw new Error ( `Invalid verification code` ) ; return code ; } }