AWSTemplateFormatVersion: 2010-09-09 Description: > Amazon Connect Voice ID demo Mappings: FunctionMap: Configuration: S3Bucket: "amazon-connect-blog-assets" S3Key: "2021/voice-id/" Parameters: CFS3BucketForWebSite: Default: "voiceid-website" Type: String AllowedPattern: '(?=^.{3,63}$)(?!^(\d+\.)+\d+$)(^(([a-z0-9]|[a-z0-9][a-z0-9\-]*[a-z0-9])\.)*([a-z0-9]|[a-z0-9][a-z0-9\-]*[a-z0-9])$)' ConstraintDescription: 'Invalid S3 Bucket name' Description: Enter the (globally unique) name you would like to use for the Amazon S3 bucket where we will store the website assets. This template will fail to deploy if the bucket name you chose is currently in use. InstanceIdParam: Type: String AllowedPattern: '\w{8}-\w{4}-\w{4}-\w{4}-\w{12}' ConstraintDescription: "Invalid Amazon Connect instance Id" Description: Amazon Connect Instance ID (Ensure you it is entered accurately in the format xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx ). InstanceNameParam: Type: String ConstraintDescription: "Invalid Amazon Connect instance alias" Description: Amazon Connect Instance Alias (Ensure you it is entered accurately as configured under Amazon Connect Service ). BasicQueueArnParam: Type: String ConstraintDescription: "Invalid Amazon Connect Queue ARN" Description: Basic Queue ARN. Metadata: 'AWS::CloudFormation::Interface': ParameterGroups: - Label: default: Amazon S3 Configuration Parameters: - CFS3BucketForWebSite - Label: default: Amazon Connect Configuration Parameters: - InstanceIdParam - InstanceNameParam - BasicQueueArnParam ParameterLabels: CFS3BucketForWebSite: default: S3 Bucket For WebSite InstanceIdParam: default: Instance ID InstanceNameParam: default: Instance Name BasicQueueArnParam: default: Basic Queue ARN Outputs: CloudfrontEndpoint: Description: Endpoint for Cloudfront distribution Value: !Join - '' - - 'https://' - !GetAtt [CFCloudFrontDistribution, DomainName] - '/voiceid.html' createContactFlow: Description: > Lambda function triggered by CFT to create sample Contact Flow. Value: !Ref CreateContactFlow createContactFlowFlowARN: Description: ARN for the CreateContactFlowFunction Value: !GetAtt CreateContactFlow.Arn Resources: createWebSiteS3Bucket: Type: 'AWS::S3::Bucket' Properties: BucketName: !Ref CFS3BucketForWebSite PublicAccessBlockConfiguration: BlockPublicAcls: True BlockPublicPolicy: True IgnorePublicAcls: True RestrictPublicBuckets: True WebsiteConfiguration: IndexDocument: voiceid.html ErrorDocument: error.html BucketEncryption: ServerSideEncryptionConfiguration: - ServerSideEncryptionByDefault: SSEAlgorithm: 'AES256' VersioningConfiguration: Status: Enabled CFS3BucketPolicy: Type: AWS::S3::BucketPolicy DependsOn: - CFCloudFrontDistributionAccessIdentity Properties: Bucket: !Ref createWebSiteS3Bucket PolicyDocument: Statement: - Action: - "s3:GetObject" Effect: "Allow" Principal: CanonicalUser: Fn::GetAtt: [ CFCloudFrontDistributionAccessIdentity , S3CanonicalUserId ] Resource: !Sub ${createWebSiteS3Bucket.Arn}/voiceidsite/* CFCloudFrontDistributionAccessIdentity: Type: AWS::CloudFront::CloudFrontOriginAccessIdentity Properties: CloudFrontOriginAccessIdentityConfig: Comment: 'CloudFront endpoint for Voice ID S3' CFCloudFrontDistribution: Type: AWS::CloudFront::Distribution Properties: DistributionConfig: Origins: - DomainName: !Join - '' - - !Ref CFS3BucketForWebSite - .s3.amazonaws.com Id: !Ref CFS3BucketForWebSite OriginPath: '/voiceidsite' S3OriginConfig: OriginAccessIdentity: !Join - '' - - 'origin-access-identity/cloudfront/' - !Ref CFCloudFrontDistributionAccessIdentity Enabled: 'true' Logging: Bucket: !GetAtt createWebSiteS3Bucket.DomainName Prefix: 'logs/' IncludeCookies: 'true' Comment: CloudFront for Voice ID DefaultRootObject: voiceid.html DefaultCacheBehavior: AllowedMethods: - DELETE - GET - HEAD - OPTIONS - PATCH - POST - PUT TargetOriginId: !Ref CFS3BucketForWebSite ForwardedValues: QueryString: true Cookies: Forward: all ViewerProtocolPolicy: redirect-to-https Restrictions: GeoRestriction: RestrictionType: none CFWebsiteCreatorRole: Type: "AWS::IAM::Role" Properties: AssumeRolePolicyDocument: Version: "2012-10-17" Statement: - Effect: "Allow" Principal: Service: - "lambda.amazonaws.com" Action: - "sts:AssumeRole" Path: "/" Policies: - PolicyName: !Sub ${AWS::StackName}-voice-id-creator-policy PolicyDocument: Version: "2012-10-17" Statement: - Effect: "Allow" Action: - 'logs:CreateLogGroup' - 'logs:CreateLogStream' - 'logs:PutLogEvents' Resource: - !Sub "arn:${AWS::Partition}:logs:${AWS::Region}:${AWS::AccountId}:log-group:/aws/lambda/*" - Effect: "Allow" Action: - "s3:PutObject" - "s3:GetObject" - "s3:PutObjectAcl" Resource: - !Join - '' - - 'arn:' - !Ref 'AWS::Partition' - ':s3:::' - !Ref CFS3BucketForWebSite - '/*' - Effect: "Allow" Action: - "s3:PutBucketPublicAccessBlock" Resource: - !Join - '' - - 'arn:' - !Ref 'AWS::Partition' - ':s3:::' - !Ref CFS3BucketForWebSite - Effect: "Allow" Action: - "s3:GetObject" Resource: - !Join - '' - - 'arn:' - !Ref 'AWS::Partition' - ':s3:::' - 'amazon-connect-blogs2' - '/*' webSiteCreator: Type: "AWS::Lambda::Function" Properties: Description: > AWS Lambda Function that will create the website and upload it to the S3 bucket Handler: "index.handler" Role: !GetAtt CFWebsiteCreatorRole.Arn Runtime: "nodejs12.x" MemorySize: 256 Timeout: 120 Code: ./website-creator/ invokeWebSiteCreator: Type: Custom::CreateWebSite DependsOn: createWebSiteS3Bucket Properties: ServiceToken: !GetAtt webSiteCreator.Arn customAction: configureWebsite Region: !Ref AWS::Region destS3Bucket: !Ref CFS3BucketForWebSite destS3KeyPrefix: voiceidsite connectInstanceName: !Ref InstanceNameParam CreateContactFlowRole: Type: "AWS::IAM::Role" Properties: AssumeRolePolicyDocument: Version: "2012-10-17" Statement: - Effect: "Allow" Principal: Service: - "lambda.amazonaws.com" Action: - "sts:AssumeRole" Path: "/" Policies: - PolicyName: !Sub ${AWS::StackName}-create-contact-flow-policy PolicyDocument: Version: "2012-10-17" Statement: - Effect: "Allow" Action: - 'logs:CreateLogGroup' - 'logs:CreateLogStream' - 'logs:PutLogEvents' Resource: - !Sub "arn:${AWS::Partition}:logs:${AWS::Region}:${AWS::AccountId}:log-group:/aws/lambda/*" - Effect: "Allow" Action: - 'connect:*' Resource: - "*" CreateContactFlow: Type: "AWS::Lambda::Function" Properties: Description: Lambda function triggered by CFT to create Sample Contact Flow for VoiceID. Runtime: nodejs12.x Role: !GetAtt CreateContactFlowRole.Arn Handler: index.handler MemorySize: 128 Timeout: 30 Environment: Variables: CONNECT_INSTANCE_ID: !Ref InstanceIdParam Code: ./contact-flow-creator/ CreateContactFlowLambdaRun: Type: Custom::CreateContactFlowLambdaRun Properties: ServiceToken: !GetAtt CreateContactFlow.Arn BASIC_QUEUE_ARN: !Ref BasicQueueArnParam CONTACT_FLOW_NAME: !Sub ${AWS::StackName}-VoiceID-Contact-Flow