constructor()

in packages/aws-rfdk/lib/core/lib/mongodb-post-install.ts [163:239]


  constructor(scope: Construct, id: string, props: MongoDbPostInstallSetupProps) {
    super(scope, id);

    props.users.x509AuthUsers?.forEach( user => {
      try {
        JSON.parse(user.roles);
      } catch (e) {
        throw new Error(`MongoDbPostInstallSetup: Could not parse JSON role for x509 user: ${user.roles}`);
      }
    });

    const region = Stack.of(this).region;
    const openSslLayerName = 'openssl-al2';
    const openSslLayerArns: any = ARNS[openSslLayerName];
    const openSslLayerArn = openSslLayerArns[region];
    const openSslLayer = LayerVersion.fromLayerVersionArn(this, 'OpenSslLayer', openSslLayerArn);

    const lamdbaFunc = new LambdaFunction(this, 'Lambda', {
      vpc: props.vpc,
      vpcSubnets: props.vpcSubnets ?? { subnetType: SubnetType.PRIVATE_WITH_EGRESS },
      description: `Used by a MongoDbPostInstallSetup ${Names.uniqueId(this)} to perform post-installation setup on a MongoDB`,
      code: Code.fromAsset(path.join(__dirname, '..', '..', 'lambdas', 'nodejs'), {
        // Exclude commented out, for now, as a work-around for a CDK bug with at least CDK v1.49.1.
        // If we exclude files, then the asset hash is not calculated correctly and can result in updates to these
        // files not being picked up by the live system.
        // exclude: [
        //   '**/*',
        //   '!mongodb', '!mongodb/*',
        //   '!lib',
        //   '!lib/custom-resource', '!lib/custom-resource/*',
        //   '!lib/aws-lambda', '!lib/aws-lambda/*',
        //   '!lib/secrets-manager', '!lib/secrets-manager/*',
        //   '**/test',
        // ],
      }),
      environment: {
        DEBUG: 'false',
      },
      runtime: Runtime.NODEJS_18_X,
      handler: 'mongodb.configureMongo',
      layers: [ openSslLayer ],
      timeout: Duration.minutes(2),
      logRetention: RetentionDays.ONE_WEEK,
    });
    lamdbaFunc.connections.allowTo(props.mongoDb, Port.tcp(props.mongoDb.port));
    props.mongoDb.certificateChain.grantRead(lamdbaFunc.grantPrincipal);
    props.mongoDb.adminUser.grantRead(lamdbaFunc.grantPrincipal);
    props.users.passwordAuthUsers?.forEach( secret => secret.grantRead(lamdbaFunc) );
    props.users.x509AuthUsers?.forEach( user => user.certificate.grantRead(lamdbaFunc) );

    const properties: IMongoDbConfigureResource = {
      Connection: {
        Hostname: props.mongoDb.fullHostname,
        Port: props.mongoDb.port.toString(),
        CaCertificate: props.mongoDb.certificateChain.secretArn,
        Credentials: props.mongoDb.adminUser.secretArn,
      },
      PasswordAuthUsers: props.users.passwordAuthUsers?.map( secret => secret.secretArn ),
      X509AuthUsers: props.users.x509AuthUsers?.map( user => ({ Certificate: user.certificate.secretArn, Roles: user.roles }) ),
    };
    const resource = new CustomResource(this, 'Default', {
      serviceToken: lamdbaFunc.functionArn,
      resourceType: 'Custom::RFDK_MongoDbPostInstallSetup',
      properties,
    });
    // Prevents a race during a stack-update.
    resource.node.addDependency(lamdbaFunc.role!);

    /* istanbul ignore next */
    if (props.mongoDb.node.defaultChild) {
      // Add a dependency on the ASG within the StaticPrivateIpServer to ensure that
      // mongo is running before we try to login to it.
      resource.node.addDependency(props.mongoDb.node.defaultChild!.node.defaultChild!);
    }

    this.node.defaultChild = resource;
  }