UNPKG

mira

Version:

NearForm Accelerator for Cloud Native Serverless AWS

111 lines 5.49 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.ServerlessAurora = void 0; const core_1 = require("@aws-cdk/core"); const aws_ec2_1 = require("@aws-cdk/aws-ec2"); const aws_rds_1 = require("@aws-cdk/aws-rds"); const aws_secretsmanager_1 = require("@aws-cdk/aws-secretsmanager"); // Initially based on https://github.com/aws/aws-cdk/issues/929#issuecomment-516511171 /** * AWS Regions list that supports serverless Postgres aurora. * List should be curated based on https://aws.amazon.com/rds/aurora/pricing/ * * @ignore - Excluded from documentation generation. */ const supportedRegions = [ 'ap-northeast-1', 'eu-west-1', 'us-east-1', 'us-east-2', 'us-west-2' ]; /** * A Construct representing a Serverless Aurora Database for use with Mira */ class ServerlessAurora extends core_1.Construct { constructor(scope, id, props) { super(scope, id); const { region /*, stackName */ } = core_1.Stack.of(this); const isTestRegion = region.startsWith('test-'); const isToken = core_1.Tokenization.isResolvable(region); if (!isToken && !isTestRegion && !supportedRegions.includes(region + '')) { // The stackName is not available at this stage if the root stack is inherited from a MiraStack. // Requires a further investigation on the token resolution process. // In this specific case is not important to have the StackName than the resolution is postponed // throw new Error(`The region (${region}) used for ${stackName} does not support Amazon Aurora serverless PostgreSQL. // Please change the default region in the AWS credentials file, use another profile, or update cdk.json. // Supported regions are: ${supportedRegions.join(', ')}.`) throw new Error(`The region (${region}) used does not support Amazon Aurora serverless PostgreSQL. Please change the default region in the AWS credentials file, use another profile, or update cdk.json. Supported regions are: ${supportedRegions.join(', ')}.`); } this.vpc = props.vpc; this.vpcSubnets = props.subnets; const secret = new aws_rds_1.DatabaseSecret(this, 'MasterUserSecret', { username: props.masterUsername || 'root' }); const securityGroup = props.securityGroup || new aws_ec2_1.SecurityGroup(this, 'DatabaseSecurityGroup', { allowAllOutbound: true, description: 'DB Cluster Mira security group', vpc: props.vpc }); this.securityGroup = securityGroup; this.securityGroupId = securityGroup.securityGroupId; const cluster = new aws_rds_1.CfnDBCluster(this, 'DatabaseCluster', { databaseName: props.databaseName, engine: 'aurora-postgresql', engineMode: 'serverless', engineVersion: '10.7', masterUsername: secret.secretValueFromJson('username').toString(), masterUserPassword: secret.secretValueFromJson('password').toString(), dbSubnetGroupName: new aws_rds_1.CfnDBSubnetGroup(this, 'db-subnet-group', { dbSubnetGroupDescription: 'Mira database cluster subnet group', subnetIds: props.vpc.selectSubnets(props.subnets).subnetIds }).ref, vpcSecurityGroupIds: [securityGroup.securityGroupId], storageEncrypted: true, // Maximum here is 35 days backupRetentionPeriod: 35, scalingConfiguration: { autoPause: true, secondsUntilAutoPause: 300, minCapacity: 8, maxCapacity: props.maxCapacity } }); cluster.applyRemovalPolicy(core_1.RemovalPolicy.DESTROY, { applyToUpdateReplacePolicy: true }); this.clusterIdentifier = cluster.ref; // create a number token that represents the port of the cluster const portAttribute = core_1.Token.asNumber(cluster.attrEndpointPort); this.clusterEndpoint = new aws_rds_1.Endpoint(cluster.attrEndpointAddress, portAttribute); if (secret) { this.secret = secret.addTargetAttachment('AttachedSecret', { target: this }); } const defaultPort = aws_ec2_1.Port.tcp(this.clusterEndpoint.port); this.connections = new aws_ec2_1.Connections({ securityGroups: [securityGroup], defaultPort }); } /** * Adds the single user rotation of the master password to this cluster. * @param id {string} * @param duration {Duration} - The duration of the rotation, if null the default of 30 days is used */ addRotationSingleUser(id, duration) { if (!this.secret) { throw new Error('Cannot add single user rotation for a cluster without secret.'); } return new aws_secretsmanager_1.SecretRotation(this, id, { secret: this.secret, vpc: this.vpc, vpcSubnets: this.vpcSubnets, target: this, application: aws_secretsmanager_1.SecretRotationApplication.POSTGRES_ROTATION_SINGLE_USER, automaticallyAfter: duration || undefined }); } asSecretAttachmentTarget() { return { targetId: this.clusterIdentifier, targetType: aws_secretsmanager_1.AttachmentTargetType.CLUSTER }; } } exports.ServerlessAurora = ServerlessAurora; //# sourceMappingURL=serverless-aurora.js.map