Skip to content

Commit 4c63f09

Browse files
authored
feat(amplify-domain): Added config for auto subdomain creation (#13342)
---- *By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license*
1 parent 66f7053 commit 4c63f09

File tree

4 files changed

+140
-1
lines changed

4 files changed

+140
-1
lines changed

packages/@aws-cdk/aws-amplify/README.md

+4-1
Original file line numberDiff line numberDiff line change
@@ -122,7 +122,10 @@ mySinglePageApp.addCustomRule(amplify.CustomRule.SINGLE_PAGE_APPLICATION_REDIREC
122122
Add a domain and map sub domains to branches:
123123

124124
```ts
125-
const domain = amplifyApp.addDomain('example.com');
125+
const domain = amplifyApp.addDomain('example.com', {
126+
enableAutoSubdomain: true, // in case subdomains should be auto registered for branches
127+
autoSubdomainCreationPatterns: ['*', 'pr*'], // regex for branches that should auto register subdomains
128+
});
126129
domain.mapRoot(master); // map master branch to domain root
127130
domain.mapSubDomain(master, 'www');
128131
domain.mapSubDomain(dev); // sub domain prefix defaults to branch name

packages/@aws-cdk/aws-amplify/lib/app.ts

+1
Original file line numberDiff line numberDiff line change
@@ -289,6 +289,7 @@ export class App extends Resource implements IApp, iam.IGrantable {
289289
return new Domain(this, id, {
290290
...options,
291291
app: this,
292+
autoSubDomainIamRole: this.grantPrincipal as iam.IRole,
292293
});
293294
}
294295
}

packages/@aws-cdk/aws-amplify/lib/domain.ts

+24
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import * as iam from '@aws-cdk/aws-iam';
12
import { Lazy, Resource, IResolvable } from '@aws-cdk/core';
23
import { Construct } from 'constructs';
34
import { CfnDomain } from './amplify.generated';
@@ -21,6 +22,20 @@ export interface DomainOptions {
2122
* @default - use `addSubDomain()` to add subdomains
2223
*/
2324
readonly subDomains?: SubDomain[];
25+
26+
/**
27+
* Automatically create subdomains for connected branches
28+
*
29+
* @default false
30+
*/
31+
readonly enableAutoSubdomain?: boolean;
32+
33+
/**
34+
* Branches which should automatically create subdomains
35+
*
36+
* @default - all repository branches ['*', 'pr*']
37+
*/
38+
readonly autoSubdomainCreationPatterns?: string[];
2439
}
2540

2641
/**
@@ -31,6 +46,12 @@ export interface DomainProps extends DomainOptions {
3146
* The application to which the domain must be connected
3247
*/
3348
readonly app: IApp;
49+
50+
/**
51+
* The IAM role with access to Route53 when using enableAutoSubdomain
52+
* @default the IAM role from App.grantPrincipal
53+
*/
54+
readonly autoSubDomainIamRole?: iam.IRole;
3455
}
3556

3657
/**
@@ -106,6 +127,9 @@ export class Domain extends Resource {
106127
appId: props.app.appId,
107128
domainName,
108129
subDomainSettings: Lazy.any({ produce: () => this.renderSubDomainSettings() }, { omitEmptyArray: true }),
130+
enableAutoSubDomain: !!props.enableAutoSubdomain,
131+
autoSubDomainCreationPatterns: props.autoSubdomainCreationPatterns || ['*', 'pr*'],
132+
autoSubDomainIamRole: props.autoSubDomainIamRole?.roleArn,
109133
});
110134

111135
this.arn = domain.attrArn;

packages/@aws-cdk/aws-amplify/test/domain.test.ts

+111
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import * as iam from '@aws-cdk/aws-iam';
12
import '@aws-cdk/assert/jest';
23
import { App, SecretValue, Stack } from '@aws-cdk/core';
34
import * as amplify from '../lib';
@@ -120,3 +121,113 @@ test('throws at synthesis without subdomains', () => {
120121
// THEN
121122
expect(() => app.synth()).toThrow(/The domain doesn't contain any subdomains/);
122123
});
124+
125+
test('auto subdomain all branches', () => {
126+
// GIVEN
127+
const stack = new Stack();
128+
const app = new amplify.App(stack, 'App', {
129+
sourceCodeProvider: new amplify.GitHubSourceCodeProvider({
130+
owner: 'aws',
131+
repository: 'aws-cdk',
132+
oauthToken: SecretValue.plainText('secret'),
133+
}),
134+
});
135+
const prodBranch = app.addBranch('master');
136+
137+
// WHEN
138+
const domain = app.addDomain('amazon.com', {
139+
enableAutoSubdomain: true,
140+
});
141+
domain.mapRoot(prodBranch);
142+
143+
// THEN
144+
expect(stack).toHaveResource('AWS::Amplify::Domain', {
145+
EnableAutoSubDomain: true,
146+
AutoSubDomainCreationPatterns: [
147+
'*',
148+
'pr*',
149+
],
150+
AutoSubDomainIAMRole: {
151+
'Fn::GetAtt': [
152+
'AppRole1AF9B530',
153+
'Arn',
154+
],
155+
},
156+
});
157+
});
158+
159+
test('auto subdomain some branches', () => {
160+
// GIVEN
161+
const stack = new Stack();
162+
const app = new amplify.App(stack, 'App', {
163+
sourceCodeProvider: new amplify.GitHubSourceCodeProvider({
164+
owner: 'aws',
165+
repository: 'aws-cdk',
166+
oauthToken: SecretValue.plainText('secret'),
167+
}),
168+
});
169+
const prodBranch = app.addBranch('master');
170+
171+
// WHEN
172+
const domain = app.addDomain('amazon.com', {
173+
enableAutoSubdomain: true,
174+
autoSubdomainCreationPatterns: ['features/**'],
175+
});
176+
domain.mapRoot(prodBranch);
177+
178+
// THEN
179+
expect(stack).toHaveResource('AWS::Amplify::Domain', {
180+
EnableAutoSubDomain: true,
181+
AutoSubDomainCreationPatterns: ['features/**'],
182+
AutoSubDomainIAMRole: {
183+
'Fn::GetAtt': [
184+
'AppRole1AF9B530',
185+
'Arn',
186+
],
187+
},
188+
});
189+
});
190+
191+
test('auto subdomain with IAM role', () => {
192+
// GIVEN
193+
const stack = new Stack();
194+
const app = new amplify.App(stack, 'App', {
195+
sourceCodeProvider: new amplify.GitHubSourceCodeProvider({
196+
owner: 'aws',
197+
repository: 'aws-cdk',
198+
oauthToken: SecretValue.plainText('secret'),
199+
}),
200+
role: iam.Role.fromRoleArn(
201+
stack,
202+
'AmplifyRole',
203+
`arn:aws:iam::${Stack.of(stack).account}:role/AmplifyRole`,
204+
{ mutable: false },
205+
),
206+
});
207+
const prodBranch = app.addBranch('master');
208+
209+
// WHEN
210+
const domain = app.addDomain('amazon.com', {
211+
enableAutoSubdomain: true,
212+
autoSubdomainCreationPatterns: ['features/**'],
213+
});
214+
domain.mapRoot(prodBranch);
215+
216+
// THEN
217+
expect(stack).toHaveResource('AWS::Amplify::Domain', {
218+
EnableAutoSubDomain: true,
219+
AutoSubDomainCreationPatterns: ['features/**'],
220+
AutoSubDomainIAMRole: {
221+
'Fn::Join': [
222+
'',
223+
[
224+
'arn:aws:iam::',
225+
{
226+
Ref: 'AWS::AccountId',
227+
},
228+
':role/AmplifyRole',
229+
],
230+
],
231+
},
232+
});
233+
});

0 commit comments

Comments
 (0)