aws-cdk-lib#Token TypeScript Examples
The following examples show how to use
aws-cdk-lib#Token.
You can vote up the ones you like or vote down the ones you don't like,
and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: manifest.ts From cloudstructs with Apache License 2.0 | 6 votes |
function validateUrl(url?: string, https = true): void {
if (url && !Token.isUnresolved(url)) {
try {
const parsed = new nodeUrl.URL(url);
if (https && parsed.protocol !== 'https:') {
throw new Error('Invalid protocol');
}
} catch (err) {
throw new Error(`${url} is not a valid${https ? ' HTTPS' : ''} url`);
}
}
}
Example #2
Source File: index.ts From cloudstructs with Apache License 2.0 | 6 votes |
function shouldAddRedirect(props: StaticWebsiteProps): boolean {
if (props.redirects && props.redirects.length === 0) {
return false;
}
if (!props.redirects && !Token.isUnresolved(props.domainName)
&& !Token.isUnresolved(props.hostedZone.zoneName)
&& props.domainName === props.hostedZone.zoneName) {
return false;
}
return true;
}
Example #3
Source File: aurora-serverless.ts From bastion-host-forward with Apache License 2.0 | 6 votes |
constructor(scope: Construct, id: string, props: BastionHostAuroraServerlessForwardProps) {
super(scope, id, {
vpc: props.vpc,
name: props.name,
securityGroup: props.securityGroup,
address: props.serverlessCluster.clusterEndpoint.hostname,
port: Token.asString(props.serverlessCluster.clusterEndpoint.port),
clientTimeout: props.clientTimeout,
serverTimeout: props.serverTimeout,
});
if (props.iamUser !== undefined && props.resourceIdentifier !== undefined) {
this.bastionHost.instance.addToRolePolicy(
new iam.PolicyStatement({
effect: iam.Effect.ALLOW,
actions: ['rds-db:connect', 'rds:*'],
resources: [
this.genDbUserArnFromRdsArn(props.resourceIdentifier, props.iamUser),
props.serverlessCluster.clusterArn,
],
}),
);
}
}
Example #4
Source File: manifest.ts From cloudstructs with Apache License 2.0 | 5 votes |
function validateLength(description: string, max: number, xs?: string): void {
if (xs && !Token.isUnresolved(xs) && xs.length > max) {
throw new Error(`Maximum length for ${description} is ${max}, got ${xs.length}: ${xs}`);
}
}
Example #5
Source File: manifest.ts From cloudstructs with Apache License 2.0 | 5 votes |
function validateItems<T>(description: string, max: number, xs?: T[]): void {
if (xs && !Token.isUnresolved(xs) && xs.length > max) {
throw new Error(`Maximum number of items for ${description} is ${max}, got ${xs.length}`);
}
}
Example #6
Source File: manifest.ts From cloudstructs with Apache License 2.0 | 5 votes |
function validateColor(color?: string): void {
if (color && !Token.isUnresolved(color) && !/^#?([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$/.test(color)) {
throw new Error(`Invalid hex color: ${color}`);
}
}
Example #7
Source File: dns-validated-domain-identity.ts From aws-cdk-ses-domain-identity with MIT License | 5 votes |
public constructor(scope: Construct, id: string, props: DnsValidatedDomainIdentityProps) {
super(scope, id);
const stack = Stack.of(this);
const region = props.region ?? stack.region;
const accountId = stack.account;
this.domainName = props.domainName;
this.dkim = props.dkim ?? false;
this.identityArn = `arn:aws:ses:${region}:${accountId}:identity/${this.domainName}`;
this.normalizedZoneName = props.hostedZone.zoneName;
// Remove trailing `.` from zone name
if (this.normalizedZoneName.endsWith(".")) {
this.normalizedZoneName = this.normalizedZoneName.substring(0, this.normalizedZoneName.length - 1);
}
// Remove any `/hostedzone/` prefix from the Hosted Zone ID
this.hostedZoneId = props.hostedZone.hostedZoneId.replace(/^\/hostedzone\//, "");
const requestorFunction = new lambda.Function(this, "DomainIdentityRequestorFunction", {
code: lambda.Code.fromAsset(path.resolve(__dirname, "..", "lambda-packages", "dns-validated-domain-identity-handler", "dist")),
handler: "index.identityRequestHandler",
runtime: lambda.Runtime.NODEJS_14_X,
memorySize: 128,
timeout: Duration.minutes(15),
role: props.customResourceRole,
});
requestorFunction.addToRolePolicy(new iam.PolicyStatement({
actions: [
"ses:GetIdentityVerificationAttributes",
"ses:GetIdentityDkimAttributes",
"ses:SetIdentityDkimEnabled",
"ses:VerifyDomainIdentity",
"ses:VerifyDomainDkim",
"ses:ListIdentities",
"ses:DeleteIdentity",
],
resources: ["*"],
}));
requestorFunction.addToRolePolicy(new iam.PolicyStatement({
actions: ["route53:GetChange"],
resources: ["*"],
}));
requestorFunction.addToRolePolicy(new iam.PolicyStatement({
actions: [
"route53:changeResourceRecordSets",
"route53:ListResourceRecordSets",
],
resources: [`arn:${Stack.of(requestorFunction).partition}:route53:::hostedzone/${this.hostedZoneId}`],
}));
const identity = new CustomResource(this, "IdentityRequestorResource", {
serviceToken: requestorFunction.functionArn,
properties: {
DomainName: this.domainName,
HostedZoneId: this.hostedZoneId,
Region: region,
DKIM: props.dkim,
},
});
this.node.addValidation({
validate: (): string[] => {
const errors: string[] = [];
// Ensure the zone name is a parent zone of the certificate domain name
if (!Token.isUnresolved(this.normalizedZoneName) &&
this.domainName !== this.normalizedZoneName &&
!this.domainName.endsWith("." + this.normalizedZoneName)) {
errors.push(`DNS zone ${this.normalizedZoneName} is not authoritative for SES identity domain name ${this.domainName}`);
}
return errors;
},
});
}
Example #8
Source File: dns-validated-domain-identitiy.test.ts From aws-cdk-ses-domain-identity with MIT License | 4 votes |
describe(DnsValidatedDomainIdentity.name, () => {
it("creates CloudFormation Custom Resource", () => {
const stack = new Stack();
const exampleDotComZone = new PublicHostedZone(stack, "ExampleDotCom", {
zoneName: "example.com",
});
// tslint:disable-next-line:no-unused-expression
new DnsValidatedDomainIdentity(stack, "DomainIdentity", {
domainName: "test.example.com",
hostedZone: exampleDotComZone,
});
Template.fromStack(stack).hasResourceProperties("AWS::CloudFormation::CustomResource", {
DomainName: "test.example.com",
ServiceToken: {
"Fn::GetAtt": [
"DomainIdentityDomainIdentityRequestorFunction700A5CBC",
"Arn",
],
},
HostedZoneId: {
Ref: "ExampleDotCom4D1B83AA",
},
});
Template.fromStack(stack).hasResourceProperties("AWS::Lambda::Function", {
Handler: "index.identityRequestHandler",
Runtime: "nodejs14.x",
MemorySize: 128,
Timeout: 900,
});
Template.fromStack(stack).hasResourceProperties("AWS::IAM::Policy", {
PolicyName: "DomainIdentityDomainIdentityRequestorFunctionServiceRoleDefaultPolicy9D23D5BE",
Roles: [
{
Ref: "DomainIdentityDomainIdentityRequestorFunctionServiceRoleD8F10EBD",
},
],
PolicyDocument: {
Version: "2012-10-17",
Statement: [
{
Action: [
"ses:GetIdentityVerificationAttributes",
"ses:GetIdentityDkimAttributes",
"ses:SetIdentityDkimEnabled",
"ses:VerifyDomainIdentity",
"ses:VerifyDomainDkim",
"ses:ListIdentities",
"ses:DeleteIdentity",
],
Effect: "Allow",
Resource: "*",
},
{
Action: "route53:GetChange",
Effect: "Allow",
Resource: "*",
},
{
Action: [
"route53:changeResourceRecordSets",
"route53:ListResourceRecordSets",
],
Effect: "Allow",
Resource: {
"Fn::Join": [
"",
[
"arn:",
{ Ref: "AWS::Partition" },
":route53:::hostedzone/",
{ Ref: "ExampleDotCom4D1B83AA" },
],
],
},
},
],
},
});
});
it("adds validation error on domain mismatch", () => {
const stack = new Stack();
const helloDotComZone = new PublicHostedZone(stack, "HelloDotCom", {
zoneName: "hello.com",
});
// tslint:disable-next-line:no-unused-expression
new DnsValidatedDomainIdentity(stack, "DomainIdentity", {
domainName: "example.com",
hostedZone: helloDotComZone,
});
expect(() => Template.fromStack(stack))
.toThrow(/DNS zone hello.com is not authoritative for SES identity domain name example.com/);
});
it("does not try to validate unresolved tokens", () => {
const stack = new Stack();
const helloDotComZone = new PublicHostedZone(stack, "HelloDotCom", {
zoneName: Token.asString("hello.com"),
});
// tslint:disable-next-line:no-unused-expression
new DnsValidatedDomainIdentity(stack, "DomainIdentity", {
domainName: "hello.com",
hostedZone: helloDotComZone,
});
expect(() => Template.fromStack(stack)).not.toThrow();
});
it("works with imported zone", () => {
// GIVEN
const app = new App();
const stack = new Stack(app, "Stack", {
env: { account: "12345678", region: "us-blue-5" },
});
const imported = HostedZone.fromLookup(stack, "ExampleDotCom", {
domainName: "mydomain.com",
});
// WHEN
// tslint:disable-next-line:no-unused-expression
new DnsValidatedDomainIdentity(stack, "DomainIdentity", {
domainName: "mydomain.com",
hostedZone: imported,
});
// THEN
Template.fromStack(stack).hasResourceProperties("AWS::CloudFormation::CustomResource", {
ServiceToken: {
"Fn::GetAtt": [
"DomainIdentityDomainIdentityRequestorFunction700A5CBC",
"Arn",
],
},
DomainName: "mydomain.com",
HostedZoneId: "DUMMY",
});
});
it("works with imported role", () => {
// GIVEN
const app = new App();
const stack = new Stack(app, "Stack", {
env: { account: "12345678", region: "us-blue-5" },
});
const helloDotComZone = new PublicHostedZone(stack, "HelloDotCom", {
zoneName: "hello.com",
});
const role = iam.Role.fromRoleArn(stack, "Role", "arn:aws:iam::account-id:role/role-name");
// WHEN
// tslint:disable-next-line:no-unused-expression
new DnsValidatedDomainIdentity(stack, "DomainIdentity", {
domainName: "hello.com",
hostedZone: helloDotComZone,
customResourceRole: role,
});
// THEN
Template.fromStack(stack).hasResourceProperties("AWS::Lambda::Function", {
Role: "arn:aws:iam::account-id:role/role-name",
});
});
it("exposes properties related to identity", () => {
const app = new App();
const stack = new Stack(app, "Stack", {
env: { account: "12345678", region: "us-blue-5" },
});
const helloDotComZone = new PublicHostedZone(stack, "HelloDotCom", {
zoneName: "example.com",
});
const identity = new DnsValidatedDomainIdentity(stack, "DomainIdentity", {
domainName: "test.example.com",
hostedZone: helloDotComZone,
});
expect(identity.identityArn).toEqual("arn:aws:ses:us-blue-5:12345678:identity/test.example.com");
});
});
Example #9
Source File: gitlab-runner-instance.ts From cdk-gitlab-runner with Apache License 2.0 | 4 votes |
constructor(scope: Construct, id: string, props: GitlabContainerRunnerProps) {
super(scope, id);
const spotFleetId = id;
const defaultProps = {
gitlabRunnerImage: 'public.ecr.aws/gitlab/gitlab-runner:alpine',
gitlaburl: 'https://gitlab.com/',
ec2type: 't3.micro',
tags: ['gitlab', 'awscdk', 'runner'],
};
const runnerProps = { ...defaultProps, ...props };
const runnerBucket = new Bucket(this, 'runnerBucket', {
removalPolicy: RemovalPolicy.DESTROY,
autoDeleteObjects: true,
});
const shell = UserData.forLinux();
shell.addCommands(...this.createUserData(runnerProps, runnerBucket.bucketName));
this.runnerRole =
runnerProps.ec2iamrole ??
new Role(this, 'runner-role', {
assumedBy: new ServicePrincipal('ec2.amazonaws.com'),
description: 'For Gitlab EC2 Runner Role',
});
this.validUntil = runnerProps.validUntil;
const instanceProfile = new CfnInstanceProfile(this, 'InstanceProfile', {
roles: [this.runnerRole.roleName],
});
runnerBucket.grantWrite(this.runnerRole);
this.vpc =
runnerProps.selfvpc ??
new Vpc(this, 'VPC', {
cidr: '10.0.0.0/16',
maxAzs: 2,
subnetConfiguration: [
{
cidrMask: 26,
name: 'RunnerVPC',
subnetType: SubnetType.PUBLIC,
},
],
natGateways: 0,
});
this.defaultRunnerSG = new SecurityGroup(this, 'SpotFleetSg', {
vpc: this.vpc,
});
this.defaultRunnerSG.connections.allowFromAnyIpv4(Port.tcp(22));
const spotOrOnDemand = runnerProps.spotFleet ?? false;
if (spotOrOnDemand) {
//throw new Error('yes new spotfleet');
const imageId = MachineImage.latestAmazonLinux({
generation: AmazonLinuxGeneration.AMAZON_LINUX_2,
}).getImage(this).imageId;
const lt = new CfnLaunchTemplate(this, 'LaunchTemplate', {
launchTemplateData: {
imageId,
instanceType: runnerProps.ec2type,
blockDeviceMappings: [
{
deviceName: '/dev/xvda',
ebs: {
volumeSize: runnerProps.ebsSize ?? 60,
},
},
],
userData: Fn.base64(shell.render()),
keyName: runnerProps.keyName,
tagSpecifications: [
{
resourceType: 'instance',
tags: [
{
key: 'Name',
value: `${Stack.of(this).stackName
}/spotFleetGitlabRunner/${spotFleetId}`,
},
],
},
],
instanceMarketOptions: {
marketType: 'spot',
spotOptions: {
blockDurationMinutes:
runnerProps.blockDuration ?? BlockDuration.ONE_HOUR,
instanceInterruptionBehavior:
runnerProps.instanceInterruptionBehavior ??
InstanceInterruptionBehavior.TERMINATE,
},
},
securityGroupIds: this.defaultRunnerSG.connections.securityGroups.map(
(m) => m.securityGroupId,
),
iamInstanceProfile: {
arn: instanceProfile.attrArn,
},
},
});
const spotFleetRole = new Role(this, 'FleetRole', {
assumedBy: new ServicePrincipal('spotfleet.amazonaws.com'),
managedPolicies: [
ManagedPolicy.fromAwsManagedPolicyName(
'service-role/AmazonEC2SpotFleetTaggingRole',
),
],
});
const vpcSubnetSelection = runnerProps.vpcSubnet ?? {
subnetType: SubnetType.PUBLIC,
};
const subnetConfig = this.vpc
.selectSubnets(vpcSubnetSelection)
.subnets.map((s) => ({
subnetId: s.subnetId,
}));
const cfnSpotFleet = new CfnSpotFleet(this, id, {
spotFleetRequestConfigData: {
launchTemplateConfigs: [
{
launchTemplateSpecification: {
launchTemplateId: lt.ref,
version: lt.attrLatestVersionNumber,
},
overrides: subnetConfig,
},
],
iamFleetRole: spotFleetRole.roleArn,
targetCapacity: 1,
validUntil: Lazy.string({ produce: () => this.validUntil }),
terminateInstancesWithExpiration: true,
},
});
const onEvent = new lambda.Function(this, 'OnEvent', {
code: lambda.Code.fromAsset(path.join(__dirname, '../assets/functions')),
handler: 'index.on_event',
runtime: lambda.Runtime.PYTHON_3_8,
timeout: Duration.seconds(60),
});
const isComplete = new lambda.Function(this, 'IsComplete', {
code: lambda.Code.fromAsset(path.join(__dirname, '../assets/functions')),
handler: 'index.is_complete',
runtime: lambda.Runtime.PYTHON_3_8,
timeout: Duration.seconds(60),
role: onEvent.role,
});
const myProvider = new cr.Provider(this, 'MyProvider', {
onEventHandler: onEvent,
isCompleteHandler: isComplete,
logRetention: logs.RetentionDays.ONE_DAY,
});
onEvent.addToRolePolicy(
new PolicyStatement({
actions: ['ec2:DescribeSpotFleetInstances'],
resources: ['*'],
}),
);
const fleetInstances = new CustomResource(this, 'GetInstanceId', {
serviceToken: myProvider.serviceToken,
properties: {
SpotFleetRequestId: cfnSpotFleet.ref,
},
});
fleetInstances.node.addDependency(cfnSpotFleet);
this.spotFleetInstanceId = Token.asString(
fleetInstances.getAtt('InstanceId'),
);
this.spotFleetRequestId = Token.asString(
fleetInstances.getAtt('SpotInstanceRequestId'),
);
new CfnOutput(this, 'InstanceId', { value: this.spotFleetInstanceId });
new CfnOutput(this, 'SpotFleetId', { value: cfnSpotFleet.ref });
} else {
this.runnerEc2 = new Instance(this, 'GitlabRunner', {
instanceType: new InstanceType(runnerProps.ec2type),
instanceName: 'Gitlab-Runner',
vpc: this.vpc,
vpcSubnets: runnerProps.vpcSubnet ?? {
subnetType: SubnetType.PUBLIC,
},
machineImage: MachineImage.latestAmazonLinux({
generation: AmazonLinuxGeneration.AMAZON_LINUX_2,
}),
role: this.runnerRole,
userData: shell,
securityGroup: this.defaultRunnerSG,
blockDevices: [
{
deviceName: '/dev/xvda',
volume: BlockDeviceVolume.ebs(runnerProps.ebsSize ?? 60),
},
],
});
new CfnOutput(this, 'Runner-Instance-ID', {
value: this.runnerEc2.instanceId,
});
}
const unregisterRunnerOnEvent = new lambda.Function(this, 'unregisterRunnerOnEvent', {
code: lambda.Code.fromAsset(path.join(__dirname, '../assets/functions')),
handler: 'unregister_runner.on_event',
runtime: lambda.Runtime.PYTHON_3_8,
timeout: Duration.seconds(60),
});
const unregisterRunnerProvider = new cr.Provider(this, 'unregisterRunnerProvider', {
onEventHandler: unregisterRunnerOnEvent,
logRetention: logs.RetentionDays.ONE_DAY,
});
const unregisterRunnerCR = new CustomResource(this, 'unregisterRunnerCR', {
resourceType: 'Custom::unregisterRunnerProvider',
serviceToken: unregisterRunnerProvider.serviceToken,
properties: {
BucketName: runnerBucket.bucketName,
GitlabUrl: runnerProps.gitlaburl,
},
});
runnerBucket.grantReadWrite(unregisterRunnerOnEvent);
unregisterRunnerCR.node.addDependency(runnerBucket);
this.runnerRole.addManagedPolicy(
ManagedPolicy.fromAwsManagedPolicyName('AmazonSSMManagedInstanceCore'),
);
new CfnOutput(this, 'Runner-Role-Arn', {
value: this.runnerRole.roleArn,
});
}