From 1e0fea72fc1d0282e65517bcc70e030b6f41637a Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Thu, 23 Jul 2020 12:00:37 -0700 Subject: [PATCH 01/17] initial changes (breaks) --- .../@aws-cdk/aws-appsync/lib/data-source.ts | 6 +- .../aws-appsync/lib/graphqlapi-base.ts | 141 ++++++++++++++++++ .../@aws-cdk/aws-appsync/lib/graphqlapi.ts | 119 ++++----------- packages/@aws-cdk/aws-appsync/lib/index.ts | 1 + packages/@aws-cdk/aws-appsync/lib/resolver.ts | 8 +- .../@aws-cdk/aws-appsync/test/appsync.test.ts | 4 +- .../aws-appsync/test/integ.graphql.ts | 4 +- 7 files changed, 185 insertions(+), 98 deletions(-) create mode 100644 packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts diff --git a/packages/@aws-cdk/aws-appsync/lib/data-source.ts b/packages/@aws-cdk/aws-appsync/lib/data-source.ts index 0daf1f996a452..0cd2a2995930a 100644 --- a/packages/@aws-cdk/aws-appsync/lib/data-source.ts +++ b/packages/@aws-cdk/aws-appsync/lib/data-source.ts @@ -3,7 +3,7 @@ import { IGrantable, IPrincipal, IRole, Role, ServicePrincipal } from '@aws-cdk/ import { IFunction } from '@aws-cdk/aws-lambda'; import { Construct, IResolvable } from '@aws-cdk/core'; import { CfnDataSource } from './appsync.generated'; -import { GraphQLApi } from './graphqlapi'; +import { IGraphQLApi } from './graphqlapi-base'; import { BaseResolverProps, Resolver } from './resolver'; /** @@ -13,7 +13,7 @@ export interface BaseDataSourceProps { /** * The API to attach this data source to */ - readonly api: GraphQLApi; + readonly api: IGraphQLApi; /** * The name of the data source */ @@ -91,7 +91,7 @@ export abstract class BaseDataSource extends Construct { */ public readonly ds: CfnDataSource; - protected api: GraphQLApi; + protected api: IGraphQLApi; protected serviceRole?: IRole; constructor(scope: Construct, id: string, props: BackedDataSourceProps, extended: ExtendedDataSourceProps) { diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts new file mode 100644 index 0000000000000..dd2881f1006d4 --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -0,0 +1,141 @@ +import { ITable } from '@aws-cdk/aws-dynamodb'; +import { IFunction } from '@aws-cdk/aws-lambda'; +import { IResource, Resource } from '@aws-cdk/core'; +import { CfnGraphQLSchema } from './appsync.generated'; +import { DynamoDbDataSource, HttpDataSource, LambdaDataSource, NoneDataSource } from './data-source'; +/** + * Interface for GraphQL + */ +export interface IGraphQLApi extends IResource { + /** + * the id of the GraphQL API + * + * @attribute + */ + readonly apiId: string; + /** + * the ARN of the API + * + * @attribute + */ + readonly arn: string; + /** + * schema + */ + readonly schema?: CfnGraphQLSchema; + + /** + * add a new dummy data source to this API + * @param name The name of the data source + * @param description The description of the data source + */ + addNoneDataSource(name: string, description: string): NoneDataSource; + + /** + * add a new DynamoDB data source to this API + * @param name The name of the data source + * @param description The description of the data source + * @param table The DynamoDB table backing this data source [disable-awslint:ref-via-interface] + */ + addDynamoDbDataSource( name: string, description: string, table: ITable ): DynamoDbDataSource; + + /** + * add a new http data source to this API + * @param name The name of the data source + * @param description The description of the data source + * @param endpoint The http endpoint + */ + addHttpDataSource(name: string, description: string, endpoint: string): HttpDataSource; + + /** + * add a new Lambda data source to this API + * @param name The name of the data source + * @param description The description of the data source + * @param lambdaFunction The Lambda function to call to interact with this data source + */ + addLambdaDataSource( name: string, description: string, lambdaFunction: IFunction ): LambdaDataSource; +} + +/** + * Base Class for GraphQL API + */ +export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { + /** + * the id of the GraphQL API + */ + public abstract readonly apiId: string; + /** + * the ARN of the API + */ + public abstract readonly arn: string; + /** + * schema + */ + public abstract readonly schema?: CfnGraphQLSchema; + + /** + * add a new dummy data source to this API + * @param name The name of the data source + * @param description The description of the data source + */ + public addNoneDataSource(name: string, description: string): NoneDataSource { + return new NoneDataSource(this, `${name}DS`, { + api: this, + description, + name, + }); + } + + /** + * add a new DynamoDB data source to this API + * @param name The name of the data source + * @param description The description of the data source + * @param table The DynamoDB table backing this data source [disable-awslint:ref-via-interface] + */ + public addDynamoDbDataSource( + name: string, + description: string, + table: ITable, + ): DynamoDbDataSource { + return new DynamoDbDataSource(this, `${name}DS`, { + api: this, + description, + name, + table, + }); + } + + /** + * add a new http data source to this API + * @param name The name of the data source + * @param description The description of the data source + * @param endpoint The http endpoint + */ + public addHttpDataSource(name: string, description: string, endpoint: string): HttpDataSource { + return new HttpDataSource(this, `${name}DS`, { + api: this, + description, + endpoint, + name, + }); + } + + /** + * add a new Lambda data source to this API + * @param name The name of the data source + * @param description The description of the data source + * @param lambdaFunction The Lambda function to call to interact with this data source + */ + public addLambdaDataSource( + name: string, + description: string, + lambdaFunction: IFunction, + ): LambdaDataSource { + return new LambdaDataSource(this, `${name}DS`, { + api: this, + description, + name, + lambdaFunction, + }); + } +} \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index e5683ef98d9d6..b4b0e5616007c 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -1,19 +1,9 @@ +import { readFileSync } from 'fs'; import { IUserPool } from '@aws-cdk/aws-cognito'; -import { ITable } from '@aws-cdk/aws-dynamodb'; -import { - ManagedPolicy, - Role, - ServicePrincipal, -} from '@aws-cdk/aws-iam'; -import { IFunction } from '@aws-cdk/aws-lambda'; +import { ManagedPolicy, Role, ServicePrincipal } from '@aws-cdk/aws-iam'; import { Construct, Duration, IResolvable } from '@aws-cdk/core'; -import { readFileSync } from 'fs'; -import { - CfnApiKey, - CfnGraphQLApi, - CfnGraphQLSchema, -} from './appsync.generated'; -import { DynamoDbDataSource, HttpDataSource, LambdaDataSource, NoneDataSource } from './data-source'; +import { CfnApiKey, CfnGraphQLApi, CfnGraphQLSchema } from './appsync.generated'; +import { IGraphQLApi, GraphQLApiBase } from './graphqlapi-base'; /** * enum with all possible values for AppSync authorization type @@ -218,7 +208,7 @@ export interface GraphQLApiProps { /** * the name of the GraphQL API */ - readonly name: string; + readonly apiName: string; /** * Optional authorization configuration @@ -249,11 +239,26 @@ export interface GraphQLApiProps { } +export interface GraphQLApiAttributes { + readonly arn: string, + readonly schema?: CfnGraphQLSchema, +} + /** * An AppSync GraphQL API */ -export class GraphQLApi extends Construct { - +export class GraphQLApi extends GraphQLApiBase { + public static fromArn(scope: Construct, id: string, attr: GraphQLApiAttributes): IGraphQLApi { + class Import extends GraphQLApiBase { + public readonly apiId = 'replace'; + public readonly arn = attr.arn; + public readonly schema = attr.schema; + constructor (s: Construct, i: string){ + super(s, i); + } + } + return new Import(scope, id); + } /** * the id of the GraphQL API */ @@ -264,12 +269,14 @@ export class GraphQLApi extends Construct { public readonly arn: string; /** * the URL of the endpoint created by AppSync + * + * @attribute */ public readonly graphQlUrl: string; /** * the name of the API */ - public name: string; + public readonly name: string; /** * underlying CFN schema resource */ @@ -285,7 +292,9 @@ export class GraphQLApi extends Construct { private _apiKey?: string; constructor(scope: Construct, id: string, props: GraphQLApiProps) { - super(scope, id); + super(scope, id, { + physicalName: props.apiName, + }); this.validateAuthorizationProps(props); const defaultAuthorizationType = @@ -305,7 +314,7 @@ export class GraphQLApi extends Construct { } this.api = new CfnGraphQLApi(this, 'Resource', { - name: props.name, + name: props.apiName, authenticationType: defaultAuthorizationType, ...(props.logConfig && { logConfig: { @@ -337,7 +346,7 @@ export class GraphQLApi extends Construct { this.apiId = this.api.attrApiId; this.arn = this.api.attrArn; this.graphQlUrl = this.api.attrGraphQlUrl; - this.name = this.api.name; + this.name = this.api.name;= if ( defaultAuthorizationType === AuthorizationType.API_KEY || @@ -367,72 +376,6 @@ export class GraphQLApi extends Construct { }); } - /** - * add a new dummy data source to this API - * @param name The name of the data source - * @param description The description of the data source - */ - public addNoneDataSource(name: string, description: string): NoneDataSource { - return new NoneDataSource(this, `${name}DS`, { - api: this, - description, - name, - }); - } - - /** - * add a new DynamoDB data source to this API - * @param name The name of the data source - * @param description The description of the data source - * @param table The DynamoDB table backing this data source [disable-awslint:ref-via-interface] - */ - public addDynamoDbDataSource( - name: string, - description: string, - table: ITable, - ): DynamoDbDataSource { - return new DynamoDbDataSource(this, `${name}DS`, { - api: this, - description, - name, - table, - }); - } - - /** - * add a new http data source to this API - * @param name The name of the data source - * @param description The description of the data source - * @param endpoint The http endpoint - */ - public addHttpDataSource(name: string, description: string, endpoint: string): HttpDataSource { - return new HttpDataSource(this, `${name}DS`, { - api: this, - description, - endpoint, - name, - }); - } - - /** - * add a new Lambda data source to this API - * @param name The name of the data source - * @param description The description of the data source - * @param lambdaFunction The Lambda function to call to interact with this data source - */ - public addLambdaDataSource( - name: string, - description: string, - lambdaFunction: IFunction, - ): LambdaDataSource { - return new LambdaDataSource(this, `${name}DS`, { - api: this, - description, - name, - lambdaFunction, - }); - } - private validateAuthorizationProps(props: GraphQLApiProps) { const defaultAuthorizationType = props.authorizationConfig?.defaultAuthorization?.authorizationType || @@ -565,4 +508,4 @@ export class GraphQLApi extends Construct { const authModes = props.authorizationConfig?.additionalAuthorizationModes; return authModes ? this.formatAdditionalAuthorizationModes(authModes) : undefined; } -} +} \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/lib/index.ts b/packages/@aws-cdk/aws-appsync/lib/index.ts index 852cbed1c54f6..e0736c1ecc397 100644 --- a/packages/@aws-cdk/aws-appsync/lib/index.ts +++ b/packages/@aws-cdk/aws-appsync/lib/index.ts @@ -5,3 +5,4 @@ export * from './data-source'; export * from './mapping-template'; export * from './resolver'; export * from './graphqlapi'; +export * from './graphqlapi-base'; diff --git a/packages/@aws-cdk/aws-appsync/lib/resolver.ts b/packages/@aws-cdk/aws-appsync/lib/resolver.ts index ef5e524ac75ae..477e9676cffd0 100644 --- a/packages/@aws-cdk/aws-appsync/lib/resolver.ts +++ b/packages/@aws-cdk/aws-appsync/lib/resolver.ts @@ -1,7 +1,7 @@ import { Construct, IResolvable } from '@aws-cdk/core'; import { CfnResolver } from './appsync.generated'; import { BaseDataSource } from './data-source'; -import { GraphQLApi } from './graphqlapi'; +import { IGraphQLApi } from './graphqlapi-base'; import { MappingTemplate } from './mapping-template'; /** * Basic properties for an AppSync resolver @@ -42,7 +42,7 @@ export interface ResolverProps extends BaseResolverProps { /** * The API this resolver is attached to */ - readonly api: GraphQLApi; + readonly api: IGraphQLApi; /** * The data source this resolver is using * @@ -74,7 +74,9 @@ export class Resolver extends Construct { requestMappingTemplate: props.requestMappingTemplate ? props.requestMappingTemplate.renderTemplate() : undefined, responseMappingTemplate: props.responseMappingTemplate ? props.responseMappingTemplate.renderTemplate() : undefined, }); - this.resolver.addDependsOn(props.api.schema); + // if (props.api.schema) { + // this.resolver.addDependsOn(props.api.schema); + // } if (props.dataSource) { this.resolver.addDependsOn(props.dataSource.ds); } diff --git a/packages/@aws-cdk/aws-appsync/test/appsync.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync.test.ts index edb263eed6800..1c7d00c5a31b6 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync.test.ts @@ -1,6 +1,6 @@ import '@aws-cdk/assert/jest'; -import * as cdk from '@aws-cdk/core'; import * as path from 'path'; +import * as cdk from '@aws-cdk/core'; import * as appsync from '../lib'; test('should not throw an Error', () => { @@ -11,7 +11,7 @@ test('should not throw an Error', () => { const when = () => { new appsync.GraphQLApi(stack, 'api', { authorizationConfig: {}, - name: 'api', + apiName: 'api', schemaDefinitionFile: path.join(__dirname, 'schema.graphql'), }); }; diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts b/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts index 5ced7472fcb05..42de09e6ae072 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts @@ -1,7 +1,7 @@ +import { join } from 'path'; import { UserPool } from '@aws-cdk/aws-cognito'; import { AttributeType, BillingMode, Table } from '@aws-cdk/aws-dynamodb'; import { App, RemovalPolicy, Stack } from '@aws-cdk/core'; -import { join } from 'path'; import { AuthorizationType, GraphQLApi, @@ -34,7 +34,7 @@ const userPool = new UserPool(stack, 'Pool', { }); const api = new GraphQLApi(stack, 'Api', { - name: 'demoapi', + apiName: 'demoapi', schemaDefinitionFile: join(__dirname, 'schema.graphql'), authorizationConfig: { defaultAuthorization: { From 748b1c2916d4ad81a5c9a06719542cd309a4cc2d Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Fri, 24 Jul 2020 12:58:03 -0700 Subject: [PATCH 02/17] non breaking --- .../aws-appsync/lib/graphqlapi-base.ts | 33 ++++++------ .../@aws-cdk/aws-appsync/lib/graphqlapi.ts | 52 ++++++++++++++----- packages/@aws-cdk/aws-appsync/lib/resolver.ts | 4 +- packages/@aws-cdk/aws-appsync/package.json | 3 +- .../@aws-cdk/aws-appsync/test/appsync.test.ts | 2 +- .../aws-appsync/test/integ.graphql.ts | 2 +- 6 files changed, 62 insertions(+), 34 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index dd2881f1006d4..08735594a4022 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -1,7 +1,6 @@ import { ITable } from '@aws-cdk/aws-dynamodb'; import { IFunction } from '@aws-cdk/aws-lambda'; -import { IResource, Resource } from '@aws-cdk/core'; -import { CfnGraphQLSchema } from './appsync.generated'; +import { CfnResource, IResource, Resource } from '@aws-cdk/core'; import { DynamoDbDataSource, HttpDataSource, LambdaDataSource, NoneDataSource } from './data-source'; /** * Interface for GraphQL @@ -19,11 +18,6 @@ export interface IGraphQLApi extends IResource { * @attribute */ readonly arn: string; - /** - * schema - */ - readonly schema?: CfnGraphQLSchema; - /** * add a new dummy data source to this API * @param name The name of the data source @@ -54,6 +48,12 @@ export interface IGraphQLApi extends IResource { * @param lambdaFunction The Lambda function to call to interact with this data source */ addLambdaDataSource( name: string, description: string, lambdaFunction: IFunction ): LambdaDataSource; + + /** + * Add schema dependency if not imported + * @param construct the construct that has a dependency + */ + addSchemaDependency( construct: CfnResource ): boolean; } /** @@ -68,10 +68,6 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * the ARN of the API */ public abstract readonly arn: string; - /** - * schema - */ - public abstract readonly schema?: CfnGraphQLSchema; /** * add a new dummy data source to this API @@ -126,11 +122,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * @param description The description of the data source * @param lambdaFunction The Lambda function to call to interact with this data source */ - public addLambdaDataSource( - name: string, - description: string, - lambdaFunction: IFunction, - ): LambdaDataSource { + public addLambdaDataSource( name: string, description: string, lambdaFunction: IFunction ): LambdaDataSource { return new LambdaDataSource(this, `${name}DS`, { api: this, description, @@ -138,4 +130,13 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { lambdaFunction, }); } + + /** + * Add schema dependency if not imported + * @param construct the construct that has a dependency + */ + public addSchemaDependency( construct: CfnResource ): boolean { + construct; + return false; + } } \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index b4b0e5616007c..2624e73c178b7 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -1,7 +1,7 @@ import { readFileSync } from 'fs'; import { IUserPool } from '@aws-cdk/aws-cognito'; import { ManagedPolicy, Role, ServicePrincipal } from '@aws-cdk/aws-iam'; -import { Construct, Duration, IResolvable } from '@aws-cdk/core'; +import { CfnResource, Construct, Duration, IResolvable, PhysicalName } from '@aws-cdk/core'; import { CfnApiKey, CfnGraphQLApi, CfnGraphQLSchema } from './appsync.generated'; import { IGraphQLApi, GraphQLApiBase } from './graphqlapi-base'; @@ -204,11 +204,10 @@ export interface LogConfig { * Properties for an AppSync GraphQL API */ export interface GraphQLApiProps { - /** * the name of the GraphQL API */ - readonly apiName: string; + readonly name: string; /** * Optional authorization configuration @@ -239,20 +238,42 @@ export interface GraphQLApiProps { } +/** + * Attributes for GraphQL From + */ export interface GraphQLApiAttributes { + /** + * the arn for the GraphQL API + */ readonly arn: string, - readonly schema?: CfnGraphQLSchema, } /** * An AppSync GraphQL API + * + * @resource AWS::AppSync::GraphQLApi */ export class GraphQLApi extends GraphQLApiBase { - public static fromArn(scope: Construct, id: string, attr: GraphQLApiAttributes): IGraphQLApi { + /** + * Import a GraphQL API given an arn + * @param scope scope + * @param id id + * @param graphQLApiArn the arn of the api + */ + public static fromGraphQLApiArn(scope: Construct, id: string, graphQLApiArn: string): IGraphQLApi { + return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: graphQLApiArn }); + } + + /** + * Import a GraphQL API through this function + * @param scope scope + * @param id id + * @param attr GraphQL API Attributes of an API + */ + public static fromGraphQLApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { class Import extends GraphQLApiBase { public readonly apiId = 'replace'; - public readonly arn = attr.arn; - public readonly schema = attr.schema; + public readonly arn = attrs.arn; constructor (s: Construct, i: string){ super(s, i); } @@ -292,9 +313,7 @@ export class GraphQLApi extends GraphQLApiBase { private _apiKey?: string; constructor(scope: Construct, id: string, props: GraphQLApiProps) { - super(scope, id, { - physicalName: props.apiName, - }); + super(scope, id); this.validateAuthorizationProps(props); const defaultAuthorizationType = @@ -314,7 +333,7 @@ export class GraphQLApi extends GraphQLApiBase { } this.api = new CfnGraphQLApi(this, 'Resource', { - name: props.apiName, + name: props.name, authenticationType: defaultAuthorizationType, ...(props.logConfig && { logConfig: { @@ -346,7 +365,7 @@ export class GraphQLApi extends GraphQLApiBase { this.apiId = this.api.attrApiId; this.arn = this.api.attrArn; this.graphQlUrl = this.api.attrGraphQlUrl; - this.name = this.api.name;= + this.name = this.api.name; if ( defaultAuthorizationType === AuthorizationType.API_KEY || @@ -439,6 +458,15 @@ export class GraphQLApi extends GraphQLApiBase { } } + /** + * Add schema dependency if not imported + * @param construct the construct that has a dependency + */ + public addSchemaDependency( construct: CfnResource ): boolean { + construct.addDependsOn(this.schema); + return true; + } + private formatOpenIdConnectConfig( config: OpenIdConnectConfig, ): CfnGraphQLApi.OpenIDConnectConfigProperty { diff --git a/packages/@aws-cdk/aws-appsync/lib/resolver.ts b/packages/@aws-cdk/aws-appsync/lib/resolver.ts index 477e9676cffd0..82adceff6b54d 100644 --- a/packages/@aws-cdk/aws-appsync/lib/resolver.ts +++ b/packages/@aws-cdk/aws-appsync/lib/resolver.ts @@ -74,9 +74,7 @@ export class Resolver extends Construct { requestMappingTemplate: props.requestMappingTemplate ? props.requestMappingTemplate.renderTemplate() : undefined, responseMappingTemplate: props.responseMappingTemplate ? props.responseMappingTemplate.renderTemplate() : undefined, }); - // if (props.api.schema) { - // this.resolver.addDependsOn(props.api.schema); - // } + props.api.addSchemaDependency(this.resolver); if (props.dataSource) { this.resolver.addDependsOn(props.dataSource.ds); } diff --git a/packages/@aws-cdk/aws-appsync/package.json b/packages/@aws-cdk/aws-appsync/package.json index ed431e29e7367..56885925745c8 100644 --- a/packages/@aws-cdk/aws-appsync/package.json +++ b/packages/@aws-cdk/aws-appsync/package.json @@ -94,7 +94,8 @@ "exclude": [ "no-unused-type:@aws-cdk/aws-appsync.ApiKeyConfig", "no-unused-type:@aws-cdk/aws-appsync.UserPoolConfig", - "no-unused-type:@aws-cdk/aws-appsync.UserPoolDefaultAction" + "no-unused-type:@aws-cdk/aws-appsync.UserPoolDefaultAction", + "props-physical-name:@aws-cdk/aws-appsync.GraphQLApiProps" ] }, "stability": "experimental", diff --git a/packages/@aws-cdk/aws-appsync/test/appsync.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync.test.ts index 1c7d00c5a31b6..1d0e01459840b 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync.test.ts @@ -11,7 +11,7 @@ test('should not throw an Error', () => { const when = () => { new appsync.GraphQLApi(stack, 'api', { authorizationConfig: {}, - apiName: 'api', + name: 'api', schemaDefinitionFile: path.join(__dirname, 'schema.graphql'), }); }; diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts b/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts index 42de09e6ae072..6ee6a1603764b 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts @@ -34,7 +34,7 @@ const userPool = new UserPool(stack, 'Pool', { }); const api = new GraphQLApi(stack, 'Api', { - apiName: 'demoapi', + name: 'demoapi', schemaDefinitionFile: join(__dirname, 'schema.graphql'), authorizationConfig: { defaultAuthorization: { From 7b77d4318ac00389d22ad1618ce0f673f4128165 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Fri, 24 Jul 2020 13:05:43 -0700 Subject: [PATCH 03/17] remove unneccesary imports --- packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index 2624e73c178b7..d588ed3724880 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -1,7 +1,7 @@ import { readFileSync } from 'fs'; import { IUserPool } from '@aws-cdk/aws-cognito'; import { ManagedPolicy, Role, ServicePrincipal } from '@aws-cdk/aws-iam'; -import { CfnResource, Construct, Duration, IResolvable, PhysicalName } from '@aws-cdk/core'; +import { CfnResource, Construct, Duration, IResolvable } from '@aws-cdk/core'; import { CfnApiKey, CfnGraphQLApi, CfnGraphQLSchema } from './appsync.generated'; import { IGraphQLApi, GraphQLApiBase } from './graphqlapi-base'; From fc12e14d514eea886d9ceaa032fb80f185e3f2d2 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Fri, 24 Jul 2020 13:08:36 -0700 Subject: [PATCH 04/17] merging master sucks --- packages/@aws-cdk/aws-appsync/.gitignore | 3 +- .../aws-appsync/test/verify/iam-query.js | 40 +++++++++++++++++++ 2 files changed, 42 insertions(+), 1 deletion(-) create mode 100644 packages/@aws-cdk/aws-appsync/test/verify/iam-query.js diff --git a/packages/@aws-cdk/aws-appsync/.gitignore b/packages/@aws-cdk/aws-appsync/.gitignore index d8a8561d50885..e0a8bac32ac3f 100644 --- a/packages/@aws-cdk/aws-appsync/.gitignore +++ b/packages/@aws-cdk/aws-appsync/.gitignore @@ -16,4 +16,5 @@ nyc.config.js !.eslintrc.js !jest.config.js -junit.xml \ No newline at end of file +!test/verify/*.js +junit.xml diff --git a/packages/@aws-cdk/aws-appsync/test/verify/iam-query.js b/packages/@aws-cdk/aws-appsync/test/verify/iam-query.js new file mode 100644 index 0000000000000..11e895d2e2c54 --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/verify/iam-query.js @@ -0,0 +1,40 @@ +require('isomorphic-fetch'); +const AWS = require('aws-sdk/global'); +const gql = require('graphql-tag'); +const appsync = require('aws-appsync'); + +const config = { + url: process.env.APPSYNC_ENDPOINT, + region: process.env.AWS_REGION, + auth: { + type: appsync.AUTH_TYPE.AWS_IAM, + credentials: AWS.config.credentials, + }, + disableOffline: true +}; + +const getTests = +`query getTests { + getTests { + id + version + } +}`; + +const client = new appsync.AWSAppSyncClient(config); + +exports.handler = (event, context, callback) => { + + (async () => { + try { + const result = await client.query({ + query: gql(getTests) + }); + console.log(result.data); + callback(null, result.data); + } catch (e) { + console.warn('Error sending mutation: ', e); + callback(Error(e)); + } + })(); +}; \ No newline at end of file From 3bde2e92e0e225f27c553bf37ca202631ac6bdcc Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Fri, 24 Jul 2020 17:44:27 -0700 Subject: [PATCH 05/17] prelimin tests --- .../@aws-cdk/aws-appsync/lib/graphqlapi.ts | 17 +++--- .../aws-appsync/test/appsync-apikey.test.ts | 2 +- .../aws-appsync/test/appsync-import.test.ts | 60 +++++++++++++++++++ .../aws-appsync/test/integ.api-import.ts | 60 +++++++++++++++++++ 4 files changed, 128 insertions(+), 11 deletions(-) create mode 100644 packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts create mode 100644 packages/@aws-cdk/aws-appsync/test/integ.api-import.ts diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index 405a16b33b26b..d9e4ff4465ba7 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -1,7 +1,7 @@ import { readFileSync } from 'fs'; import { IUserPool } from '@aws-cdk/aws-cognito'; import { ManagedPolicy, Role, ServicePrincipal, Grant, IGrantable } from '@aws-cdk/aws-iam'; -import { CfnResource, Construct, Duration, IResolvable, Stack } from '@aws-cdk/core'; +import { CfnResource, Construct, Duration, Fn, IResolvable, Stack } from '@aws-cdk/core'; import { CfnApiKey, CfnGraphQLApi, CfnGraphQLSchema } from './appsync.generated'; import { IGraphQLApi, GraphQLApiBase } from './graphqlapi-base'; @@ -309,7 +309,7 @@ export interface GraphQLApiAttributes { /** * the api id of the GraphQL Api */ - readonly api: string, + readonly apiId: string, } /** @@ -329,7 +329,7 @@ export class GraphQLApi extends GraphQLApiBase { service: 'appsync', resource: `apis/${graphQLApiId}`, }); - return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: generatedArn, api: graphQLApiId}); + return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: generatedArn, apiId: graphQLApiId}); } /** @@ -339,11 +339,11 @@ export class GraphQLApi extends GraphQLApiBase { * @param graphQLApiArn the arn of the api */ public static fromGraphQLApiArn(scope: Construct, id: string, graphQLApiArn: string): IGraphQLApi { - const apiId = graphQLApiArn.split('/').slice(-1)[0]; - if (apiId == undefined) { + const apiId = Fn.select(1, Fn.split('/', graphQLApiArn)); + if (apiId == undefined || apiId == graphQLApiArn) { throw Error('Arn does not contain a valid apiId'); } - return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: graphQLApiArn, api: apiId}); + return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: graphQLApiArn, apiId: apiId}); } /** @@ -353,11 +353,8 @@ export class GraphQLApi extends GraphQLApiBase { * @param attrs GraphQL API Attributes of an API */ public static fromGraphQLApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { - if (attrs.arn == undefined && attrs.api == undefined ){ - throw Error('Attributes requires either arn or api attribute'); - } class Import extends GraphQLApiBase { - public readonly apiId = attrs.api; + public readonly apiId = attrs.apiId; public readonly arn = attrs.arn; constructor (s: Construct, i: string){ super(s, i); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-apikey.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-apikey.test.ts index da49317ee5a64..dacedbf03d4fc 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-apikey.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-apikey.test.ts @@ -1,6 +1,6 @@ import '@aws-cdk/assert/jest'; -import * as cdk from '@aws-cdk/core'; import * as path from 'path'; +import * as cdk from '@aws-cdk/core'; import * as appsync from '../lib'; describe('AppSync Authorization Config', () => { diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts new file mode 100644 index 0000000000000..ab2709435f567 --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts @@ -0,0 +1,60 @@ +import * as path from 'path'; +import '@aws-cdk/assert/jest'; +import * as cdk from '@aws-cdk/core'; +import * as appsync from '../lib'; + +let stack: cdk.Stack; +let baseApi: appsync.GraphQLApi; +beforeEach( () => { + // Given + stack = new cdk.Stack(); + baseApi = new appsync.GraphQLApi(stack, 'baseApi', { + name: 'api', + schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), + }); +}); + +test('imported api can add NoneDataSource from id', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'importedApi', baseApi.apiId); + + api.addNoneDataSource('none', 'none data source with imported Api'); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); +}); + +test('imported api can add NoneDataSource from arn', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'importedApi', baseApi.arn); + + api.addNoneDataSource('none', 'none data source with imported Api'); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + ApiId: { 'Fn::Select': [ 1, { 'Fn::Split': [ '/', { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'Arn' ] } ] } ] }, + }); +}); + +test('imported api can add NoneDataSource from attributes', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + apiId: baseApi.apiId, + arn: baseApi.arn, + }); + + api.addNoneDataSource('none', 'none data source with imported Api'); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); +}); + diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts new file mode 100644 index 0000000000000..79515fb65a96f --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts @@ -0,0 +1,60 @@ +import * as path from 'path'; +import * as db from '@aws-cdk/aws-dynamodb'; +import * as cdk from '@aws-cdk/core'; +import * as appsync from '../lib'; + +/* + * Creates an Appsync GraphQL API in a separate stack. + * Add dependencies to imported api. + * + * Stack verification steps: + * Install dependencies and deploy integration test. Check if data sources are + * connected to the graphQL Api + * + * -- cdk deploy --app 'node integ.api-import.js' stack -- start -- + * -- aws appsync list-graphql-apis -- obtain api id -- + * -- aws appsync list-data-sources --api-id [api_id] -- testDS/None -- + * -- cdk destroy --app 'node integ.api-import.js' stack baseStack -- clean -- + */ + +const app = new cdk.App(); +const baseStack = new cdk.Stack(app, 'baseStack'); + +const baseApi = new appsync.GraphQLApi(baseStack, 'baseApi', { + name: 'baseApi', + schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), +}); + +const stack = new cdk.Stack(app, 'stack'); +const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'Api', `${baseApi.apiId}`); + +const testTable = new db.Table(stack, 'TestTable', { + billingMode: db.BillingMode.PAY_PER_REQUEST, + partitionKey: { + name: 'id', + type: db.AttributeType.STRING, + }, + removalPolicy: cdk.RemovalPolicy.DESTROY, +}); + +const testDS = api.addDynamoDbDataSource('testDataSource', 'test table data source', testTable); + +testDS.createResolver({ + typeName: 'Query', + fieldName: 'getTests', + requestMappingTemplate: appsync.MappingTemplate.dynamoDbScanTable(), + responseMappingTemplate: appsync.MappingTemplate.dynamoDbResultList(), +}); + +testDS.createResolver({ + typeName: 'Mutation', + fieldName: 'addTest', + requestMappingTemplate: appsync.MappingTemplate.dynamoDbPutItem(appsync.PrimaryKey.partition('id').auto(), appsync.Values.projecting('test')), + responseMappingTemplate: appsync.MappingTemplate.dynamoDbResultItem(), +}); + +const api2 = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'api2', baseApi.arn); + +api2.addNoneDataSource('none', 'none'); + +app.synth(); \ No newline at end of file From 48f782481b1ef41db9f972c79d48ff01b19752a8 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Fri, 24 Jul 2020 18:42:59 -0700 Subject: [PATCH 06/17] update readme --- packages/@aws-cdk/aws-appsync/README.md | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/packages/@aws-cdk/aws-appsync/README.md b/packages/@aws-cdk/aws-appsync/README.md index f9811ddd9c1be..9014d5988881e 100644 --- a/packages/@aws-cdk/aws-appsync/README.md +++ b/packages/@aws-cdk/aws-appsync/README.md @@ -81,6 +81,23 @@ demoDS.createResolver({ }); ``` +## Imports + +Any GraphQL Api can be imported from another stack. Utilizing the `fromXxx` +functions, you have the ability to add data sources and resolvers through +a `IGraphQLApi` interface. + +```ts +const importedApi = appsync.GraphQLApi.fromGraphQLApiId(...); +importedApi.addDynamoDbDataSource(...); +``` + +GraphQL Apis can be imported in three ways: +- `arn` through `GraphQLApi.fromGraphQLApiArn`: `apiId` is generated from parameter +- `apiId` through `GraphQLApi.fromGraphQLApiId`: `arn` is generated from parameter +- or both through `GraphQLApi.fromGraphQLApiAttributes`: both are specified + + ## Permissions When using `AWS_IAM` as the authorization type for GraphQL API, an IAM Role From a68e1f655d63de79530055dfd9aa17b268d1f6c4 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Mon, 27 Jul 2020 14:42:10 -0700 Subject: [PATCH 07/17] more unit tests for core data sources --- .../aws-appsync/test/appsync-import.test.ts | 116 +++++++++ .../test/integ.api-import.expected.json | 224 ++++++++++++++++++ .../aws-appsync/test/integ.api-import.ts | 2 + 3 files changed, 342 insertions(+) create mode 100644 packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts index ab2709435f567..3830dacf0a7f7 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts @@ -1,5 +1,7 @@ import * as path from 'path'; import '@aws-cdk/assert/jest'; +import * as db from '@aws-cdk/aws-dynamodb'; +import * as lambda from '@aws-cdk/aws-lambda'; import * as cdk from '@aws-cdk/core'; import * as appsync from '../lib'; @@ -58,3 +60,117 @@ test('imported api can add NoneDataSource from attributes', () => { }); }); +test('imported api can add DynamoDbDataSource from id', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'importedApi', baseApi.apiId); + const table = new db.Table(stack, 'table', { + partitionKey: { + name: 'key', + type: db.AttributeType.NUMBER, + }, + }); + api.addDynamoDbDataSource('db', 'db data source with imported Api', table); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); +}); + +test('imported api can add DynamoDbDataSource from arn', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'importedApi', baseApi.arn); + const table = new db.Table(stack, 'table', { + partitionKey: { + name: 'key', + type: db.AttributeType.NUMBER, + }, + }); + api.addDynamoDbDataSource('db', 'db data source with imported Api', table); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + ApiId: { 'Fn::Select': [ 1, { 'Fn::Split': [ '/', { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'Arn' ] } ] } ] }, + }); +}); + +test('imported api can add DynamoDbDataSource from attributes', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + apiId: baseApi.apiId, + arn: baseApi.arn, + }); + const table = new db.Table(stack, 'table', { + partitionKey: { + name: 'key', + type: db.AttributeType.NUMBER, + }, + }); + api.addDynamoDbDataSource('db', 'db data source with imported Api', table); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); +}); + +test('imported api can add LambdaDbDataSource from id', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'importedApi', baseApi.apiId); + const func = new lambda.Function(stack, 'func', { + code: lambda.Code.fromAsset('test/verify'), + handler: 'iam-query.handler', + runtime: lambda.Runtime.NODEJS_12_X, + }); + api.addLambdaDataSource('lambda', 'lambda data source with imported Api', func); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); +}); + +test('imported api can add LambdaDataSource from arn', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'importedApi', baseApi.arn); + const func = new lambda.Function(stack, 'func', { + code: lambda.Code.fromAsset('test/verify'), + handler: 'iam-query.handler', + runtime: lambda.Runtime.NODEJS_12_X, + }); + api.addLambdaDataSource('lambda', 'lambda data source with imported Api', func); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + ApiId: { 'Fn::Select': [ 1, { 'Fn::Split': [ '/', { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'Arn' ] } ] } ] }, + }); +}); + +test('imported api can add LambdaDataSource from attributes', () => { + // WHEN + const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + apiId: baseApi.apiId, + arn: baseApi.arn, + }); + const func = new lambda.Function(stack, 'func', { + code: lambda.Code.fromAsset('test/verify'), + handler: 'iam-query.handler', + runtime: lambda.Runtime.NODEJS_12_X, + }); + api.addLambdaDataSource('lambda', 'lambda data source with imported Api', func); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); +}); diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json new file mode 100644 index 0000000000000..db54cd93089e6 --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json @@ -0,0 +1,224 @@ +[ + { + "Resources": { + "baseApiCDA4D43A": { + "Type": "AWS::AppSync::GraphQLApi", + "Properties": { + "AuthenticationType": "API_KEY", + "Name": "baseApi" + } + }, + "baseApiDefaultAPIKeyApiKey4804ACE5": { + "Type": "AWS::AppSync::ApiKey", + "Properties": { + "ApiId": { + "Fn::GetAtt": [ + "baseApiCDA4D43A", + "ApiId" + ] + }, + "Description": "Default API Key created by CDK" + } + }, + "baseApiSchemaB12C7BB0": { + "Type": "AWS::AppSync::GraphQLSchema", + "Properties": { + "ApiId": { + "Fn::GetAtt": [ + "baseApiCDA4D43A", + "ApiId" + ] + }, + "Definition": "type test {\n version: String!\n}\n\ntype Query {\n getTests: [ test! ]!\n}\n\ntype Mutation {\n addTest(version: String!): test\n}\n" + } + } + }, + "Outputs": { + "ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68": { + "Value": { + "Fn::GetAtt": [ + "baseApiCDA4D43A", + "ApiId" + ] + }, + "Export": { + "Name": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" + } + }, + "ExportsOutputFnGetAttbaseApiCDA4D43AArn68A2A4E6": { + "Value": { + "Fn::GetAtt": [ + "baseApiCDA4D43A", + "Arn" + ] + }, + "Export": { + "Name": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AArn68A2A4E6" + } + } + } + }, + { + "Resources": { + "ApitestDataSourceDSServiceRoleE543E310": { + "Type": "AWS::IAM::Role", + "Properties": { + "AssumeRolePolicyDocument": { + "Statement": [ + { + "Action": "sts:AssumeRole", + "Effect": "Allow", + "Principal": { + "Service": "appsync.amazonaws.com" + } + } + ], + "Version": "2012-10-17" + } + } + }, + "ApitestDataSourceDSServiceRoleDefaultPolicy53D2252C": { + "Type": "AWS::IAM::Policy", + "Properties": { + "PolicyDocument": { + "Statement": [ + { + "Action": [ + "dynamodb:BatchGetItem", + "dynamodb:GetRecords", + "dynamodb:GetShardIterator", + "dynamodb:Query", + "dynamodb:GetItem", + "dynamodb:Scan", + "dynamodb:BatchWriteItem", + "dynamodb:PutItem", + "dynamodb:UpdateItem", + "dynamodb:DeleteItem" + ], + "Effect": "Allow", + "Resource": [ + { + "Fn::GetAtt": [ + "TestTable5769773A", + "Arn" + ] + }, + { + "Ref": "AWS::NoValue" + } + ] + } + ], + "Version": "2012-10-17" + }, + "PolicyName": "ApitestDataSourceDSServiceRoleDefaultPolicy53D2252C", + "Roles": [ + { + "Ref": "ApitestDataSourceDSServiceRoleE543E310" + } + ] + } + }, + "ApitestDataSourceDS776EA507": { + "Type": "AWS::AppSync::DataSource", + "Properties": { + "ApiId": { + "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" + }, + "Name": "testDataSource", + "Type": "AMAZON_DYNAMODB", + "Description": "test table data source", + "DynamoDBConfig": { + "AwsRegion": { + "Ref": "AWS::Region" + }, + "TableName": { + "Ref": "TestTable5769773A" + } + }, + "ServiceRoleArn": { + "Fn::GetAtt": [ + "ApitestDataSourceDSServiceRoleE543E310", + "Arn" + ] + } + } + }, + "ApitestDataSourceDSQuerygetTestsResolver61ED88B6": { + "Type": "AWS::AppSync::Resolver", + "Properties": { + "ApiId": { + "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" + }, + "FieldName": "getTests", + "TypeName": "Query", + "DataSourceName": "testDataSource", + "Kind": "UNIT", + "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", + "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" + }, + "DependsOn": [ + "ApitestDataSourceDS776EA507" + ] + }, + "ApitestDataSourceDSMutationaddTestResolver0D3A4591": { + "Type": "AWS::AppSync::Resolver", + "Properties": { + "ApiId": { + "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" + }, + "FieldName": "addTest", + "TypeName": "Mutation", + "DataSourceName": "testDataSource", + "Kind": "UNIT", + "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", + "ResponseMappingTemplate": "$util.toJson($ctx.result)" + }, + "DependsOn": [ + "ApitestDataSourceDS776EA507" + ] + }, + "TestTable5769773A": { + "Type": "AWS::DynamoDB::Table", + "Properties": { + "KeySchema": [ + { + "AttributeName": "id", + "KeyType": "HASH" + } + ], + "AttributeDefinitions": [ + { + "AttributeName": "id", + "AttributeType": "S" + } + ], + "BillingMode": "PAY_PER_REQUEST" + }, + "UpdateReplacePolicy": "Delete", + "DeletionPolicy": "Delete" + }, + "api2noneDSA74A64A5": { + "Type": "AWS::AppSync::DataSource", + "Properties": { + "ApiId": { + "Fn::Select": [ + 1, + { + "Fn::Split": [ + "/", + { + "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AArn68A2A4E6" + } + ] + } + ] + }, + "Name": "none", + "Type": "NONE", + "Description": "none" + } + } + } + } +] \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts index 79515fb65a96f..3e019d4ee8f60 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts @@ -1,3 +1,5 @@ +/// !cdk-integ * + import * as path from 'path'; import * as db from '@aws-cdk/aws-dynamodb'; import * as cdk from '@aws-cdk/core'; From b0ea1a23a1fc2b301e4901da6b333cf179a78aaa Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Wed, 29 Jul 2020 12:42:18 -0700 Subject: [PATCH 08/17] addresses suggestions --- packages/@aws-cdk/aws-appsync/README.md | 21 +++--- .../aws-appsync/lib/graphqlapi-base.ts | 50 +++++++------ .../@aws-cdk/aws-appsync/lib/graphqlapi.ts | 61 ++++++---------- .../aws-appsync/test/appsync-import.test.ts | 73 ++++--------------- .../test/integ.api-import.expected.json | 23 +----- .../aws-appsync/test/integ.api-import.ts | 9 ++- 6 files changed, 83 insertions(+), 154 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/README.md b/packages/@aws-cdk/aws-appsync/README.md index 9014d5988881e..70a700fbfea93 100644 --- a/packages/@aws-cdk/aws-appsync/README.md +++ b/packages/@aws-cdk/aws-appsync/README.md @@ -83,20 +83,21 @@ demoDS.createResolver({ ## Imports -Any GraphQL Api can be imported from another stack. Utilizing the `fromXxx` -functions, you have the ability to add data sources and resolvers through -a `IGraphQLApi` interface. +Any GraphQL Api that has been created outside the stack can be imported from +another stack into your CDK app. Utilizing the `fromXxx` function, you have +the ability to add data sources and resolvers through a `IGraphQLApi` interface. ```ts -const importedApi = appsync.GraphQLApi.fromGraphQLApiId(...); -importedApi.addDynamoDbDataSource(...); +const importedApi = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'IApi', { + graphqlApiId: api.apiId, + graphqlArn: api.arn, +}); +importedApi.addDynamoDbDataSource('TableDataSource', 'Table', table); ``` -GraphQL Apis can be imported in three ways: -- `arn` through `GraphQLApi.fromGraphQLApiArn`: `apiId` is generated from parameter -- `apiId` through `GraphQLApi.fromGraphQLApiId`: `arn` is generated from parameter -- or both through `GraphQLApi.fromGraphQLApiAttributes`: both are specified - +If you don't specify `graphqlArn` in `fromXxxAttributes`, CDK will autogenerate +the expected `arn` for the imported api, given the `apiId`. For creating data +sources and resolvers, an `apiId` is sufficient. ## Permissions diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index 08735594a4022..2243d73c9011c 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -2,36 +2,41 @@ import { ITable } from '@aws-cdk/aws-dynamodb'; import { IFunction } from '@aws-cdk/aws-lambda'; import { CfnResource, IResource, Resource } from '@aws-cdk/core'; import { DynamoDbDataSource, HttpDataSource, LambdaDataSource, NoneDataSource } from './data-source'; + /** * Interface for GraphQL */ export interface IGraphQLApi extends IResource { + /** - * the id of the GraphQL API - * + * an unique AWS AppSync GraphQL API identifier + * i.e. 'lxz775lwdrgcndgz3nurvac7oa' * @attribute */ readonly apiId: string; + /** * the ARN of the API * * @attribute */ readonly arn: string; + /** - * add a new dummy data source to this API + * add a new dummy data source to this API. Useful for pipeline resolvers + * and for backend changes that don't require a data source. * @param name The name of the data source * @param description The description of the data source */ - addNoneDataSource(name: string, description: string): NoneDataSource; + addNoneDataSource(name?: string, description?: string): NoneDataSource; /** * add a new DynamoDB data source to this API * @param name The name of the data source * @param description The description of the data source - * @param table The DynamoDB table backing this data source [disable-awslint:ref-via-interface] + * @param table The DynamoDB table backing this data source */ - addDynamoDbDataSource( name: string, description: string, table: ITable ): DynamoDbDataSource; + addDynamoDbDataSource(name: string, description: string, table: ITable): DynamoDbDataSource; /** * add a new http data source to this API @@ -47,38 +52,41 @@ export interface IGraphQLApi extends IResource { * @param description The description of the data source * @param lambdaFunction The Lambda function to call to interact with this data source */ - addLambdaDataSource( name: string, description: string, lambdaFunction: IFunction ): LambdaDataSource; + addLambdaDataSource(name: string, description: string, lambdaFunction: IFunction): LambdaDataSource; /** * Add schema dependency if not imported * @param construct the construct that has a dependency */ - addSchemaDependency( construct: CfnResource ): boolean; + addSchemaDependency(construct: CfnResource): boolean; } /** * Base Class for GraphQL API */ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { + /** * the id of the GraphQL API */ public abstract readonly apiId: string; + /** * the ARN of the API */ public abstract readonly arn: string; /** - * add a new dummy data source to this API - * @param name The name of the data source - * @param description The description of the data source + * add a new none data source to this API. Useful for pipeline resolvers + * and for backend changes that don't require a data source. + * @param name The name of the data source @default 'None' + * @param description The description of the data source @default undefined */ - public addNoneDataSource(name: string, description: string): NoneDataSource { - return new NoneDataSource(this, `${name}DS`, { + public addNoneDataSource(name?: string, description?: string): NoneDataSource { + return new NoneDataSource(this, `${name ?? 'None'}DS`, { api: this, description, - name, + name: name ?? 'NoneDS', }); } @@ -86,13 +94,9 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * add a new DynamoDB data source to this API * @param name The name of the data source * @param description The description of the data source - * @param table The DynamoDB table backing this data source [disable-awslint:ref-via-interface] + * @param table The DynamoDB table backing this data source */ - public addDynamoDbDataSource( - name: string, - description: string, - table: ITable, - ): DynamoDbDataSource { + public addDynamoDbDataSource(name: string, description: string, table: ITable): DynamoDbDataSource { return new DynamoDbDataSource(this, `${name}DS`, { api: this, description, @@ -122,7 +126,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * @param description The description of the data source * @param lambdaFunction The Lambda function to call to interact with this data source */ - public addLambdaDataSource( name: string, description: string, lambdaFunction: IFunction ): LambdaDataSource { + public addLambdaDataSource(name: string, description: string, lambdaFunction: IFunction): LambdaDataSource { return new LambdaDataSource(this, `${name}DS`, { api: this, description, @@ -133,9 +137,9 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * Add schema dependency if not imported - * @param construct the construct that has a dependency + * @param construct the dependee */ - public addSchemaDependency( construct: CfnResource ): boolean { + public addSchemaDependency(construct: CfnResource): boolean { construct; return false; } diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index d9e4ff4465ba7..85cee95f69dcc 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -1,7 +1,7 @@ import { readFileSync } from 'fs'; import { IUserPool } from '@aws-cdk/aws-cognito'; import { ManagedPolicy, Role, ServicePrincipal, Grant, IGrantable } from '@aws-cdk/aws-iam'; -import { CfnResource, Construct, Duration, Fn, IResolvable, Stack } from '@aws-cdk/core'; +import { CfnResource, Construct, Duration, IResolvable, Stack } from '@aws-cdk/core'; import { CfnApiKey, CfnGraphQLApi, CfnGraphQLSchema } from './appsync.generated'; import { IGraphQLApi, GraphQLApiBase } from './graphqlapi-base'; @@ -298,18 +298,19 @@ export class IamResource { } /** - * Attributes for GraphQL From + * Attributes for GraphQL imports */ export interface GraphQLApiAttributes { /** - * the arn for the GraphQL Api + * the api id of the GraphQL Api */ - readonly arn: string, + readonly graphqlApiId: string, /** - * the api id of the GraphQL Api + * the arn for the GraphQL Api + * @default - autogenerated arn */ - readonly apiId: string, + readonly graphqlArn?: string, } /** @@ -318,34 +319,6 @@ export interface GraphQLApiAttributes { * @resource AWS::AppSync::GraphQLApi */ export class GraphQLApi extends GraphQLApiBase { - /** - * Import a GraphQL API given an arn - * @param scope scope - * @param id id - * @param graphQLApiId the apiId of the api - */ - public static fromGraphQLApiId(scope: Construct, id: string, graphQLApiId: string): IGraphQLApi { - const generatedArn = Stack.of(scope).formatArn({ - service: 'appsync', - resource: `apis/${graphQLApiId}`, - }); - return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: generatedArn, apiId: graphQLApiId}); - } - - /** - * Import a GraphQL API given an arn - * @param scope scope - * @param id id - * @param graphQLApiArn the arn of the api - */ - public static fromGraphQLApiArn(scope: Construct, id: string, graphQLApiArn: string): IGraphQLApi { - const apiId = Fn.select(1, Fn.split('/', graphQLApiArn)); - if (apiId == undefined || apiId == graphQLApiArn) { - throw Error('Arn does not contain a valid apiId'); - } - return GraphQLApi.fromGraphQLApiAttributes(scope, id, { arn: graphQLApiArn, apiId: apiId}); - } - /** * Import a GraphQL API through this function * @param scope scope @@ -353,37 +326,47 @@ export class GraphQLApi extends GraphQLApiBase { * @param attrs GraphQL API Attributes of an API */ public static fromGraphQLApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { + const arn = attrs.graphqlArn ?? Stack.of(scope).formatArn({ + service: 'appsync', + resource: `apis/${attrs.graphqlApiId}`, + }); class Import extends GraphQLApiBase { - public readonly apiId = attrs.apiId; - public readonly arn = attrs.arn; + public readonly apiId = attrs.graphqlApiId; + public readonly arn = arn; constructor (s: Construct, i: string){ super(s, i); } } return new Import(scope, id); } + /** * the id of the GraphQL API */ public readonly apiId: string; + /** * the ARN of the API */ public readonly arn: string; + /** * the URL of the endpoint created by AppSync * * @attribute */ public readonly graphQlUrl: string; + /** * the name of the API */ public readonly name: string; + /** * underlying CFN schema resource */ public readonly schema: CfnGraphQLSchema; + /** * the configured API key, if present */ @@ -591,10 +574,10 @@ export class GraphQLApi extends GraphQLApiBase { } /** - * Add schema dependency if not imported - * @param construct the construct that has a dependency + * Add schema dependency to a given construct + * @param construct the dependee */ - public addSchemaDependency( construct: CfnResource ): boolean { + public addSchemaDependency(construct: CfnResource): boolean { construct.addDependsOn(this.schema); return true; } diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts index 3830dacf0a7f7..1f6674c5698be 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts @@ -18,7 +18,9 @@ beforeEach( () => { test('imported api can add NoneDataSource from id', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'importedApi', baseApi.apiId); + const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + graphqlApiId: baseApi.apiId, + }); api.addNoneDataSource('none', 'none data source with imported Api'); @@ -29,25 +31,11 @@ test('imported api can add NoneDataSource from id', () => { }, }); }); - -test('imported api can add NoneDataSource from arn', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'importedApi', baseApi.arn); - - api.addNoneDataSource('none', 'none data source with imported Api'); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'NONE', - ApiId: { 'Fn::Select': [ 1, { 'Fn::Split': [ '/', { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'Arn' ] } ] } ] }, - }); -}); - test('imported api can add NoneDataSource from attributes', () => { // WHEN const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { - apiId: baseApi.apiId, - arn: baseApi.arn, + graphqlApiId: baseApi.apiId, + graphqlArn: baseApi.arn, }); api.addNoneDataSource('none', 'none data source with imported Api'); @@ -62,7 +50,9 @@ test('imported api can add NoneDataSource from attributes', () => { test('imported api can add DynamoDbDataSource from id', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'importedApi', baseApi.apiId); + const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + graphqlApiId: baseApi.apiId, + }); const table = new db.Table(stack, 'table', { partitionKey: { name: 'key', @@ -79,29 +69,11 @@ test('imported api can add DynamoDbDataSource from id', () => { }); }); -test('imported api can add DynamoDbDataSource from arn', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'importedApi', baseApi.arn); - const table = new db.Table(stack, 'table', { - partitionKey: { - name: 'key', - type: db.AttributeType.NUMBER, - }, - }); - api.addDynamoDbDataSource('db', 'db data source with imported Api', table); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'AMAZON_DYNAMODB', - ApiId: { 'Fn::Select': [ 1, { 'Fn::Split': [ '/', { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'Arn' ] } ] } ] }, - }); -}); - test('imported api can add DynamoDbDataSource from attributes', () => { // WHEN const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { - apiId: baseApi.apiId, - arn: baseApi.arn, + graphqlApiId: baseApi.apiId, + graphqlArn: baseApi.arn, }); const table = new db.Table(stack, 'table', { partitionKey: { @@ -121,7 +93,9 @@ test('imported api can add DynamoDbDataSource from attributes', () => { test('imported api can add LambdaDbDataSource from id', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'importedApi', baseApi.apiId); + const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + graphqlApiId: baseApi.apiId, + }); const func = new lambda.Function(stack, 'func', { code: lambda.Code.fromAsset('test/verify'), handler: 'iam-query.handler', @@ -137,28 +111,11 @@ test('imported api can add LambdaDbDataSource from id', () => { }); }); -test('imported api can add LambdaDataSource from arn', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'importedApi', baseApi.arn); - const func = new lambda.Function(stack, 'func', { - code: lambda.Code.fromAsset('test/verify'), - handler: 'iam-query.handler', - runtime: lambda.Runtime.NODEJS_12_X, - }); - api.addLambdaDataSource('lambda', 'lambda data source with imported Api', func); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'AWS_LAMBDA', - ApiId: { 'Fn::Select': [ 1, { 'Fn::Split': [ '/', { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'Arn' ] } ] } ] }, - }); -}); - test('imported api can add LambdaDataSource from attributes', () => { // WHEN const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { - apiId: baseApi.apiId, - arn: baseApi.arn, + graphqlApiId: baseApi.apiId, + graphqlArn: baseApi.arn, }); const func = new lambda.Function(stack, 'func', { code: lambda.Code.fromAsset('test/verify'), diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json index db54cd93089e6..bd1b0eb4667ef 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json @@ -44,17 +44,6 @@ "Export": { "Name": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" } - }, - "ExportsOutputFnGetAttbaseApiCDA4D43AArn68A2A4E6": { - "Value": { - "Fn::GetAtt": [ - "baseApiCDA4D43A", - "Arn" - ] - }, - "Export": { - "Name": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AArn68A2A4E6" - } } } }, @@ -202,17 +191,7 @@ "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { - "Fn::Select": [ - 1, - { - "Fn::Split": [ - "/", - { - "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AArn68A2A4E6" - } - ] - } - ] + "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" }, "Name": "none", "Type": "NONE", diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts index 3e019d4ee8f60..d3497d83ff0aa 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts @@ -28,7 +28,9 @@ const baseApi = new appsync.GraphQLApi(baseStack, 'baseApi', { }); const stack = new cdk.Stack(app, 'stack'); -const api = appsync.GraphQLApi.fromGraphQLApiId(stack, 'Api', `${baseApi.apiId}`); +const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'Api', { + graphqlApiId: `${baseApi.apiId}`, +}); const testTable = new db.Table(stack, 'TestTable', { billingMode: db.BillingMode.PAY_PER_REQUEST, @@ -55,7 +57,10 @@ testDS.createResolver({ responseMappingTemplate: appsync.MappingTemplate.dynamoDbResultItem(), }); -const api2 = appsync.GraphQLApi.fromGraphQLApiArn(stack, 'api2', baseApi.arn); +const api2 = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'api2', { + graphqlApiId: baseApi.apiId, + graphqlArn: baseApi.arn, +}); api2.addNoneDataSource('none', 'none'); From e136805e0ec789d986efec64c33059bb9535fd8f Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Thu, 30 Jul 2020 10:13:24 -0700 Subject: [PATCH 09/17] spacing before param --- .../@aws-cdk/aws-appsync/lib/graphqlapi-base.ts | 17 ++++++++++------- packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts | 4 +++- 2 files changed, 13 insertions(+), 8 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index 2243d73c9011c..bccd7e0f7e56e 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -11,6 +11,7 @@ export interface IGraphQLApi extends IResource { /** * an unique AWS AppSync GraphQL API identifier * i.e. 'lxz775lwdrgcndgz3nurvac7oa' + * * @attribute */ readonly apiId: string; @@ -25,6 +26,7 @@ export interface IGraphQLApi extends IResource { /** * add a new dummy data source to this API. Useful for pipeline resolvers * and for backend changes that don't require a data source. + * * @param name The name of the data source * @param description The description of the data source */ @@ -40,6 +42,7 @@ export interface IGraphQLApi extends IResource { /** * add a new http data source to this API + * * @param name The name of the data source * @param description The description of the data source * @param endpoint The http endpoint @@ -48,17 +51,12 @@ export interface IGraphQLApi extends IResource { /** * add a new Lambda data source to this API + * * @param name The name of the data source * @param description The description of the data source * @param lambdaFunction The Lambda function to call to interact with this data source */ addLambdaDataSource(name: string, description: string, lambdaFunction: IFunction): LambdaDataSource; - - /** - * Add schema dependency if not imported - * @param construct the construct that has a dependency - */ - addSchemaDependency(construct: CfnResource): boolean; } /** @@ -79,6 +77,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new none data source to this API. Useful for pipeline resolvers * and for backend changes that don't require a data source. + * * @param name The name of the data source @default 'None' * @param description The description of the data source @default undefined */ @@ -92,6 +91,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new DynamoDB data source to this API + * * @param name The name of the data source * @param description The description of the data source * @param table The DynamoDB table backing this data source @@ -107,6 +107,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new http data source to this API + * * @param name The name of the data source * @param description The description of the data source * @param endpoint The http endpoint @@ -122,6 +123,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new Lambda data source to this API + * * @param name The name of the data source * @param description The description of the data source * @param lambdaFunction The Lambda function to call to interact with this data source @@ -137,9 +139,10 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * Add schema dependency if not imported + * * @param construct the dependee */ - public addSchemaDependency(construct: CfnResource): boolean { + protected addSchemaDependency(construct: CfnResource): boolean { construct; return false; } diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index 85cee95f69dcc..c920762a27c35 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -321,6 +321,7 @@ export interface GraphQLApiAttributes { export class GraphQLApi extends GraphQLApiBase { /** * Import a GraphQL API through this function + * * @param scope scope * @param id id * @param attrs GraphQL API Attributes of an API @@ -575,9 +576,10 @@ export class GraphQLApi extends GraphQLApiBase { /** * Add schema dependency to a given construct + * * @param construct the dependee */ - public addSchemaDependency(construct: CfnResource): boolean { + protected addSchemaDependency(construct: CfnResource): boolean { construct.addDependsOn(this.schema); return true; } From 07dfea2aceb4b4c4da6152823ac5d4b73aaaf3e1 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Thu, 30 Jul 2020 12:33:12 -0700 Subject: [PATCH 10/17] prelim changes to shiv's suggestions --- .../aws-appsync/lib/graphqlapi-base.ts | 18 ++++++++++++++---- .../@aws-cdk/aws-appsync/lib/graphqlapi.ts | 10 ++++++---- packages/@aws-cdk/aws-appsync/package.json | 3 ++- .../aws-appsync/test/appsync-import.test.ts | 14 +++++++------- .../aws-appsync/test/integ.api-import.ts | 4 ++-- 5 files changed, 31 insertions(+), 18 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index bccd7e0f7e56e..8b037a537b71d 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -57,6 +57,13 @@ export interface IGraphQLApi extends IResource { * @param lambdaFunction The Lambda function to call to interact with this data source */ addLambdaDataSource(name: string, description: string, lambdaFunction: IFunction): LambdaDataSource; + + /** + * Add schema dependency if not imported + * + * @param construct the dependee + */ + addSchemaDependency(construct: CfnResource): boolean; } /** @@ -65,7 +72,8 @@ export interface IGraphQLApi extends IResource { export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** - * the id of the GraphQL API + * an unique AWS AppSync GraphQL API identifier + * i.e. 'lxz775lwdrgcndgz3nurvac7oa' */ public abstract readonly apiId: string; @@ -78,8 +86,10 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * add a new none data source to this API. Useful for pipeline resolvers * and for backend changes that don't require a data source. * - * @param name The name of the data source @default 'None' - * @param description The description of the data source @default undefined + * @param name The name of the data source + * @default 'None' + * @param description The description of the data source + * @default undefined */ public addNoneDataSource(name?: string, description?: string): NoneDataSource { return new NoneDataSource(this, `${name ?? 'None'}DS`, { @@ -142,7 +152,7 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * * @param construct the dependee */ - protected addSchemaDependency(construct: CfnResource): boolean { + public addSchemaDependency(construct: CfnResource): boolean { construct; return false; } diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index c920762a27c35..001dbc844c4bc 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -302,7 +302,8 @@ export class IamResource { */ export interface GraphQLApiAttributes { /** - * the api id of the GraphQL Api + * an unique AWS AppSync GraphQL API identifier + * i.e. 'lxz775lwdrgcndgz3nurvac7oa' */ readonly graphqlApiId: string, @@ -326,7 +327,7 @@ export class GraphQLApi extends GraphQLApiBase { * @param id id * @param attrs GraphQL API Attributes of an API */ - public static fromGraphQLApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { + public static fromGraphqlApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { const arn = attrs.graphqlArn ?? Stack.of(scope).formatArn({ service: 'appsync', resource: `apis/${attrs.graphqlApiId}`, @@ -342,7 +343,8 @@ export class GraphQLApi extends GraphQLApiBase { } /** - * the id of the GraphQL API + * an unique AWS AppSync GraphQL API identifier + * i.e. 'lxz775lwdrgcndgz3nurvac7oa' */ public readonly apiId: string; @@ -579,7 +581,7 @@ export class GraphQLApi extends GraphQLApiBase { * * @param construct the dependee */ - protected addSchemaDependency(construct: CfnResource): boolean { + public addSchemaDependency(construct: CfnResource): boolean { construct.addDependsOn(this.schema); return true; } diff --git a/packages/@aws-cdk/aws-appsync/package.json b/packages/@aws-cdk/aws-appsync/package.json index 56885925745c8..c069b817f9e04 100644 --- a/packages/@aws-cdk/aws-appsync/package.json +++ b/packages/@aws-cdk/aws-appsync/package.json @@ -95,7 +95,8 @@ "no-unused-type:@aws-cdk/aws-appsync.ApiKeyConfig", "no-unused-type:@aws-cdk/aws-appsync.UserPoolConfig", "no-unused-type:@aws-cdk/aws-appsync.UserPoolDefaultAction", - "props-physical-name:@aws-cdk/aws-appsync.GraphQLApiProps" + "props-physical-name:@aws-cdk/aws-appsync.GraphQLApiProps", + "from-method:@aws-cdk/aws-appsync.GraphQLApi" ] }, "stability": "experimental", diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts index 1f6674c5698be..ea0a119aa1076 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts @@ -8,7 +8,7 @@ import * as appsync from '../lib'; let stack: cdk.Stack; let baseApi: appsync.GraphQLApi; beforeEach( () => { - // Given + // GIVEN stack = new cdk.Stack(); baseApi = new appsync.GraphQLApi(stack, 'baseApi', { name: 'api', @@ -18,7 +18,7 @@ beforeEach( () => { test('imported api can add NoneDataSource from id', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: baseApi.apiId, }); @@ -33,7 +33,7 @@ test('imported api can add NoneDataSource from id', () => { }); test('imported api can add NoneDataSource from attributes', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: baseApi.apiId, graphqlArn: baseApi.arn, }); @@ -50,7 +50,7 @@ test('imported api can add NoneDataSource from attributes', () => { test('imported api can add DynamoDbDataSource from id', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: baseApi.apiId, }); const table = new db.Table(stack, 'table', { @@ -71,7 +71,7 @@ test('imported api can add DynamoDbDataSource from id', () => { test('imported api can add DynamoDbDataSource from attributes', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: baseApi.apiId, graphqlArn: baseApi.arn, }); @@ -93,7 +93,7 @@ test('imported api can add DynamoDbDataSource from attributes', () => { test('imported api can add LambdaDbDataSource from id', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: baseApi.apiId, }); const func = new lambda.Function(stack, 'func', { @@ -113,7 +113,7 @@ test('imported api can add LambdaDbDataSource from id', () => { test('imported api can add LambdaDataSource from attributes', () => { // WHEN - const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'importedApi', { + const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: baseApi.apiId, graphqlArn: baseApi.arn, }); diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts index d3497d83ff0aa..d3ba6bfa03c0e 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts @@ -28,7 +28,7 @@ const baseApi = new appsync.GraphQLApi(baseStack, 'baseApi', { }); const stack = new cdk.Stack(app, 'stack'); -const api = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'Api', { +const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'Api', { graphqlApiId: `${baseApi.apiId}`, }); @@ -57,7 +57,7 @@ testDS.createResolver({ responseMappingTemplate: appsync.MappingTemplate.dynamoDbResultItem(), }); -const api2 = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'api2', { +const api2 = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'api2', { graphqlApiId: baseApi.apiId, graphqlArn: baseApi.arn, }); From a44a9b883811098fe32bf237534fb76c9a7677ef Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Fri, 31 Jul 2020 11:52:26 -0700 Subject: [PATCH 11/17] round out unit tests --- .../aws-appsync/lib/graphqlapi-base.ts | 4 +- .../aws-appsync/test/appsync-dynamodb.test.ts | 143 ++++++++++++++++-- .../aws-appsync/test/appsync-http.test.ts | 106 +++++++++++++ .../aws-appsync/test/appsync-import.test.ts | 134 ---------------- .../aws-appsync/test/appsync-lambda.test.ts | 121 +++++++++++++++ .../aws-appsync/test/appsync-none.test.ts | 104 +++++++++++++ .../test/integ.api-import.expected.json | 26 ++-- .../test/integ.graphql-iam.expected.json | 38 ++--- 8 files changed, 498 insertions(+), 178 deletions(-) create mode 100644 packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts delete mode 100644 packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts create mode 100644 packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts create mode 100644 packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index 007b56bcd0b1e..4235a0cafeb2e 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -128,11 +128,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - 'DynamoDbCDKDefault' + * @default name - 'TableCDKDefault' * description - undefined */ public addDynamoDbDataSource(table: ITable, options?: DataSourceOptions): DynamoDbDataSource { - const name = options?.name ?? 'DynamoDbCDKDefault'; + const name = options?.name ?? 'TableCDKDefault'; return new DynamoDbDataSource(this, name, { api: this, table, diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts index 37e1ecc0ea57b..d3b032415dea2 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts @@ -1,15 +1,93 @@ import '@aws-cdk/assert/jest'; -import { MappingTemplate, PrimaryKey, Values } from '../lib'; +import * as path from 'path'; +import * as db from '@aws-cdk/aws-dynamodb'; +import * as cdk from '@aws-cdk/core'; +import * as appsync from '../lib'; function joined(str: string): string { return str.replace(/\s+/g, ''); } +// GLOBAL GIVEN +let stack: cdk.Stack; +let api: appsync.GraphQLApi; +beforeEach(() => { + stack = new cdk.Stack(); + api = new appsync.GraphQLApi(stack, 'baseApi', { + name: 'api', + schemaDefinition: appsync.SchemaDefinition.FILE, + schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), + }); +}); + +describe('DynamoDb Data Source configuration', () => { + // GIVEN + let table: db.Table; + beforeEach(() => { + table = new db.Table(stack, 'table', { + partitionKey: { + name: 'id', + type: db.AttributeType.STRING, + }, + }); + }); + + test('default configuration produces name `TableCDKDefault`', () => { + // WHEN + api.addDynamoDbDataSource(table); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + Name: 'TableCDKDefault', + }); + }); + + test('appsync configures name correctly', () => { + // WHEN + api.addDynamoDbDataSource(table, { + name: 'custom', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + Name: 'custom', + }); + }); + + test('appsync configures name and description correctly', () => { + // WHEN + api.addDynamoDbDataSource(table, { + name: 'custom', + description: 'custom description', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + Name: 'custom', + Description: 'custom description', + }); + }); + + test('appsync errors when creating multiple dynamo db data sources with no configuration', () => { + // WHEN + const when = () => { + api.addDynamoDbDataSource(table); + api.addDynamoDbDataSource(table); + }; + + // EXPECT + expect(when).toThrow('There is already a Construct with name \'TableCDKDefault\' in GraphQLApi [baseApi]'); + }); +}); + describe('DynamoDB Mapping Templates', () => { test('PutItem projecting all', () => { - const template = MappingTemplate.dynamoDbPutItem( - PrimaryKey.partition('id').is('id'), - Values.projecting(), + const template = appsync.MappingTemplate.dynamoDbPutItem( + appsync.PrimaryKey.partition('id').is('id'), + appsync.Values.projecting(), ); const rendered = joined(template.renderTemplate()); @@ -28,9 +106,9 @@ describe('DynamoDB Mapping Templates', () => { }); test('PutItem with invididual attributes', () => { - const template = MappingTemplate.dynamoDbPutItem( - PrimaryKey.partition('id').is('id'), - Values.attribute('val').is('ctx.args.val'), + const template = appsync.MappingTemplate.dynamoDbPutItem( + appsync.PrimaryKey.partition('id').is('id'), + appsync.Values.attribute('val').is('ctx.args.val'), ); const rendered = joined(template.renderTemplate()); @@ -50,9 +128,9 @@ describe('DynamoDB Mapping Templates', () => { }); test('PutItem with additional attributes', () => { - const template = MappingTemplate.dynamoDbPutItem( - PrimaryKey.partition('id').is('id'), - Values.projecting().attribute('val').is('ctx.args.val'), + const template = appsync.MappingTemplate.dynamoDbPutItem( + appsync.PrimaryKey.partition('id').is('id'), + appsync.Values.projecting().attribute('val').is('ctx.args.val'), ); const rendered = joined(template.renderTemplate()); @@ -70,4 +148,49 @@ describe('DynamoDB Mapping Templates', () => { }`), ); }); +}); + +describe('adding DynamoDb data source from imported api', () => { + // GIVEN + let table: db.Table; + beforeEach(() => { + table = new db.Table(stack, 'table', { + partitionKey: { + name: 'id', + type: db.AttributeType.STRING, + }, + }); + }); + + test('imported api can add DynamoDbDataSource from id', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + }); + importedApi.addDynamoDbDataSource(table); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); + + test('imported api can add DynamoDbDataSource from attributes', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + graphqlArn: api.arn, + }); + importedApi.addDynamoDbDataSource(table); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AMAZON_DYNAMODB', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); + }); \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts new file mode 100644 index 0000000000000..886581a75f74e --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts @@ -0,0 +1,106 @@ +import '@aws-cdk/assert/jest'; +import * as path from 'path'; +import * as cdk from '@aws-cdk/core'; +import * as appsync from '../lib'; + +// GLOBAL GIVEN +let stack: cdk.Stack; +let api: appsync.GraphQLApi; +let endpoint: string; +beforeEach(() => { + stack = new cdk.Stack(); + api = new appsync.GraphQLApi(stack, 'baseApi', { + name: 'api', + schemaDefinition: appsync.SchemaDefinition.FILE, + schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), + }); + endpoint = 'aws.amazon.com'; +}); + +describe('Http Data Source configuration', () => { + + test('default configuration produces name `HttpCDKDefault`', () => { + // WHEN + api.addHttpDataSource(endpoint); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'HTTP', + Name: 'HttpCDKDefault', + }); + }); + + test('appsync configures name correctly', () => { + // WHEN + api.addHttpDataSource(endpoint, { + name: 'custom', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'HTTP', + Name: 'custom', + }); + }); + + test('appsync configures name and description correctly', () => { + // WHEN + api.addHttpDataSource(endpoint, { + name: 'custom', + description: 'custom description', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'HTTP', + Name: 'custom', + Description: 'custom description', + }); + }); + + test('appsync errors when creating multiple http data sources with no configuration', () => { + // WHEN + const when = () => { + api.addHttpDataSource(endpoint); + api.addHttpDataSource(endpoint); + }; + + // EXPECT + expect(when).toThrow('There is already a Construct with name \'HttpCDKDefault\' in GraphQLApi [baseApi]'); + }); +}); + +describe('adding http data source from imported api', () => { + test('imported api can add HttpDataSource from id', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + }); + importedApi.addHttpDataSource(endpoint); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'HTTP', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); + + test('imported api can add HttpDataSource from attributes', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + graphqlArn: api.arn, + }); + importedApi.addHttpDataSource(endpoint); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'HTTP', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); +}); + + diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts deleted file mode 100644 index c9c12ecb2d192..0000000000000 --- a/packages/@aws-cdk/aws-appsync/test/appsync-import.test.ts +++ /dev/null @@ -1,134 +0,0 @@ -import * as path from 'path'; -import '@aws-cdk/assert/jest'; -import * as db from '@aws-cdk/aws-dynamodb'; -import * as lambda from '@aws-cdk/aws-lambda'; -import * as cdk from '@aws-cdk/core'; -import * as appsync from '../lib'; - -let stack: cdk.Stack; -let baseApi: appsync.GraphQLApi; -beforeEach( () => { - // GIVEN - stack = new cdk.Stack(); - baseApi = new appsync.GraphQLApi(stack, 'baseApi', { - name: 'api', - schemaDefinition: appsync.SchemaDefinition.FILE, - schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), - }); -}); - -test('imported api can add NoneDataSource from id', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { - graphqlApiId: baseApi.apiId, - }); - - api.addNoneDataSource(); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'NONE', - ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], - }, - }); -}); -test('imported api can add NoneDataSource from attributes', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { - graphqlApiId: baseApi.apiId, - graphqlArn: baseApi.arn, - }); - - api.addNoneDataSource(); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'NONE', - ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], - }, - }); -}); - -test('imported api can add DynamoDbDataSource from id', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { - graphqlApiId: baseApi.apiId, - }); - const table = new db.Table(stack, 'table', { - partitionKey: { - name: 'key', - type: db.AttributeType.NUMBER, - }, - }); - api.addDynamoDbDataSource(table); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'AMAZON_DYNAMODB', - ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], - }, - }); -}); - -test('imported api can add DynamoDbDataSource from attributes', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { - graphqlApiId: baseApi.apiId, - graphqlArn: baseApi.arn, - }); - const table = new db.Table(stack, 'table', { - partitionKey: { - name: 'key', - type: db.AttributeType.NUMBER, - }, - }); - api.addDynamoDbDataSource(table); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'AMAZON_DYNAMODB', - ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], - }, - }); -}); - -test('imported api can add LambdaDbDataSource from id', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { - graphqlApiId: baseApi.apiId, - }); - const func = new lambda.Function(stack, 'func', { - code: lambda.Code.fromAsset('test/verify'), - handler: 'iam-query.handler', - runtime: lambda.Runtime.NODEJS_12_X, - }); - api.addLambdaDataSource(func); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'AWS_LAMBDA', - ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], - }, - }); -}); - -test('imported api can add LambdaDataSource from attributes', () => { - // WHEN - const api = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { - graphqlApiId: baseApi.apiId, - graphqlArn: baseApi.arn, - }); - const func = new lambda.Function(stack, 'func', { - code: lambda.Code.fromAsset('test/verify'), - handler: 'iam-query.handler', - runtime: lambda.Runtime.NODEJS_12_X, - }); - api.addLambdaDataSource(func); - - // THEN - expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { - Type: 'AWS_LAMBDA', - ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], - }, - }); -}); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts new file mode 100644 index 0000000000000..13ecd7b6af951 --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts @@ -0,0 +1,121 @@ +import '@aws-cdk/assert/jest'; +import * as path from 'path'; +import * as lambda from '@aws-cdk/aws-lambda'; +import * as cdk from '@aws-cdk/core'; +import * as appsync from '../lib'; + +// GLOBAL GIVEN +let stack: cdk.Stack; +let api: appsync.GraphQLApi; +beforeEach(() => { + stack = new cdk.Stack(); + api = new appsync.GraphQLApi(stack, 'baseApi', { + name: 'api', + schemaDefinition: appsync.SchemaDefinition.FILE, + schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), + }); +}); + +describe('Lambda Data Source configuration', () => { + // GIVEN + let func: lambda.Function; + beforeEach(() => { + func = new lambda.Function(stack, 'func', { + code: lambda.Code.fromAsset('test/verify'), + handler: 'iam-query.handler', + runtime: lambda.Runtime.NODEJS_12_X, + }); + }); + + test('default configuration produces name `TableCDKDefault`', () => { + // WHEN + api.addLambdaDataSource(func); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + Name: 'LambdaCDKDefault', + }); + }); + + test('appsync configures name correctly', () => { + // WHEN + api.addLambdaDataSource(func, { + name: 'custom', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + Name: 'custom', + }); + }); + + test('appsync configures name and description correctly', () => { + // WHEN + api.addLambdaDataSource(func, { + name: 'custom', + description: 'custom description', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + Name: 'custom', + Description: 'custom description', + }); + }); + + test('appsync errors when creating multiple lambda data sources with no configuration', () => { + // WHEN + const when = () => { + api.addLambdaDataSource(func); + api.addLambdaDataSource(func); + }; + + // EXPECT + expect(when).toThrow('There is already a Construct with name \'LambdaCDKDefault\' in GraphQLApi [baseApi]'); + }); +}); + +describe('adding lambda data source from imported api',() => { + let func: lambda.Function; + beforeEach(() => { + func = new lambda.Function(stack, 'func', { + code: lambda.Code.fromAsset('test/verify'), + handler: 'iam-query.handler', + runtime: lambda.Runtime.NODEJS_12_X, + }); + }); + + test('imported api can add LambdaDbDataSource from id', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + }); + importedApi.addLambdaDataSource(func); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); + + test('imported api can add LambdaDataSource from attributes', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + graphqlArn: api.arn, + }); + importedApi.addLambdaDataSource(func); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'AWS_LAMBDA', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); +}); \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts new file mode 100644 index 0000000000000..adda764fa1a77 --- /dev/null +++ b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts @@ -0,0 +1,104 @@ +import '@aws-cdk/assert/jest'; +import * as path from 'path'; +import * as cdk from '@aws-cdk/core'; +import * as appsync from '../lib'; + +// GLOBAL GIVEN +let stack: cdk.Stack; +let api: appsync.GraphQLApi; +beforeEach(() => { + stack = new cdk.Stack(); + api = new appsync.GraphQLApi(stack, 'baseApi', { + name: 'api', + schemaDefinition: appsync.SchemaDefinition.FILE, + schemaDefinitionFile: path.join(__dirname, 'appsync.test.graphql'), + }); +}); + +describe('DynamoDb Data Source configuration', () => { + + test('default configuration produces name `NoneCDKDefault`', () => { + // WHEN + api.addNoneDataSource(); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + Name: 'NoneCDKDefault', + }); + }); + + test('appsync configures name correctly', () => { + // WHEN + api.addNoneDataSource({ + name: 'custom', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + Name: 'custom', + }); + }); + + test('appsync configures name and description correctly', () => { + // WHEN + api.addNoneDataSource({ + name: 'custom', + description: 'custom description', + }); + + // EXPECT + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + Name: 'custom', + Description: 'custom description', + }); + }); + + test('appsync errors when creating multiple none data sources with no configuration', () => { + // WHEN + const when = () => { + api.addNoneDataSource(); + api.addNoneDataSource(); + }; + + // EXPECT + expect(when).toThrow('There is already a Construct with name \'NoneCDKDefault\' in GraphQLApi [baseApi]'); + }); +}); + +describe('adding none data source from imported api', () => { + test('imported api can add NoneDataSource from id', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + }); + importedApi.addNoneDataSource(); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); + + test('imported api can add NoneDataSource from attributes', () => { + // WHEN + const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { + graphqlApiId: api.apiId, + graphqlArn: api.arn, + }); + importedApi.addNoneDataSource(); + + // THEN + expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { + Type: 'NONE', + ApiId: { 'Fn::GetAtt': [ 'baseApiCDA4D43A', 'ApiId' ], + }, + }); + }); +}); + + diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json index bd1cdea1aa103..f0c9b2f4aa078 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json @@ -49,7 +49,7 @@ }, { "Resources": { - "ApiDynamoDbCDKDefaultServiceRoleFF246E00": { + "ApiTableCDKDefaultServiceRoleF54231AA": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -66,7 +66,7 @@ } } }, - "ApiDynamoDbCDKDefaultServiceRoleDefaultPolicy2BC1F6C3": { + "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -100,21 +100,21 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiDynamoDbCDKDefaultServiceRoleDefaultPolicy2BC1F6C3", + "PolicyName": "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657", "Roles": [ { - "Ref": "ApiDynamoDbCDKDefaultServiceRoleFF246E00" + "Ref": "ApiTableCDKDefaultServiceRoleF54231AA" } ] } }, - "ApiDynamoDbCDKDefault5BF6C4EC": { + "ApiTableCDKDefault0035EEA0": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" }, - "Name": "DynamoDbCDKDefault", + "Name": "TableCDKDefault", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -126,13 +126,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiDynamoDbCDKDefaultServiceRoleFF246E00", + "ApiTableCDKDefaultServiceRoleF54231AA", "Arn" ] } } }, - "ApiDynamoDbCDKDefaultQuerygetTestsResolver39CE25D4": { + "ApiTableCDKDefaultQuerygetTestsResolverCB3712E2": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -140,16 +140,16 @@ }, "FieldName": "getTests", "TypeName": "Query", - "DataSourceName": "DynamoDbCDKDefault", + "DataSourceName": "TableCDKDefault", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApiDynamoDbCDKDefault5BF6C4EC" + "ApiTableCDKDefault0035EEA0" ] }, - "ApiDynamoDbCDKDefaultMutationaddTestResolverB340117E": { + "ApiTableCDKDefaultMutationaddTestResolver8087CE09": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -157,13 +157,13 @@ }, "FieldName": "addTest", "TypeName": "Mutation", - "DataSourceName": "DynamoDbCDKDefault", + "DataSourceName": "TableCDKDefault", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiDynamoDbCDKDefault5BF6C4EC" + "ApiTableCDKDefault0035EEA0" ] }, "TestTable5769773A": { diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json index 86284c0deb8f4..9f9ee37ed3dd7 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json @@ -109,7 +109,7 @@ "Definition": "type test @aws_iam {\n id: String!\n version: String!\n}\n\ntype Query {\n getTest(id: String!): test\n getTests: [ test! ]\n @aws_iam \n}\n\ninput TestInput {\n version: String!\n}\n\ntype Mutation {\n addTest(input: TestInput!): test\n @aws_iam\n}\n" } }, - "ApiDynamoDbCDKDefaultServiceRoleFF246E00": { + "ApiTableCDKDefaultServiceRoleF54231AA": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -126,7 +126,7 @@ } } }, - "ApiDynamoDbCDKDefaultServiceRoleDefaultPolicy2BC1F6C3": { + "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -160,15 +160,15 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiDynamoDbCDKDefaultServiceRoleDefaultPolicy2BC1F6C3", + "PolicyName": "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657", "Roles": [ { - "Ref": "ApiDynamoDbCDKDefaultServiceRoleFF246E00" + "Ref": "ApiTableCDKDefaultServiceRoleF54231AA" } ] } }, - "ApiDynamoDbCDKDefault5BF6C4EC": { + "ApiTableCDKDefault0035EEA0": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -177,7 +177,7 @@ "ApiId" ] }, - "Name": "DynamoDbCDKDefault", + "Name": "TableCDKDefault", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -189,13 +189,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiDynamoDbCDKDefaultServiceRoleFF246E00", + "ApiTableCDKDefaultServiceRoleF54231AA", "Arn" ] } } }, - "ApiDynamoDbCDKDefaultQuerygetTestResolverCC295D20": { + "ApiTableCDKDefaultQuerygetTestResolverD961215D": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -206,17 +206,17 @@ }, "FieldName": "getTest", "TypeName": "Query", - "DataSourceName": "DynamoDbCDKDefault", + "DataSourceName": "TableCDKDefault", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\": \"2017-02-28\", \"operation\": \"GetItem\", \"key\": {\"id\": $util.dynamodb.toDynamoDBJson($ctx.args.id)}}", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiDynamoDbCDKDefault5BF6C4EC", - "ApiSchema510EECD7" + "ApiSchema510EECD7", + "ApiTableCDKDefault0035EEA0" ] }, - "ApiDynamoDbCDKDefaultQuerygetTestsResolver39CE25D4": { + "ApiTableCDKDefaultQuerygetTestsResolverCB3712E2": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -227,17 +227,17 @@ }, "FieldName": "getTests", "TypeName": "Query", - "DataSourceName": "DynamoDbCDKDefault", + "DataSourceName": "TableCDKDefault", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApiDynamoDbCDKDefault5BF6C4EC", - "ApiSchema510EECD7" + "ApiSchema510EECD7", + "ApiTableCDKDefault0035EEA0" ] }, - "ApiDynamoDbCDKDefaultMutationaddTestResolverB340117E": { + "ApiTableCDKDefaultMutationaddTestResolver8087CE09": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -248,14 +248,14 @@ }, "FieldName": "addTest", "TypeName": "Mutation", - "DataSourceName": "DynamoDbCDKDefault", + "DataSourceName": "TableCDKDefault", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiDynamoDbCDKDefault5BF6C4EC", - "ApiSchema510EECD7" + "ApiSchema510EECD7", + "ApiTableCDKDefault0035EEA0" ] }, "TestTable5769773A": { From d7678bab9310ad14c5fb37dd1b0484b920cb4da7 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Mon, 3 Aug 2020 09:38:03 -0700 Subject: [PATCH 12/17] adjust documentation --- .../aws-appsync/lib/graphqlapi-base.ts | 45 ++++++++++--------- .../aws-appsync/test/appsync-dynamodb.test.ts | 6 +-- .../aws-appsync/test/appsync-http.test.ts | 6 +-- .../aws-appsync/test/appsync-lambda.test.ts | 6 +-- .../aws-appsync/test/appsync-none.test.ts | 6 +-- .../test/integ.api-import.expected.json | 30 ++++++------- .../test/integ.graphql-iam.expected.json | 38 ++++++++-------- .../test/integ.graphql.expected.json | 24 +++++----- 8 files changed, 81 insertions(+), 80 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index 4235a0cafeb2e..4e86327293887 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -10,14 +10,15 @@ export interface DataSourceOptions { /** * The name of the data source * - * @default - 'CDKDefault' + * @default - Automatically generated name 'CDKDataSource' + * i.e. (LambdaCDKDataSource) */ readonly name?: string; /** * The description of the data source * - * @default - undefined + * @default - No description */ readonly description?: string; } @@ -47,8 +48,8 @@ export interface IGraphQLApi extends IResource { * and for backend changes that don't require a data source. * * @param options The optional configuration for this data source - * @default name - 'NoneCDKDefault' - * description - undefined + * @default name - 'NoneCDKDataSource' + * description - No description */ addNoneDataSource(options?: DataSourceOptions): NoneDataSource; @@ -57,8 +58,8 @@ export interface IGraphQLApi extends IResource { * * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - 'DynamoDbCDKDefault' - * description - undefined + * @default name - 'DynamoDbCDKDataSource' + * description - No description */ addDynamoDbDataSource(table: ITable, options?: DataSourceOptions): DynamoDbDataSource; @@ -67,8 +68,8 @@ export interface IGraphQLApi extends IResource { * * @param endpoint The http endpoint * @param options The optional configuration for this data source - * @default name - 'HttpCDKDefault' - * description - undefined + * @default name - 'HttpCDKDataSource' + * description - No description */ addHttpDataSource(endpoint: string, options?: DataSourceOptions): HttpDataSource; @@ -77,8 +78,8 @@ export interface IGraphQLApi extends IResource { * * @param lambdaFunction The Lambda function to call to interact with this data source * @param options The optional configuration for this data source - * @default name - 'LambdaCDKDefault' - * description - undefined + * @default name - 'LambdaCDKDataSource' + * description - No description */ addLambdaDataSource(lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource; @@ -111,11 +112,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * and for backend changes that don't require a data source. * * @param options The optional configuration for this data source - * @default name - 'NoneCDKDefault' - * description - undefined + * @default name - 'NoneCDKDataSource' + * description - No description */ public addNoneDataSource(options?: DataSourceOptions): NoneDataSource { - const name = options?.name ?? 'NoneCDKDefault'; + const name = options?.name ?? 'NoneCDKDataSource'; return new NoneDataSource(this, name, { api: this, name: name, @@ -128,11 +129,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - 'TableCDKDefault' - * description - undefined + * @default name - 'DynamoDbCDKDataSource' + * description - No description */ public addDynamoDbDataSource(table: ITable, options?: DataSourceOptions): DynamoDbDataSource { - const name = options?.name ?? 'TableCDKDefault'; + const name = options?.name ?? 'DynamoDbCDKDataSource'; return new DynamoDbDataSource(this, name, { api: this, table, @@ -146,11 +147,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * * @param endpoint The http endpoint * @param options The optional configuration for this data source - * @default name - 'HttpCDKDefault' - * description - undefined + * @default name - 'HttpCDKDataSource' + * description - No description */ public addHttpDataSource(endpoint: string, options?: DataSourceOptions): HttpDataSource { - const name = options?.name ?? 'HttpCDKDefault'; + const name = options?.name ?? 'HttpCDKDataSource'; return new HttpDataSource(this, name, { api: this, endpoint, @@ -164,11 +165,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * * @param lambdaFunction The Lambda function to call to interact with this data source * @param options The optional configuration for this data source - * @default name - 'LambdaCDKDefault' - * description - undefined + * @default name - 'LambdaCDKDataSource' + * description - No description */ public addLambdaDataSource(lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource { - const name = options?.name ?? 'LambdaCDKDefault'; + const name = options?.name ?? 'LambdaCDKDataSource'; return new LambdaDataSource(this, name, { api: this, lambdaFunction, diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts index d3b032415dea2..0e25e8daf9913 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts @@ -32,14 +32,14 @@ describe('DynamoDb Data Source configuration', () => { }); }); - test('default configuration produces name `TableCDKDefault`', () => { + test('default configuration produces name `DynamoDbCDKDataSource`', () => { // WHEN api.addDynamoDbDataSource(table); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AMAZON_DYNAMODB', - Name: 'TableCDKDefault', + Name: 'DynamoDbCDKDataSource', }); }); @@ -79,7 +79,7 @@ describe('DynamoDb Data Source configuration', () => { }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'TableCDKDefault\' in GraphQLApi [baseApi]'); + expect(when).toThrow('There is already a Construct with name \'DynamoDbCDKDataSource\' in GraphQLApi [baseApi]'); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts index 886581a75f74e..45d0c79b3712b 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts @@ -19,14 +19,14 @@ beforeEach(() => { describe('Http Data Source configuration', () => { - test('default configuration produces name `HttpCDKDefault`', () => { + test('default configuration produces name `HttpCDKDataSource`', () => { // WHEN api.addHttpDataSource(endpoint); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'HTTP', - Name: 'HttpCDKDefault', + Name: 'HttpCDKDataSource', }); }); @@ -66,7 +66,7 @@ describe('Http Data Source configuration', () => { }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'HttpCDKDefault\' in GraphQLApi [baseApi]'); + expect(when).toThrow('There is already a Construct with name \'HttpCDKDataSource\' in GraphQLApi [baseApi]'); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts index 13ecd7b6af951..be500cfb4ac49 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts @@ -27,14 +27,14 @@ describe('Lambda Data Source configuration', () => { }); }); - test('default configuration produces name `TableCDKDefault`', () => { + test('default configuration produces name `TableCDKDataSource`', () => { // WHEN api.addLambdaDataSource(func); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AWS_LAMBDA', - Name: 'LambdaCDKDefault', + Name: 'LambdaCDKDataSource', }); }); @@ -74,7 +74,7 @@ describe('Lambda Data Source configuration', () => { }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'LambdaCDKDefault\' in GraphQLApi [baseApi]'); + expect(when).toThrow('There is already a Construct with name \'LambdaCDKDataSource\' in GraphQLApi [baseApi]'); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts index adda764fa1a77..bcee1a50a02fc 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts @@ -17,14 +17,14 @@ beforeEach(() => { describe('DynamoDb Data Source configuration', () => { - test('default configuration produces name `NoneCDKDefault`', () => { + test('default configuration produces name `NoneCDKDataSource`', () => { // WHEN api.addNoneDataSource(); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'NONE', - Name: 'NoneCDKDefault', + Name: 'NoneCDKDataSource', }); }); @@ -64,7 +64,7 @@ describe('DynamoDb Data Source configuration', () => { }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'NoneCDKDefault\' in GraphQLApi [baseApi]'); + expect(when).toThrow('There is already a Construct with name \'NoneCDKDataSource\' in GraphQLApi [baseApi]'); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json index f0c9b2f4aa078..65b9ad2748134 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json @@ -49,7 +49,7 @@ }, { "Resources": { - "ApiTableCDKDefaultServiceRoleF54231AA": { + "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -66,7 +66,7 @@ } } }, - "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657": { + "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -100,21 +100,21 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657", + "PolicyName": "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A", "Roles": [ { - "Ref": "ApiTableCDKDefaultServiceRoleF54231AA" + "Ref": "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05" } ] } }, - "ApiTableCDKDefault0035EEA0": { + "ApiDynamoDbCDKDataSource32962474": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" }, - "Name": "TableCDKDefault", + "Name": "DynamoDbCDKDataSource", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -126,13 +126,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiTableCDKDefaultServiceRoleF54231AA", + "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05", "Arn" ] } } }, - "ApiTableCDKDefaultQuerygetTestsResolverCB3712E2": { + "ApiDynamoDbCDKDataSourceQuerygetTestsResolver9705E49C": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -140,16 +140,16 @@ }, "FieldName": "getTests", "TypeName": "Query", - "DataSourceName": "TableCDKDefault", + "DataSourceName": "DynamoDbCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApiTableCDKDefault0035EEA0" + "ApiDynamoDbCDKDataSource32962474" ] }, - "ApiTableCDKDefaultMutationaddTestResolver8087CE09": { + "ApiDynamoDbCDKDataSourceMutationaddTestResolver17820EE2": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -157,13 +157,13 @@ }, "FieldName": "addTest", "TypeName": "Mutation", - "DataSourceName": "TableCDKDefault", + "DataSourceName": "DynamoDbCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiTableCDKDefault0035EEA0" + "ApiDynamoDbCDKDataSource32962474" ] }, "TestTable5769773A": { @@ -186,13 +186,13 @@ "UpdateReplacePolicy": "Delete", "DeletionPolicy": "Delete" }, - "api2NoneCDKDefaultCFB889A5": { + "api2NoneCDKDataSourceFEEDF6D1": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" }, - "Name": "NoneCDKDefault", + "Name": "NoneCDKDataSource", "Type": "NONE" } } diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json index 9f9ee37ed3dd7..ef57e2e7abfa0 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json @@ -109,7 +109,7 @@ "Definition": "type test @aws_iam {\n id: String!\n version: String!\n}\n\ntype Query {\n getTest(id: String!): test\n getTests: [ test! ]\n @aws_iam \n}\n\ninput TestInput {\n version: String!\n}\n\ntype Mutation {\n addTest(input: TestInput!): test\n @aws_iam\n}\n" } }, - "ApiTableCDKDefaultServiceRoleF54231AA": { + "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -126,7 +126,7 @@ } } }, - "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657": { + "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -160,15 +160,15 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiTableCDKDefaultServiceRoleDefaultPolicy745D6657", + "PolicyName": "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A", "Roles": [ { - "Ref": "ApiTableCDKDefaultServiceRoleF54231AA" + "Ref": "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05" } ] } }, - "ApiTableCDKDefault0035EEA0": { + "ApiDynamoDbCDKDataSource32962474": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -177,7 +177,7 @@ "ApiId" ] }, - "Name": "TableCDKDefault", + "Name": "DynamoDbCDKDataSource", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -189,13 +189,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiTableCDKDefaultServiceRoleF54231AA", + "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05", "Arn" ] } } }, - "ApiTableCDKDefaultQuerygetTestResolverD961215D": { + "ApiDynamoDbCDKDataSourceQuerygetTestResolver0DB284BB": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -206,17 +206,17 @@ }, "FieldName": "getTest", "TypeName": "Query", - "DataSourceName": "TableCDKDefault", + "DataSourceName": "DynamoDbCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\": \"2017-02-28\", \"operation\": \"GetItem\", \"key\": {\"id\": $util.dynamodb.toDynamoDBJson($ctx.args.id)}}", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiSchema510EECD7", - "ApiTableCDKDefault0035EEA0" + "ApiDynamoDbCDKDataSource32962474", + "ApiSchema510EECD7" ] }, - "ApiTableCDKDefaultQuerygetTestsResolverCB3712E2": { + "ApiDynamoDbCDKDataSourceQuerygetTestsResolver9705E49C": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -227,17 +227,17 @@ }, "FieldName": "getTests", "TypeName": "Query", - "DataSourceName": "TableCDKDefault", + "DataSourceName": "DynamoDbCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApiSchema510EECD7", - "ApiTableCDKDefault0035EEA0" + "ApiDynamoDbCDKDataSource32962474", + "ApiSchema510EECD7" ] }, - "ApiTableCDKDefaultMutationaddTestResolver8087CE09": { + "ApiDynamoDbCDKDataSourceMutationaddTestResolver17820EE2": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -248,14 +248,14 @@ }, "FieldName": "addTest", "TypeName": "Mutation", - "DataSourceName": "TableCDKDefault", + "DataSourceName": "DynamoDbCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiSchema510EECD7", - "ApiTableCDKDefault0035EEA0" + "ApiDynamoDbCDKDataSource32962474", + "ApiSchema510EECD7" ] }, "TestTable5769773A": { diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json index acfc17bf98c2c..9995e7e4b7b56 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json @@ -121,7 +121,7 @@ "Definition": "type ServiceVersion @aws_api_key {\n version: String!\n}\n\ntype Customer @aws_api_key {\n id: String!\n name: String!\n}\n\ninput SaveCustomerInput {\n name: String!\n}\n\ntype Order @aws_api_key {\n customer: String!\n order: String!\n}\n\ntype Payment @aws_api_key {\n id: String!\n amount: String!\n}\n\ninput PaymentInput {\n amount: String!\n}\n\ntype Query @aws_api_key {\n getServiceVersion: ServiceVersion\n getCustomers: [Customer]\n getCustomer(id: String): Customer\n getCustomerOrdersEq(customer: String): Order\n getCustomerOrdersLt(customer: String): Order\n getCustomerOrdersLe(customer: String): Order\n getCustomerOrdersGt(customer: String): Order\n getCustomerOrdersGe(customer: String): Order\n getCustomerOrdersFilter(customer: String, order: String): Order\n getCustomerOrdersBetween(customer: String, order1: String, order2: String): Order\n getPayment(id: String): Payment\n}\n\ninput FirstOrderInput {\n product: String!\n quantity: Int!\n}\n\ntype Mutation @aws_api_key {\n addCustomer(customer: SaveCustomerInput!): Customer\n saveCustomer(id: String!, customer: SaveCustomerInput!): Customer\n removeCustomer(id: String!): Customer\n saveCustomerWithFirstOrder(customer: SaveCustomerInput!, order: FirstOrderInput!, referral: String): Order\n savePayment(payment: PaymentInput!): Payment\n doPostOnAws: String!\n}\n" } }, - "ApiNoneCDKDefault17ACBBC2": { + "ApiNoneCDKDataSourceDBC45994": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -130,11 +130,11 @@ "ApiId" ] }, - "Name": "NoneCDKDefault", + "Name": "NoneCDKDataSource", "Type": "NONE" } }, - "ApiNoneCDKDefaultQuerygetServiceVersionResolverD7F3590D": { + "ApiNoneCDKDataSourceQuerygetServiceVersionResolverA5AD60E6": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -145,13 +145,13 @@ }, "FieldName": "getServiceVersion", "TypeName": "Query", - "DataSourceName": "NoneCDKDefault", + "DataSourceName": "NoneCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\":\"2017-02-28\"}", "ResponseMappingTemplate": "{\"version\":\"v1\"}" }, "DependsOn": [ - "ApiNoneCDKDefault17ACBBC2", + "ApiNoneCDKDataSourceDBC45994", "ApiSchema510EECD7" ] }, @@ -740,7 +740,7 @@ "ApiSchema510EECD7" ] }, - "ApiHttpCDKDefaultServiceRole0E0C2E53": { + "ApiHttpCDKDataSourceServiceRole992CDB9E": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -757,7 +757,7 @@ } } }, - "ApiHttpCDKDefault2B4C6D63": { + "ApiHttpCDKDataSourceA919CDB4": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -766,20 +766,20 @@ "ApiId" ] }, - "Name": "HttpCDKDefault", + "Name": "HttpCDKDataSource", "Type": "HTTP", "HttpConfig": { "Endpoint": "https://aws.amazon.com/" }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiHttpCDKDefaultServiceRole0E0C2E53", + "ApiHttpCDKDataSourceServiceRole992CDB9E", "Arn" ] } } }, - "ApiHttpCDKDefaultMutationdoPostOnAwsResolver208308C9": { + "ApiHttpCDKDataSourceMutationdoPostOnAwsResolverBDE25968": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -790,13 +790,13 @@ }, "FieldName": "doPostOnAws", "TypeName": "Mutation", - "DataSourceName": "HttpCDKDefault", + "DataSourceName": "HttpCDKDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\n \"version\": \"2018-05-29\",\n \"method\": \"POST\",\n # if full path is https://api.xxxxxxxxx.com/posts then resourcePath would be /posts\n \"resourcePath\": \"/path/123\",\n \"params\":{\n \"body\": $util.toJson($ctx.args),\n \"headers\":{\n \"Content-Type\": \"application/json\",\n \"Authorization\": \"$ctx.request.headers.Authorization\"\n }\n }\n }", "ResponseMappingTemplate": "\n ## Raise a GraphQL field error in case of a datasource invocation error\n #if($ctx.error)\n $util.error($ctx.error.message, $ctx.error.type)\n #end\n ## if the response status code is not 200, then return an error. Else return the body **\n #if($ctx.result.statusCode == 200)\n ## If response is 200, return the body.\n $ctx.result.body\n #else\n ## If response is not 200, append the response to error block.\n $utils.appendError($ctx.result.body, \"$ctx.result.statusCode\")\n #end\n " }, "DependsOn": [ - "ApiHttpCDKDefault2B4C6D63", + "ApiHttpCDKDataSourceA919CDB4", "ApiSchema510EECD7" ] }, From c066ba9c60fdae5285ec86e6e3e5503f375e1d95 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Wed, 5 Aug 2020 11:46:50 -0700 Subject: [PATCH 13/17] changes to addXxxDataSource api and data source implementation --- .../@aws-cdk/aws-appsync/lib/data-source.ts | 10 +- .../aws-appsync/lib/graphqlapi-base.ts | 53 +++--- .../@aws-cdk/aws-appsync/lib/graphqlapi.ts | 4 +- .../aws-appsync/test/appsync-dynamodb.test.ts | 20 +-- .../aws-appsync/test/appsync-http.test.ts | 20 +-- .../aws-appsync/test/appsync-lambda.test.ts | 20 +-- .../aws-appsync/test/appsync-none.test.ts | 33 ++-- .../test/integ.api-import.expected.json | 30 ++-- .../aws-appsync/test/integ.api-import.ts | 6 +- .../test/integ.graphql-iam.expected.json | 32 ++-- .../aws-appsync/test/integ.graphql-iam.ts | 2 +- .../test/integ.graphql.expected.json | 156 +++++++++--------- .../aws-appsync/test/integ.graphql.ts | 10 +- 13 files changed, 204 insertions(+), 192 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/data-source.ts b/packages/@aws-cdk/aws-appsync/lib/data-source.ts index 0cd2a2995930a..329ca8685e008 100644 --- a/packages/@aws-cdk/aws-appsync/lib/data-source.ts +++ b/packages/@aws-cdk/aws-appsync/lib/data-source.ts @@ -16,8 +16,10 @@ export interface BaseDataSourceProps { readonly api: IGraphQLApi; /** * The name of the data source + * + * @default - id of data source */ - readonly name: string; + readonly name?: string; /** * the description of the data source * @@ -100,15 +102,15 @@ export abstract class BaseDataSource extends Construct { if (extended.type !== 'NONE') { this.serviceRole = props.serviceRole || new Role(this, 'ServiceRole', { assumedBy: new ServicePrincipal('appsync') }); } - + const name = props.name ?? id; this.ds = new CfnDataSource(this, 'Resource', { apiId: props.api.apiId, - name: props.name, + name: name, description: props.description, serviceRoleArn: this.serviceRole?.roleArn, ...extended, }); - this.name = props.name; + this.name = name; this.api = props.api; } diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index 4e86327293887..e912f79b1bf2d 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -8,10 +8,9 @@ import { DynamoDbDataSource, HttpDataSource, LambdaDataSource, NoneDataSource } */ export interface DataSourceOptions { /** - * The name of the data source + * The name of the data source, overrides the id given by cdk * - * @default - Automatically generated name 'CDKDataSource' - * i.e. (LambdaCDKDataSource) + * @default - the id provisioned */ readonly name?: string; @@ -47,41 +46,45 @@ export interface IGraphQLApi extends IResource { * add a new dummy data source to this API. Useful for pipeline resolvers * and for backend changes that don't require a data source. * + * @param id The data source's id * @param options The optional configuration for this data source - * @default name - 'NoneCDKDataSource' + * @default name - the id * description - No description */ - addNoneDataSource(options?: DataSourceOptions): NoneDataSource; + addNoneDataSource(id: string, options?: DataSourceOptions): NoneDataSource; /** * add a new DynamoDB data source to this API * + * @param id The data source's id * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - 'DynamoDbCDKDataSource' + * @default name - the id * description - No description */ - addDynamoDbDataSource(table: ITable, options?: DataSourceOptions): DynamoDbDataSource; + addDynamoDbDataSource(id: string, table: ITable, options?: DataSourceOptions): DynamoDbDataSource; /** * add a new http data source to this API * + * @param id The data source's id * @param endpoint The http endpoint * @param options The optional configuration for this data source - * @default name - 'HttpCDKDataSource' + * @default name - 'the id * description - No description */ - addHttpDataSource(endpoint: string, options?: DataSourceOptions): HttpDataSource; + addHttpDataSource(id: string, endpoint: string, options?: DataSourceOptions): HttpDataSource; /** * add a new Lambda data source to this API * + * @param id The data source's id * @param lambdaFunction The Lambda function to call to interact with this data source * @param options The optional configuration for this data source - * @default name - 'LambdaCDKDataSource' + * @default name - the id * description - No description */ - addLambdaDataSource(lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource; + addLambdaDataSource(id: string, lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource; /** * Add schema dependency if not imported @@ -115,11 +118,10 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * @default name - 'NoneCDKDataSource' * description - No description */ - public addNoneDataSource(options?: DataSourceOptions): NoneDataSource { - const name = options?.name ?? 'NoneCDKDataSource'; - return new NoneDataSource(this, name, { + public addNoneDataSource(id: string, options?: DataSourceOptions): NoneDataSource { + return new NoneDataSource(this, id, { api: this, - name: name, + name: options?.name, description: options?.description, }); } @@ -132,12 +134,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * @default name - 'DynamoDbCDKDataSource' * description - No description */ - public addDynamoDbDataSource(table: ITable, options?: DataSourceOptions): DynamoDbDataSource { - const name = options?.name ?? 'DynamoDbCDKDataSource'; - return new DynamoDbDataSource(this, name, { + public addDynamoDbDataSource(id: string, table: ITable, options?: DataSourceOptions): DynamoDbDataSource { + return new DynamoDbDataSource(this, id, { api: this, table, - name, + name: options?.name, description: options?.description, }); } @@ -150,12 +151,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * @default name - 'HttpCDKDataSource' * description - No description */ - public addHttpDataSource(endpoint: string, options?: DataSourceOptions): HttpDataSource { - const name = options?.name ?? 'HttpCDKDataSource'; - return new HttpDataSource(this, name, { + public addHttpDataSource(id: string, endpoint: string, options?: DataSourceOptions): HttpDataSource { + return new HttpDataSource(this, id, { api: this, endpoint, - name, + name: options?.name, description: options?.description, }); } @@ -168,12 +168,11 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { * @default name - 'LambdaCDKDataSource' * description - No description */ - public addLambdaDataSource(lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource { - const name = options?.name ?? 'LambdaCDKDataSource'; - return new LambdaDataSource(this, name, { + public addLambdaDataSource(id: string, lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource { + return new LambdaDataSource(this, id, { api: this, lambdaFunction, - name, + name: options?.name, description: options?.description, }); } diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index f7521b8d236da..621c10bd18eb3 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -329,7 +329,7 @@ export interface GraphQLApiAttributes { * the arn for the GraphQL Api * @default - autogenerated arn */ - readonly graphqlArn?: string, + readonly graphqlApiArn?: string, } /** @@ -346,7 +346,7 @@ export class GraphQLApi extends GraphQLApiBase { * @param attrs GraphQL API Attributes of an API */ public static fromGraphqlApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { - const arn = attrs.graphqlArn ?? Stack.of(scope).formatArn({ + const arn = attrs.graphqlApiArn ?? Stack.of(scope).formatArn({ service: 'appsync', resource: `apis/${attrs.graphqlApiId}`, }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts index 0e25e8daf9913..0b7e29de2b295 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts @@ -34,18 +34,18 @@ describe('DynamoDb Data Source configuration', () => { test('default configuration produces name `DynamoDbCDKDataSource`', () => { // WHEN - api.addDynamoDbDataSource(table); + api.addDynamoDbDataSource('ds', table); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AMAZON_DYNAMODB', - Name: 'DynamoDbCDKDataSource', + Name: 'ds', }); }); test('appsync configures name correctly', () => { // WHEN - api.addDynamoDbDataSource(table, { + api.addDynamoDbDataSource('ds', table, { name: 'custom', }); @@ -58,7 +58,7 @@ describe('DynamoDb Data Source configuration', () => { test('appsync configures name and description correctly', () => { // WHEN - api.addDynamoDbDataSource(table, { + api.addDynamoDbDataSource('ds', table, { name: 'custom', description: 'custom description', }); @@ -74,12 +74,12 @@ describe('DynamoDb Data Source configuration', () => { test('appsync errors when creating multiple dynamo db data sources with no configuration', () => { // WHEN const when = () => { - api.addDynamoDbDataSource(table); - api.addDynamoDbDataSource(table); + api.addDynamoDbDataSource('ds', table); + api.addDynamoDbDataSource('ds', table); }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'DynamoDbCDKDataSource\' in GraphQLApi [baseApi]'); + expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); }); @@ -167,7 +167,7 @@ describe('adding DynamoDb data source from imported api', () => { const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, }); - importedApi.addDynamoDbDataSource(table); + importedApi.addDynamoDbDataSource('ds', table); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { @@ -181,9 +181,9 @@ describe('adding DynamoDb data source from imported api', () => { // WHEN const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, - graphqlArn: api.arn, + graphqlApiArn: api.arn, }); - importedApi.addDynamoDbDataSource(table); + importedApi.addDynamoDbDataSource('ds', table); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts index 45d0c79b3712b..c8535ba83ff9a 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts @@ -21,18 +21,18 @@ describe('Http Data Source configuration', () => { test('default configuration produces name `HttpCDKDataSource`', () => { // WHEN - api.addHttpDataSource(endpoint); + api.addHttpDataSource('ds', endpoint); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'HTTP', - Name: 'HttpCDKDataSource', + Name: 'ds', }); }); test('appsync configures name correctly', () => { // WHEN - api.addHttpDataSource(endpoint, { + api.addHttpDataSource('ds', endpoint, { name: 'custom', }); @@ -45,7 +45,7 @@ describe('Http Data Source configuration', () => { test('appsync configures name and description correctly', () => { // WHEN - api.addHttpDataSource(endpoint, { + api.addHttpDataSource('ds', endpoint, { name: 'custom', description: 'custom description', }); @@ -61,12 +61,12 @@ describe('Http Data Source configuration', () => { test('appsync errors when creating multiple http data sources with no configuration', () => { // WHEN const when = () => { - api.addHttpDataSource(endpoint); - api.addHttpDataSource(endpoint); + api.addHttpDataSource('ds', endpoint); + api.addHttpDataSource('ds', endpoint); }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'HttpCDKDataSource\' in GraphQLApi [baseApi]'); + expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); }); @@ -76,7 +76,7 @@ describe('adding http data source from imported api', () => { const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, }); - importedApi.addHttpDataSource(endpoint); + importedApi.addHttpDataSource('ds', endpoint); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { @@ -90,9 +90,9 @@ describe('adding http data source from imported api', () => { // WHEN const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, - graphqlArn: api.arn, + graphqlApiArn: api.arn, }); - importedApi.addHttpDataSource(endpoint); + importedApi.addHttpDataSource('ds', endpoint); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts index be500cfb4ac49..eb41a5aa67a53 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts @@ -29,18 +29,18 @@ describe('Lambda Data Source configuration', () => { test('default configuration produces name `TableCDKDataSource`', () => { // WHEN - api.addLambdaDataSource(func); + api.addLambdaDataSource('ds', func); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AWS_LAMBDA', - Name: 'LambdaCDKDataSource', + Name: 'ds', }); }); test('appsync configures name correctly', () => { // WHEN - api.addLambdaDataSource(func, { + api.addLambdaDataSource('ds', func, { name: 'custom', }); @@ -53,7 +53,7 @@ describe('Lambda Data Source configuration', () => { test('appsync configures name and description correctly', () => { // WHEN - api.addLambdaDataSource(func, { + api.addLambdaDataSource('ds', func, { name: 'custom', description: 'custom description', }); @@ -69,12 +69,12 @@ describe('Lambda Data Source configuration', () => { test('appsync errors when creating multiple lambda data sources with no configuration', () => { // WHEN const when = () => { - api.addLambdaDataSource(func); - api.addLambdaDataSource(func); + api.addLambdaDataSource('ds', func); + api.addLambdaDataSource('ds', func); }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'LambdaCDKDataSource\' in GraphQLApi [baseApi]'); + expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); }); @@ -93,7 +93,7 @@ describe('adding lambda data source from imported api',() => { const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, }); - importedApi.addLambdaDataSource(func); + importedApi.addLambdaDataSource('ds', func); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { @@ -107,9 +107,9 @@ describe('adding lambda data source from imported api',() => { // WHEN const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, - graphqlArn: api.arn, + graphqlApiArn: api.arn, }); - importedApi.addLambdaDataSource(func); + importedApi.addLambdaDataSource('ds', func); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts index bcee1a50a02fc..b523200ffbe46 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts @@ -15,22 +15,22 @@ beforeEach(() => { }); }); -describe('DynamoDb Data Source configuration', () => { +describe('None Data Source configuration', () => { test('default configuration produces name `NoneCDKDataSource`', () => { // WHEN - api.addNoneDataSource(); + api.addNoneDataSource('ds'); // EXPECT expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'NONE', - Name: 'NoneCDKDataSource', + Name: 'ds', }); }); test('appsync configures name correctly', () => { // WHEN - api.addNoneDataSource({ + api.addNoneDataSource('ds', { name: 'custom', }); @@ -43,7 +43,7 @@ describe('DynamoDb Data Source configuration', () => { test('appsync configures name and description correctly', () => { // WHEN - api.addNoneDataSource({ + api.addNoneDataSource('ds', { name: 'custom', description: 'custom description', }); @@ -59,12 +59,23 @@ describe('DynamoDb Data Source configuration', () => { test('appsync errors when creating multiple none data sources with no configuration', () => { // WHEN const when = () => { - api.addNoneDataSource(); - api.addNoneDataSource(); + api.addNoneDataSource('ds'); + api.addNoneDataSource('ds'); }; // EXPECT - expect(when).toThrow('There is already a Construct with name \'NoneCDKDataSource\' in GraphQLApi [baseApi]'); + expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); + }); + + test('appsync errors when creating multiple none data sources with same name configuration', () => { + // WHEN + const when = () => { + api.addNoneDataSource('ds1', { name: 'custom' }); + api.addNoneDataSource('ds2', { name: 'custom' }); + }; + + // EXPECT + expect(when).not.toThrowError(); }); }); @@ -74,7 +85,7 @@ describe('adding none data source from imported api', () => { const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, }); - importedApi.addNoneDataSource(); + importedApi.addNoneDataSource('none'); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { @@ -88,9 +99,9 @@ describe('adding none data source from imported api', () => { // WHEN const importedApi = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'importedApi', { graphqlApiId: api.apiId, - graphqlArn: api.arn, + graphqlApiArn: api.arn, }); - importedApi.addNoneDataSource(); + importedApi.addNoneDataSource('none'); // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json index 65b9ad2748134..3a0b9a76b760c 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.expected.json @@ -49,7 +49,7 @@ }, { "Resources": { - "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05": { + "ApidsServiceRoleADC7D124": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -66,7 +66,7 @@ } } }, - "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A": { + "ApidsServiceRoleDefaultPolicyE5E18D6D": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -100,21 +100,21 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A", + "PolicyName": "ApidsServiceRoleDefaultPolicyE5E18D6D", "Roles": [ { - "Ref": "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05" + "Ref": "ApidsServiceRoleADC7D124" } ] } }, - "ApiDynamoDbCDKDataSource32962474": { + "Apids0DB53FEA": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" }, - "Name": "DynamoDbCDKDataSource", + "Name": "ds", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -126,13 +126,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05", + "ApidsServiceRoleADC7D124", "Arn" ] } } }, - "ApiDynamoDbCDKDataSourceQuerygetTestsResolver9705E49C": { + "ApidsQuerygetTestsResolver952F49EE": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -140,16 +140,16 @@ }, "FieldName": "getTests", "TypeName": "Query", - "DataSourceName": "DynamoDbCDKDataSource", + "DataSourceName": "ds", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApiDynamoDbCDKDataSource32962474" + "Apids0DB53FEA" ] }, - "ApiDynamoDbCDKDataSourceMutationaddTestResolver17820EE2": { + "ApidsMutationaddTestResolverBCF0400B": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -157,13 +157,13 @@ }, "FieldName": "addTest", "TypeName": "Mutation", - "DataSourceName": "DynamoDbCDKDataSource", + "DataSourceName": "ds", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiDynamoDbCDKDataSource32962474" + "Apids0DB53FEA" ] }, "TestTable5769773A": { @@ -186,13 +186,13 @@ "UpdateReplacePolicy": "Delete", "DeletionPolicy": "Delete" }, - "api2NoneCDKDataSourceFEEDF6D1": { + "api2noneC88DB89F": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { "Fn::ImportValue": "baseStack:ExportsOutputFnGetAttbaseApiCDA4D43AApiId50287E68" }, - "Name": "NoneCDKDataSource", + "Name": "none", "Type": "NONE" } } diff --git a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts index 2df59cb5e990d..74a8942246e51 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.api-import.ts @@ -42,7 +42,7 @@ const testTable = new db.Table(stack, 'TestTable', { removalPolicy: cdk.RemovalPolicy.DESTROY, }); -const testDS = api.addDynamoDbDataSource(testTable); +const testDS = api.addDynamoDbDataSource('ds', testTable); testDS.createResolver({ typeName: 'Query', @@ -60,9 +60,9 @@ testDS.createResolver({ const api2 = appsync.GraphQLApi.fromGraphqlApiAttributes(stack, 'api2', { graphqlApiId: baseApi.apiId, - graphqlArn: baseApi.arn, + graphqlApiArn: baseApi.arn, }); -api2.addNoneDataSource(); +api2.addNoneDataSource('none'); app.synth(); \ No newline at end of file diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json index ef57e2e7abfa0..af8b7a9702c2c 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.expected.json @@ -109,7 +109,7 @@ "Definition": "type test @aws_iam {\n id: String!\n version: String!\n}\n\ntype Query {\n getTest(id: String!): test\n getTests: [ test! ]\n @aws_iam \n}\n\ninput TestInput {\n version: String!\n}\n\ntype Mutation {\n addTest(input: TestInput!): test\n @aws_iam\n}\n" } }, - "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05": { + "ApidsServiceRoleADC7D124": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -126,7 +126,7 @@ } } }, - "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A": { + "ApidsServiceRoleDefaultPolicyE5E18D6D": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -160,15 +160,15 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiDynamoDbCDKDataSourceServiceRoleDefaultPolicy3E2B077A", + "PolicyName": "ApidsServiceRoleDefaultPolicyE5E18D6D", "Roles": [ { - "Ref": "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05" + "Ref": "ApidsServiceRoleADC7D124" } ] } }, - "ApiDynamoDbCDKDataSource32962474": { + "Apids0DB53FEA": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -177,7 +177,7 @@ "ApiId" ] }, - "Name": "DynamoDbCDKDataSource", + "Name": "testDataSource", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -189,13 +189,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiDynamoDbCDKDataSourceServiceRole9FB7AB05", + "ApidsServiceRoleADC7D124", "Arn" ] } } }, - "ApiDynamoDbCDKDataSourceQuerygetTestResolver0DB284BB": { + "ApidsQuerygetTestResolverCCED7EC2": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -206,17 +206,17 @@ }, "FieldName": "getTest", "TypeName": "Query", - "DataSourceName": "DynamoDbCDKDataSource", + "DataSourceName": "testDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\": \"2017-02-28\", \"operation\": \"GetItem\", \"key\": {\"id\": $util.dynamodb.toDynamoDBJson($ctx.args.id)}}", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiDynamoDbCDKDataSource32962474", + "Apids0DB53FEA", "ApiSchema510EECD7" ] }, - "ApiDynamoDbCDKDataSourceQuerygetTestsResolver9705E49C": { + "ApidsQuerygetTestsResolver952F49EE": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -227,17 +227,17 @@ }, "FieldName": "getTests", "TypeName": "Query", - "DataSourceName": "DynamoDbCDKDataSource", + "DataSourceName": "testDataSource", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApiDynamoDbCDKDataSource32962474", + "Apids0DB53FEA", "ApiSchema510EECD7" ] }, - "ApiDynamoDbCDKDataSourceMutationaddTestResolver17820EE2": { + "ApidsMutationaddTestResolverBCF0400B": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -248,13 +248,13 @@ }, "FieldName": "addTest", "TypeName": "Mutation", - "DataSourceName": "DynamoDbCDKDataSource", + "DataSourceName": "testDataSource", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.test)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApiDynamoDbCDKDataSource32962474", + "Apids0DB53FEA", "ApiSchema510EECD7" ] }, diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.ts b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.ts index 7d540099b5b83..9613070f49dbc 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql-iam.ts @@ -65,7 +65,7 @@ const testTable = new Table(stack, 'TestTable', { removalPolicy: RemovalPolicy.DESTROY, }); -const testDS = api.addDynamoDbDataSource(testTable); +const testDS = api.addDynamoDbDataSource('ds', testTable, {name: 'testDataSource'}); testDS.createResolver({ typeName: 'Query', diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json b/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json index 9995e7e4b7b56..abc4f4a676497 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql.expected.json @@ -121,7 +121,7 @@ "Definition": "type ServiceVersion @aws_api_key {\n version: String!\n}\n\ntype Customer @aws_api_key {\n id: String!\n name: String!\n}\n\ninput SaveCustomerInput {\n name: String!\n}\n\ntype Order @aws_api_key {\n customer: String!\n order: String!\n}\n\ntype Payment @aws_api_key {\n id: String!\n amount: String!\n}\n\ninput PaymentInput {\n amount: String!\n}\n\ntype Query @aws_api_key {\n getServiceVersion: ServiceVersion\n getCustomers: [Customer]\n getCustomer(id: String): Customer\n getCustomerOrdersEq(customer: String): Order\n getCustomerOrdersLt(customer: String): Order\n getCustomerOrdersLe(customer: String): Order\n getCustomerOrdersGt(customer: String): Order\n getCustomerOrdersGe(customer: String): Order\n getCustomerOrdersFilter(customer: String, order: String): Order\n getCustomerOrdersBetween(customer: String, order1: String, order2: String): Order\n getPayment(id: String): Payment\n}\n\ninput FirstOrderInput {\n product: String!\n quantity: Int!\n}\n\ntype Mutation @aws_api_key {\n addCustomer(customer: SaveCustomerInput!): Customer\n saveCustomer(id: String!, customer: SaveCustomerInput!): Customer\n removeCustomer(id: String!): Customer\n saveCustomerWithFirstOrder(customer: SaveCustomerInput!, order: FirstOrderInput!, referral: String): Order\n savePayment(payment: PaymentInput!): Payment\n doPostOnAws: String!\n}\n" } }, - "ApiNoneCDKDataSourceDBC45994": { + "Apinone1F55F3F3": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -130,11 +130,11 @@ "ApiId" ] }, - "Name": "NoneCDKDataSource", + "Name": "None", "Type": "NONE" } }, - "ApiNoneCDKDataSourceQuerygetServiceVersionResolverA5AD60E6": { + "ApinoneQuerygetServiceVersionResolver336A3C2C": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -145,17 +145,17 @@ }, "FieldName": "getServiceVersion", "TypeName": "Query", - "DataSourceName": "NoneCDKDataSource", + "DataSourceName": "None", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\":\"2017-02-28\"}", "ResponseMappingTemplate": "{\"version\":\"v1\"}" }, "DependsOn": [ - "ApiNoneCDKDataSourceDBC45994", + "Apinone1F55F3F3", "ApiSchema510EECD7" ] }, - "ApicustomerServiceRole346E89CA": { + "ApicustomerDsServiceRole76CAD539": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -172,7 +172,7 @@ } } }, - "ApicustomerServiceRoleDefaultPolicy4BC79BA3": { + "ApicustomerDsServiceRoleDefaultPolicyF8E72AE7": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -206,15 +206,15 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApicustomerServiceRoleDefaultPolicy4BC79BA3", + "PolicyName": "ApicustomerDsServiceRoleDefaultPolicyF8E72AE7", "Roles": [ { - "Ref": "ApicustomerServiceRole346E89CA" + "Ref": "ApicustomerDsServiceRole76CAD539" } ] } }, - "ApicustomerA4A81100": { + "ApicustomerDsFE73DAC5": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -223,7 +223,7 @@ "ApiId" ] }, - "Name": "customer", + "Name": "Customer", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -235,13 +235,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApicustomerServiceRole346E89CA", + "ApicustomerDsServiceRole76CAD539", "Arn" ] } } }, - "ApicustomerQuerygetCustomersResolverE0EEF328": { + "ApicustomerDsQuerygetCustomersResolverA74C8A2E": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -252,17 +252,17 @@ }, "FieldName": "getCustomers", "TypeName": "Query", - "DataSourceName": "customer", + "DataSourceName": "Customer", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Scan\"}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "ApicustomerA4A81100", + "ApicustomerDsFE73DAC5", "ApiSchema510EECD7" ] }, - "ApicustomerQuerygetCustomerResolverE52762E2": { + "ApicustomerDsQuerygetCustomerResolver3649A130": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -273,17 +273,17 @@ }, "FieldName": "getCustomer", "TypeName": "Query", - "DataSourceName": "customer", + "DataSourceName": "Customer", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\": \"2017-02-28\", \"operation\": \"GetItem\", \"key\": {\"id\": $util.dynamodb.toDynamoDBJson($ctx.args.id)}}", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApicustomerA4A81100", + "ApicustomerDsFE73DAC5", "ApiSchema510EECD7" ] }, - "ApicustomerMutationaddCustomerResolver5D475955": { + "ApicustomerDsMutationaddCustomerResolver4DE5B517": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -294,17 +294,17 @@ }, "FieldName": "addCustomer", "TypeName": "Mutation", - "DataSourceName": "customer", + "DataSourceName": "Customer", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.customer)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApicustomerA4A81100", + "ApicustomerDsFE73DAC5", "ApiSchema510EECD7" ] }, - "ApicustomerMutationsaveCustomerResolverB88520D1": { + "ApicustomerDsMutationsaveCustomerResolver241DD231": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -315,17 +315,17 @@ }, "FieldName": "saveCustomer", "TypeName": "Mutation", - "DataSourceName": "customer", + "DataSourceName": "Customer", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.customer)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($ctx.args.id)\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApicustomerA4A81100", + "ApicustomerDsFE73DAC5", "ApiSchema510EECD7" ] }, - "ApicustomerMutationsaveCustomerWithFirstOrderResolverD9DFFE0F": { + "ApicustomerDsMutationsaveCustomerWithFirstOrderResolver7DE2CBC8": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -336,17 +336,17 @@ }, "FieldName": "saveCustomerWithFirstOrder", "TypeName": "Mutation", - "DataSourceName": "customer", + "DataSourceName": "Customer", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.order)\n $util.qr($input.put(\"referral\", referral))\n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"order\" : $util.dynamodb.toDynamoDBJson($util.autoId()),\"customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer.id)\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApicustomerA4A81100", + "ApicustomerDsFE73DAC5", "ApiSchema510EECD7" ] }, - "ApicustomerMutationremoveCustomerResolverC1CF2E35": { + "ApicustomerDsMutationremoveCustomerResolverAD3AE7F5": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -357,17 +357,17 @@ }, "FieldName": "removeCustomer", "TypeName": "Mutation", - "DataSourceName": "customer", + "DataSourceName": "Customer", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\": \"2017-02-28\", \"operation\": \"DeleteItem\", \"key\": {\"id\": $util.dynamodb.toDynamoDBJson($ctx.args.id)}}", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApicustomerA4A81100", + "ApicustomerDsFE73DAC5", "ApiSchema510EECD7" ] }, - "ApiorderServiceRoleAD898930": { + "ApiorderDsServiceRoleCC2040C0": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -384,7 +384,7 @@ } } }, - "ApiorderServiceRoleDefaultPolicyC918AE08": { + "ApiorderDsServiceRoleDefaultPolicy3315FCF4": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -418,15 +418,15 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApiorderServiceRoleDefaultPolicyC918AE08", + "PolicyName": "ApiorderDsServiceRoleDefaultPolicy3315FCF4", "Roles": [ { - "Ref": "ApiorderServiceRoleAD898930" + "Ref": "ApiorderDsServiceRoleCC2040C0" } ] } }, - "Apiorder88C17B87": { + "ApiorderDsB50C8AAD": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -435,7 +435,7 @@ "ApiId" ] }, - "Name": "order", + "Name": "Order", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -447,13 +447,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiorderServiceRoleAD898930", + "ApiorderDsServiceRoleCC2040C0", "Arn" ] } } }, - "ApiorderQuerygetCustomerOrdersEqResolver84523DEA": { + "ApiorderDsQuerygetCustomerOrdersEqResolverEF9D5350": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -464,17 +464,17 @@ }, "FieldName": "getCustomerOrdersEq", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer = :customer\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApiorderQuerygetCustomerOrdersLtResolver9D083A9F": { + "ApiorderDsQuerygetCustomerOrdersLtResolver909F3D8F": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -485,17 +485,17 @@ }, "FieldName": "getCustomerOrdersLt", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer < :customer\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApiorderQuerygetCustomerOrdersLeResolver1ACB2AFA": { + "ApiorderDsQuerygetCustomerOrdersLeResolverF230A8BE": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -506,17 +506,17 @@ }, "FieldName": "getCustomerOrdersLe", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer <= :customer\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApiorderQuerygetCustomerOrdersGtResolverD5F872BC": { + "ApiorderDsQuerygetCustomerOrdersGtResolverF01F806B": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -527,17 +527,17 @@ }, "FieldName": "getCustomerOrdersGt", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer > :customer\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApiorderQuerygetCustomerOrdersGeResolver9FECFB88": { + "ApiorderDsQuerygetCustomerOrdersGeResolver63CAD303": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -548,17 +548,17 @@ }, "FieldName": "getCustomerOrdersGe", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer >= :customer\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApiorderQuerygetCustomerOrdersFilterResolverDFFAA0FF": { + "ApiorderDsQuerygetCustomerOrdersFilterResolverCD2B8747": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -569,17 +569,17 @@ }, "FieldName": "getCustomerOrdersFilter", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer = :customer AND begins_with(#order, :order)\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\", \"#order\" : \"order\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer), \":order\" : $util.dynamodb.toDynamoDBJson($ctx.args.order)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApiorderQuerygetCustomerOrdersBetweenResolverE6CB3776": { + "ApiorderDsQuerygetCustomerOrdersBetweenResolver7DEE368E": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -590,17 +590,17 @@ }, "FieldName": "getCustomerOrdersBetween", "TypeName": "Query", - "DataSourceName": "order", + "DataSourceName": "Order", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\" : \"2017-02-28\", \"operation\" : \"Query\", \"query\" : {\n \"expression\" : \"#customer = :customer AND #order BETWEEN :order1 AND :order2\",\n \"expressionNames\" : {\n \"#customer\" : \"customer\", \"#order\" : \"order\"\n },\n \"expressionValues\" : {\n \":customer\" : $util.dynamodb.toDynamoDBJson($ctx.args.customer), \":order1\" : $util.dynamodb.toDynamoDBJson($ctx.args.order1), \":order2\" : $util.dynamodb.toDynamoDBJson($ctx.args.order2)\n }\n }}", "ResponseMappingTemplate": "$util.toJson($ctx.result.items)" }, "DependsOn": [ - "Apiorder88C17B87", + "ApiorderDsB50C8AAD", "ApiSchema510EECD7" ] }, - "ApipaymentServiceRoleBCB06044": { + "ApipaymentDsServiceRole0DAC58D6": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -617,7 +617,7 @@ } } }, - "ApipaymentServiceRoleDefaultPolicy93F9E362": { + "ApipaymentDsServiceRoleDefaultPolicy528E42B0": { "Type": "AWS::IAM::Policy", "Properties": { "PolicyDocument": { @@ -665,15 +665,15 @@ ], "Version": "2012-10-17" }, - "PolicyName": "ApipaymentServiceRoleDefaultPolicy93F9E362", + "PolicyName": "ApipaymentDsServiceRoleDefaultPolicy528E42B0", "Roles": [ { - "Ref": "ApipaymentServiceRoleBCB06044" + "Ref": "ApipaymentDsServiceRole0DAC58D6" } ] } }, - "ApipaymentA20A845D": { + "ApipaymentDs95C7AC36": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -682,7 +682,7 @@ "ApiId" ] }, - "Name": "payment", + "Name": "Payment", "Type": "AMAZON_DYNAMODB", "DynamoDBConfig": { "AwsRegion": { @@ -692,13 +692,13 @@ }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApipaymentServiceRoleBCB06044", + "ApipaymentDsServiceRole0DAC58D6", "Arn" ] } } }, - "ApipaymentQuerygetPaymentResolver561B2354": { + "ApipaymentDsQuerygetPaymentResolverD172BFC9": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -709,17 +709,17 @@ }, "FieldName": "getPayment", "TypeName": "Query", - "DataSourceName": "payment", + "DataSourceName": "Payment", "Kind": "UNIT", "RequestMappingTemplate": "{\"version\": \"2017-02-28\", \"operation\": \"GetItem\", \"key\": {\"id\": $util.dynamodb.toDynamoDBJson($ctx.args.id)}}", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApipaymentA20A845D", + "ApipaymentDs95C7AC36", "ApiSchema510EECD7" ] }, - "ApipaymentMutationsavePaymentResolver7C21AF6E": { + "ApipaymentDsMutationsavePaymentResolverE09FE5BB": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -730,17 +730,17 @@ }, "FieldName": "savePayment", "TypeName": "Mutation", - "DataSourceName": "payment", + "DataSourceName": "Payment", "Kind": "UNIT", "RequestMappingTemplate": "\n #set($input = $ctx.args.payment)\n \n {\n \"version\": \"2017-02-28\",\n \"operation\": \"PutItem\",\n \"key\" : {\n \"id\" : $util.dynamodb.toDynamoDBJson($util.autoId())\n },\n \"attributeValues\": $util.dynamodb.toMapValuesJson($input)\n }", "ResponseMappingTemplate": "$util.toJson($ctx.result)" }, "DependsOn": [ - "ApipaymentA20A845D", + "ApipaymentDs95C7AC36", "ApiSchema510EECD7" ] }, - "ApiHttpCDKDataSourceServiceRole992CDB9E": { + "ApidsServiceRoleADC7D124": { "Type": "AWS::IAM::Role", "Properties": { "AssumeRolePolicyDocument": { @@ -757,7 +757,7 @@ } } }, - "ApiHttpCDKDataSourceA919CDB4": { + "Apids0DB53FEA": { "Type": "AWS::AppSync::DataSource", "Properties": { "ApiId": { @@ -766,20 +766,20 @@ "ApiId" ] }, - "Name": "HttpCDKDataSource", + "Name": "http", "Type": "HTTP", "HttpConfig": { "Endpoint": "https://aws.amazon.com/" }, "ServiceRoleArn": { "Fn::GetAtt": [ - "ApiHttpCDKDataSourceServiceRole992CDB9E", + "ApidsServiceRoleADC7D124", "Arn" ] } } }, - "ApiHttpCDKDataSourceMutationdoPostOnAwsResolverBDE25968": { + "ApidsMutationdoPostOnAwsResolver9583D8A3": { "Type": "AWS::AppSync::Resolver", "Properties": { "ApiId": { @@ -790,13 +790,13 @@ }, "FieldName": "doPostOnAws", "TypeName": "Mutation", - "DataSourceName": "HttpCDKDataSource", + "DataSourceName": "http", "Kind": "UNIT", "RequestMappingTemplate": "{\n \"version\": \"2018-05-29\",\n \"method\": \"POST\",\n # if full path is https://api.xxxxxxxxx.com/posts then resourcePath would be /posts\n \"resourcePath\": \"/path/123\",\n \"params\":{\n \"body\": $util.toJson($ctx.args),\n \"headers\":{\n \"Content-Type\": \"application/json\",\n \"Authorization\": \"$ctx.request.headers.Authorization\"\n }\n }\n }", "ResponseMappingTemplate": "\n ## Raise a GraphQL field error in case of a datasource invocation error\n #if($ctx.error)\n $util.error($ctx.error.message, $ctx.error.type)\n #end\n ## if the response status code is not 200, then return an error. Else return the body **\n #if($ctx.result.statusCode == 200)\n ## If response is 200, return the body.\n $ctx.result.body\n #else\n ## If response is not 200, append the response to error block.\n $utils.appendError($ctx.result.body, \"$ctx.result.statusCode\")\n #end\n " }, "DependsOn": [ - "ApiHttpCDKDataSourceA919CDB4", + "Apids0DB53FEA", "ApiSchema510EECD7" ] }, diff --git a/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts b/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts index da63f1132d4ee..add2e19cb8b68 100644 --- a/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts +++ b/packages/@aws-cdk/aws-appsync/test/integ.graphql.ts @@ -54,7 +54,7 @@ const api = new GraphQLApi(stack, 'Api', { }, }); -const noneDS = api.addNoneDataSource(); +const noneDS = api.addNoneDataSource('none', {name: 'None'}); noneDS.createResolver({ typeName: 'Query', @@ -99,9 +99,9 @@ new Table(stack, 'PaymentTable', { const paymentTable = Table.fromTableName(stack, 'ImportedPaymentTable', 'PaymentTable'); -const customerDS = api.addDynamoDbDataSource(customerTable, {name: 'customer'}); -const orderDS = api.addDynamoDbDataSource(orderTable, {name: 'order'}); -const paymentDS = api.addDynamoDbDataSource(paymentTable, {name: 'payment'}); +const customerDS = api.addDynamoDbDataSource('customerDs', customerTable, {name: 'Customer'}); +const orderDS = api.addDynamoDbDataSource('orderDs', orderTable, {name: 'Order'}); +const paymentDS = api.addDynamoDbDataSource('paymentDs', paymentTable, {name: 'Payment'}); customerDS.createResolver({ typeName: 'Query', @@ -189,7 +189,7 @@ paymentDS.createResolver({ responseMappingTemplate: MappingTemplate.dynamoDbResultItem(), }); -const httpDS = api.addHttpDataSource('https://aws.amazon.com/'); +const httpDS = api.addHttpDataSource('ds', 'https://aws.amazon.com/', {name: 'http'}); httpDS.createResolver({ typeName: 'Mutation', From ecc91452c31cc55114438f6936baf2b622faa434 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Wed, 5 Aug 2020 12:07:58 -0700 Subject: [PATCH 14/17] update Readme --- packages/@aws-cdk/aws-appsync/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/README.md b/packages/@aws-cdk/aws-appsync/README.md index 575025d8a043e..22c168618713a 100644 --- a/packages/@aws-cdk/aws-appsync/README.md +++ b/packages/@aws-cdk/aws-appsync/README.md @@ -63,7 +63,7 @@ const demoTable = new db.Table(stack, 'DemoTable', { }, }); -const demoDS = api.addDynamoDbDataSource('demoDataSource', 'Table for Demos"', demoTable); +const demoDS = api.addDynamoDbDataSource('demoDataSource', demoTable); // Resolver for the Query "getDemos" that scans the DyanmoDb table and returns the entire list. demoDS.createResolver({ @@ -93,7 +93,7 @@ const importedApi = appsync.GraphQLApi.fromGraphQLApiAttributes(stack, 'IApi', { graphqlApiId: api.apiId, graphqlArn: api.arn, }); -importedApi.addDynamoDbDataSource('TableDataSource', 'Table', table); +importedApi.addDynamoDbDataSource('TableDataSource', table); ``` If you don't specify `graphqlArn` in `fromXxxAttributes`, CDK will autogenerate From 4976bab72cbd8e531806395d1a2d5f1be52287c8 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Wed, 5 Aug 2020 12:11:21 -0700 Subject: [PATCH 15/17] update doc strings for addXxxDataSource --- .../@aws-cdk/aws-appsync/lib/graphqlapi-base.ts | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index e912f79b1bf2d..fc8a69f48a6df 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -111,11 +111,12 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { public abstract readonly arn: string; /** - * add a new none data source to this API. Useful for pipeline resolvers + * add a new dummy data source to this API. Useful for pipeline resolvers * and for backend changes that don't require a data source. * + * @param id The data source's id * @param options The optional configuration for this data source - * @default name - 'NoneCDKDataSource' + * @default name - the id * description - No description */ public addNoneDataSource(id: string, options?: DataSourceOptions): NoneDataSource { @@ -129,9 +130,10 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new DynamoDB data source to this API * + * @param id The data source's id * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - 'DynamoDbCDKDataSource' + * @default name - the id * description - No description */ public addDynamoDbDataSource(id: string, table: ITable, options?: DataSourceOptions): DynamoDbDataSource { @@ -146,9 +148,10 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new http data source to this API * + * @param id The data source's id * @param endpoint The http endpoint * @param options The optional configuration for this data source - * @default name - 'HttpCDKDataSource' + * @default name - 'the id * description - No description */ public addHttpDataSource(id: string, endpoint: string, options?: DataSourceOptions): HttpDataSource { @@ -163,9 +166,10 @@ export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { /** * add a new Lambda data source to this API * + * @param id The data source's id * @param lambdaFunction The Lambda function to call to interact with this data source * @param options The optional configuration for this data source - * @default name - 'LambdaCDKDataSource' + * @default name - the id * description - No description */ public addLambdaDataSource(id: string, lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource { From 5243ef0732f41f61c813ac9c02d82d0f0e682ed0 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Wed, 5 Aug 2020 15:24:37 -0700 Subject: [PATCH 16/17] snakecasing --- packages/@aws-cdk/aws-appsync/lib/data-source.ts | 6 +++--- packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts | 4 ++-- packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts | 10 +++++----- packages/@aws-cdk/aws-appsync/lib/resolver.ts | 4 ++-- 4 files changed, 12 insertions(+), 12 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/data-source.ts b/packages/@aws-cdk/aws-appsync/lib/data-source.ts index 329ca8685e008..04c617b12e5d0 100644 --- a/packages/@aws-cdk/aws-appsync/lib/data-source.ts +++ b/packages/@aws-cdk/aws-appsync/lib/data-source.ts @@ -3,7 +3,7 @@ import { IGrantable, IPrincipal, IRole, Role, ServicePrincipal } from '@aws-cdk/ import { IFunction } from '@aws-cdk/aws-lambda'; import { Construct, IResolvable } from '@aws-cdk/core'; import { CfnDataSource } from './appsync.generated'; -import { IGraphQLApi } from './graphqlapi-base'; +import { IGraphqlApi } from './graphqlapi-base'; import { BaseResolverProps, Resolver } from './resolver'; /** @@ -13,7 +13,7 @@ export interface BaseDataSourceProps { /** * The API to attach this data source to */ - readonly api: IGraphQLApi; + readonly api: IGraphqlApi; /** * The name of the data source * @@ -93,7 +93,7 @@ export abstract class BaseDataSource extends Construct { */ public readonly ds: CfnDataSource; - protected api: IGraphQLApi; + protected api: IGraphqlApi; protected serviceRole?: IRole; constructor(scope: Construct, id: string, props: BackedDataSourceProps, extended: ExtendedDataSourceProps) { diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index fc8a69f48a6df..798e34f11a770 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -25,7 +25,7 @@ export interface DataSourceOptions { /** * Interface for GraphQL */ -export interface IGraphQLApi extends IResource { +export interface IGraphqlApi extends IResource { /** * an unique AWS AppSync GraphQL API identifier @@ -97,7 +97,7 @@ export interface IGraphQLApi extends IResource { /** * Base Class for GraphQL API */ -export abstract class GraphQLApiBase extends Resource implements IGraphQLApi { +export abstract class GraphqlApiBase extends Resource implements IGraphqlApi { /** * an unique AWS AppSync GraphQL API identifier diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts index 621c10bd18eb3..b861d5e4b05d0 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi.ts @@ -3,7 +3,7 @@ import { IUserPool } from '@aws-cdk/aws-cognito'; import { ManagedPolicy, Role, ServicePrincipal, Grant, IGrantable } from '@aws-cdk/aws-iam'; import { CfnResource, Construct, Duration, IResolvable, Stack } from '@aws-cdk/core'; import { CfnApiKey, CfnGraphQLApi, CfnGraphQLSchema } from './appsync.generated'; -import { IGraphQLApi, GraphQLApiBase } from './graphqlapi-base'; +import { IGraphqlApi, GraphqlApiBase } from './graphqlapi-base'; /** * enum with all possible values for AppSync authorization type @@ -318,7 +318,7 @@ export class IamResource { /** * Attributes for GraphQL imports */ -export interface GraphQLApiAttributes { +export interface GraphqlApiAttributes { /** * an unique AWS AppSync GraphQL API identifier * i.e. 'lxz775lwdrgcndgz3nurvac7oa' @@ -337,7 +337,7 @@ export interface GraphQLApiAttributes { * * @resource AWS::AppSync::GraphQLApi */ -export class GraphQLApi extends GraphQLApiBase { +export class GraphQLApi extends GraphqlApiBase { /** * Import a GraphQL API through this function * @@ -345,12 +345,12 @@ export class GraphQLApi extends GraphQLApiBase { * @param id id * @param attrs GraphQL API Attributes of an API */ - public static fromGraphqlApiAttributes(scope: Construct, id: string, attrs: GraphQLApiAttributes): IGraphQLApi { + public static fromGraphqlApiAttributes(scope: Construct, id: string, attrs: GraphqlApiAttributes): IGraphqlApi { const arn = attrs.graphqlApiArn ?? Stack.of(scope).formatArn({ service: 'appsync', resource: `apis/${attrs.graphqlApiId}`, }); - class Import extends GraphQLApiBase { + class Import extends GraphqlApiBase { public readonly apiId = attrs.graphqlApiId; public readonly arn = arn; constructor (s: Construct, i: string){ diff --git a/packages/@aws-cdk/aws-appsync/lib/resolver.ts b/packages/@aws-cdk/aws-appsync/lib/resolver.ts index efe8fc5423dc9..205155cc791c8 100644 --- a/packages/@aws-cdk/aws-appsync/lib/resolver.ts +++ b/packages/@aws-cdk/aws-appsync/lib/resolver.ts @@ -1,7 +1,7 @@ import { Construct } from '@aws-cdk/core'; import { CfnResolver } from './appsync.generated'; import { BaseDataSource } from './data-source'; -import { IGraphQLApi } from './graphqlapi-base'; +import { IGraphqlApi } from './graphqlapi-base'; import { MappingTemplate } from './mapping-template'; /** @@ -44,7 +44,7 @@ export interface ResolverProps extends BaseResolverProps { /** * The API this resolver is attached to */ - readonly api: IGraphQLApi; + readonly api: IGraphqlApi; /** * The data source this resolver is using * From a668e1304de6fb6eaeff27f8c15faddb7f616789 Mon Sep 17 00:00:00 2001 From: Bryan Pan Date: Thu, 6 Aug 2020 10:37:36 -0700 Subject: [PATCH 17/17] address suggestions --- .../aws-appsync/lib/graphqlapi-base.ts | 18 +----------------- .../aws-appsync/test/appsync-dynamodb.test.ts | 8 ++++---- .../aws-appsync/test/appsync-http.test.ts | 8 ++++---- .../aws-appsync/test/appsync-lambda.test.ts | 8 ++++---- .../aws-appsync/test/appsync-none.test.ts | 10 +++++----- 5 files changed, 18 insertions(+), 34 deletions(-) diff --git a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts index 798e34f11a770..2f357c142db91 100644 --- a/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts +++ b/packages/@aws-cdk/aws-appsync/lib/graphqlapi-base.ts @@ -10,7 +10,7 @@ export interface DataSourceOptions { /** * The name of the data source, overrides the id given by cdk * - * @default - the id provisioned + * @default - generated by cdk given the id */ readonly name?: string; @@ -48,8 +48,6 @@ export interface IGraphqlApi extends IResource { * * @param id The data source's id * @param options The optional configuration for this data source - * @default name - the id - * description - No description */ addNoneDataSource(id: string, options?: DataSourceOptions): NoneDataSource; @@ -59,8 +57,6 @@ export interface IGraphqlApi extends IResource { * @param id The data source's id * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - the id - * description - No description */ addDynamoDbDataSource(id: string, table: ITable, options?: DataSourceOptions): DynamoDbDataSource; @@ -70,8 +66,6 @@ export interface IGraphqlApi extends IResource { * @param id The data source's id * @param endpoint The http endpoint * @param options The optional configuration for this data source - * @default name - 'the id - * description - No description */ addHttpDataSource(id: string, endpoint: string, options?: DataSourceOptions): HttpDataSource; @@ -81,8 +75,6 @@ export interface IGraphqlApi extends IResource { * @param id The data source's id * @param lambdaFunction The Lambda function to call to interact with this data source * @param options The optional configuration for this data source - * @default name - the id - * description - No description */ addLambdaDataSource(id: string, lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource; @@ -116,8 +108,6 @@ export abstract class GraphqlApiBase extends Resource implements IGraphqlApi { * * @param id The data source's id * @param options The optional configuration for this data source - * @default name - the id - * description - No description */ public addNoneDataSource(id: string, options?: DataSourceOptions): NoneDataSource { return new NoneDataSource(this, id, { @@ -133,8 +123,6 @@ export abstract class GraphqlApiBase extends Resource implements IGraphqlApi { * @param id The data source's id * @param table The DynamoDB table backing this data source * @param options The optional configuration for this data source - * @default name - the id - * description - No description */ public addDynamoDbDataSource(id: string, table: ITable, options?: DataSourceOptions): DynamoDbDataSource { return new DynamoDbDataSource(this, id, { @@ -151,8 +139,6 @@ export abstract class GraphqlApiBase extends Resource implements IGraphqlApi { * @param id The data source's id * @param endpoint The http endpoint * @param options The optional configuration for this data source - * @default name - 'the id - * description - No description */ public addHttpDataSource(id: string, endpoint: string, options?: DataSourceOptions): HttpDataSource { return new HttpDataSource(this, id, { @@ -169,8 +155,6 @@ export abstract class GraphqlApiBase extends Resource implements IGraphqlApi { * @param id The data source's id * @param lambdaFunction The Lambda function to call to interact with this data source * @param options The optional configuration for this data source - * @default name - the id - * description - No description */ public addLambdaDataSource(id: string, lambdaFunction: IFunction, options?: DataSourceOptions): LambdaDataSource { return new LambdaDataSource(this, id, { diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts index 0b7e29de2b295..a43e13afa9528 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-dynamodb.test.ts @@ -36,7 +36,7 @@ describe('DynamoDb Data Source configuration', () => { // WHEN api.addDynamoDbDataSource('ds', table); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AMAZON_DYNAMODB', Name: 'ds', @@ -49,7 +49,7 @@ describe('DynamoDb Data Source configuration', () => { name: 'custom', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AMAZON_DYNAMODB', Name: 'custom', @@ -63,7 +63,7 @@ describe('DynamoDb Data Source configuration', () => { description: 'custom description', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AMAZON_DYNAMODB', Name: 'custom', @@ -78,7 +78,7 @@ describe('DynamoDb Data Source configuration', () => { api.addDynamoDbDataSource('ds', table); }; - // EXPECT + // THEN expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts index c8535ba83ff9a..25961b87cb8d2 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-http.test.ts @@ -23,7 +23,7 @@ describe('Http Data Source configuration', () => { // WHEN api.addHttpDataSource('ds', endpoint); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'HTTP', Name: 'ds', @@ -36,7 +36,7 @@ describe('Http Data Source configuration', () => { name: 'custom', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'HTTP', Name: 'custom', @@ -50,7 +50,7 @@ describe('Http Data Source configuration', () => { description: 'custom description', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'HTTP', Name: 'custom', @@ -65,7 +65,7 @@ describe('Http Data Source configuration', () => { api.addHttpDataSource('ds', endpoint); }; - // EXPECT + // THEN expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts index eb41a5aa67a53..b178fee2282cf 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-lambda.test.ts @@ -31,7 +31,7 @@ describe('Lambda Data Source configuration', () => { // WHEN api.addLambdaDataSource('ds', func); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AWS_LAMBDA', Name: 'ds', @@ -44,7 +44,7 @@ describe('Lambda Data Source configuration', () => { name: 'custom', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AWS_LAMBDA', Name: 'custom', @@ -58,7 +58,7 @@ describe('Lambda Data Source configuration', () => { description: 'custom description', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'AWS_LAMBDA', Name: 'custom', @@ -73,7 +73,7 @@ describe('Lambda Data Source configuration', () => { api.addLambdaDataSource('ds', func); }; - // EXPECT + // THEN expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); }); diff --git a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts index b523200ffbe46..13ab095ed0fee 100644 --- a/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts +++ b/packages/@aws-cdk/aws-appsync/test/appsync-none.test.ts @@ -21,7 +21,7 @@ describe('None Data Source configuration', () => { // WHEN api.addNoneDataSource('ds'); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'NONE', Name: 'ds', @@ -34,7 +34,7 @@ describe('None Data Source configuration', () => { name: 'custom', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'NONE', Name: 'custom', @@ -48,7 +48,7 @@ describe('None Data Source configuration', () => { description: 'custom description', }); - // EXPECT + // THEN expect(stack).toHaveResourceLike('AWS::AppSync::DataSource', { Type: 'NONE', Name: 'custom', @@ -63,7 +63,7 @@ describe('None Data Source configuration', () => { api.addNoneDataSource('ds'); }; - // EXPECT + // THEN expect(when).toThrow("There is already a Construct with name 'ds' in GraphQLApi [baseApi]"); }); @@ -74,7 +74,7 @@ describe('None Data Source configuration', () => { api.addNoneDataSource('ds2', { name: 'custom' }); }; - // EXPECT + // THEN expect(when).not.toThrowError(); }); });