// Jest Snapshot v1, https://goo.gl/fbAQLP exports[`VideoOnDemand Stack Test 1`] = ` { Conditions: { EnableMediaPackageCondition: { Fn::Equals: [ { Ref: EnableMediaPackage, }, Yes, ], }, EnableSnsCondition: { Fn::Equals: [ { Ref: EnableSns, }, Yes, ], }, EnableSqsCondition: { Fn::Equals: [ { Ref: EnableSqs, }, Yes, ], }, FrameCaptureCondition: { Fn::Equals: [ { Ref: FrameCapture, }, Yes, ], }, }, Description: (SO0021) - Video on Demand on AWS workflow with AWS Step Functions, MediaConvert, MediaPackage, S3, CloudFront and DynamoDB. Version %%VERSION%%, Metadata: { AWS::CloudFormation::Interface: { ParameterGroups: [ { Label: { default: Workflow, }, Parameters: [ AdminEmail, WorkflowTrigger, Glacier, EnableSns, EnableSqs, ], }, { Label: { default: AWS Elemental MediaConvert, }, Parameters: [ FrameCapture, AcceleratedTranscoding, ], }, { Label: { default: AWS Elemental MediaPackage, }, Parameters: [ EnableMediaPackage, ], }, ], ParameterLabels: { AcceleratedTranscoding: { default: Accelerated Transcoding, }, AdminEmail: { default: Notification email address, }, EnableMediaPackage: { default: Enable MediaPackage, }, EnableSns: { default: Enable SNS Notifications, }, EnableSqs: { default: Enable SQS Messaging, }, FrameCapture: { default: Enable Frame Capture, }, Glacier: { default: Archive source content, }, WorkflowTrigger: { default: Workflow trigger, }, }, }, }, Outputs: { AnonymousMetricUUID: { Description: AnonymousMetric UUID, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :UUID, ], ], }, }, Value: { Fn::GetAtt: [ UUID, UUID, ], }, }, AppRegistryConsole: { Description: AppRegistry, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -AppRegistry, ], ], }, }, Value: { Fn::Join: [ , [ https://, { Ref: AWS::Region, }, .console.aws.amazon.com/servicecatalog/home?#applications/, { Fn::GetAtt: [ AppRegistryApp5349BE86, Id, ], }, ], ], }, }, CloudFrontDomainName: { Description: CloudFront Domain Name, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :CloudFront, ], ], }, }, Value: { Fn::GetAtt: [ CloudFrontToS3CloudFrontDistribution241D9866, DomainName, ], }, }, DestinationBucketName: { Description: Destination Bucket, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :Destination, ], ], }, }, Value: { Ref: Destination920A3C57, }, }, DynamoDBTableName: { Description: DynamoDB Table, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :DynamoDBTable, ], ], }, }, Value: { Ref: DynamoDBTable59784FC0, }, }, SnsTopicName: { Description: SNS Topic, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :SnsTopic, ], ], }, }, Value: { Fn::GetAtt: [ SnsTopic2C1570A4, TopicName, ], }, }, SourceBucketName: { Description: Source Bucket, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :Source, ], ], }, }, Value: { Ref: Source71E471F1, }, }, SqsArn: { Description: SQS Queue ARN, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :SqsQueueArn, ], ], }, }, Value: { Fn::GetAtt: [ SqsQueue13597403, Arn, ], }, }, SqsUrl: { Description: SQS Queue URL, Export: { Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, :SqsQueue, ], ], }, }, Value: { Ref: SqsQueue13597403, }, }, }, Parameters: { AcceleratedTranscoding: { AllowedValues: [ ENABLED, DISABLED, PREFERRED, ], Default: PREFERRED, Description: Enable accelerated transcoding in AWS Elemental MediaConvert. PREFERRED will only use acceleration if the input files is supported. ENABLED accleration is applied to all files (this will fail for unsupported file types) see MediaConvert Documentation for more detail https://docs.aws.amazon.com/mediaconvert/latest/ug/accelerated-transcoding.html, Type: String, }, AdminEmail: { AllowedPattern: ^[_A-Za-z0-9-\\+]+(\\.[_A-Za-z0-9-]+)*@[A-Za-z0-9-]+(\\.[A-Za-z0-9]+)*(\\.[A-Za-z]{2,})$, Description: Email address for SNS notifications (subscribed users will receive ingest, publishing, and error notifications), Type: String, }, EnableMediaPackage: { AllowedValues: [ Yes, No, ], Default: No, Description: If enabled, MediaPackage VOD will be included in the workflow, Type: String, }, EnableSns: { AllowedValues: [ Yes, No, ], Default: Yes, Description: Enable Ingest and Publish email notifications, error messages are not affected by this parameter., Type: String, }, EnableSqs: { AllowedValues: [ Yes, No, ], Default: Yes, Description: Publish the workflow results to an SQS queue to injest upstream, Type: String, }, FrameCapture: { AllowedValues: [ Yes, No, ], Default: No, Description: If enabled, frame capture is added to the job submitted to MediaConvert, Type: String, }, Glacier: { AllowedValues: [ DISABLED, GLACIER, DEEP_ARCHIVE, ], Default: DISABLED, Description: If enabled, source assets will be tagged for archiving to Glacier or Glacier Deep Archive once the workflow is complete, Type: String, }, WorkflowTrigger: { AllowedValues: [ VideoFile, MetadataFile, ], Default: VideoFile, Description: How the workflow will be triggered (source video upload to S3 or source metadata file upload), Type: String, }, }, Resources: { AnonymousMetric: { DeletionPolicy: Delete, Properties: { EnableMediaPackage: { Ref: EnableMediaPackage, }, FrameCapture: { Ref: FrameCapture, }, Glacier: { Ref: Glacier, }, Resource: AnonymousMetric, SendAnonymizedMetric: { Fn::FindInMap: [ AnonymizedData, SendAnonymizedData, Data, ], }, ServiceToken: { Fn::GetAtt: [ CustomResource8CDCD7A7, Arn, ], }, SolutionId: SO0021, Transcoder: MediaConvert, UUID: { Fn::GetAtt: [ UUID, UUID, ], }, Version: %%VERSION%%, WorkflowTrigger: { Ref: WorkflowTrigger, }, }, Type: AWS::CloudFormation::CustomResource, UpdateReplacePolicy: Delete, }, AppRegistryApp5349BE86: { Properties: { Description: Service Catalog application to track and manage all your resources. The SolutionId is SO0021 and SolutionVersion is %%VERSION%%., Name: { Fn::Join: [ , [ video-on-demand-on-aws-, { Ref: AWS::Region, }, -, { Ref: AWS::AccountId, }, -, { Ref: AWS::StackName, }, ], ], }, Tags: { SolutionId: SO0021, Solutions:ApplicationType: AWS-Solutions, Solutions:SolutionID: SO0021, Solutions:SolutionName: Video on Demand on AWS, Solutions:SolutionVersion: %%VERSION%%, }, }, Type: AWS::ServiceCatalogAppRegistry::Application, }, AppRegistryAssociation: { Properties: { Application: { Fn::GetAtt: [ AppRegistryApp5349BE86, Id, ], }, Resource: { Ref: AWS::StackId, }, ResourceType: CFN_STACK, }, Type: AWS::ServiceCatalogAppRegistry::ResourceAssociation, }, AppRegistryAttributeGroupId7C2D526E: { Properties: { Attributes: { applicationType: AWS-Solutions, solutionID: SO0021, solutionName: Video on Demand on AWS, version: %%VERSION%%, }, Description: Attribute group for solution information, Name: { Fn::Join: [ , [ A30-, { Ref: AWS::Region, }, -, { Ref: AWS::StackName, }, ], ], }, Tags: { SolutionId: SO0021, }, }, Type: AWS::ServiceCatalogAppRegistry::AttributeGroup, }, AppRegistryAttributeGroupIdApplicationAttributeGroupAssociatione9644211d9ed28C08BBE: { Properties: { Application: { Fn::GetAtt: [ AppRegistryApp5349BE86, Id, ], }, AttributeGroup: { Fn::GetAtt: [ AppRegistryAttributeGroupId7C2D526E, Id, ], }, }, Type: AWS::ServiceCatalogAppRegistry::AttributeGroupAssociation, }, ArchiveSourceLambda320F09D9: { DependsOn: [ ArchiveSourcePolicy1D98A4F5, ArchiveSourceRole49DA53ED, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Updates tags on source files to enable Glacier, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -archive-source, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ ArchiveSourceRole49DA53ED, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, ArchiveSourcePolicy1D98A4F5: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: s3:PutObjectTagging, Effect: Allow, Resource: { Fn::Join: [ , [ { Fn::GetAtt: [ Source71E471F1, Arn, ], }, /*, ], ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -archive-source-role, ], ], }, Roles: [ { Ref: ArchiveSourceRole49DA53ED, }, ], }, Type: AWS::IAM::Policy, }, ArchiveSourceRole49DA53ED: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, CachePolicy26D8A535: { Properties: { CachePolicyConfig: { DefaultTTL: 86400, MaxTTL: 86400, MinTTL: 0, Name: { Fn::Join: [ , [ cp-, { Ref: AWS::Region, }, -, { Ref: AWS::StackName, }, ], ], }, ParametersInCacheKeyAndForwardedToOrigin: { CookiesConfig: { CookieBehavior: none, }, EnableAcceptEncodingBrotli: false, EnableAcceptEncodingGzip: false, HeadersConfig: { HeaderBehavior: whitelist, Headers: [ Origin, Access-Control-Request-Method, Access-Control-Request-Headers, ], }, QueryStringsConfig: { QueryStringBehavior: none, }, }, }, }, Type: AWS::CloudFront::CachePolicy, }, CloudFrontToS3CloudFrontDistribution241D9866: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-CFR1, reason: Use case does not warrant CloudFront Geo restriction, }, { id: AwsSolutions-CFR2, reason: Use case does not warrant CloudFront integration with AWS WAF, }, { id: AwsSolutions-CFR4, reason: CloudFront automatically sets the security policy to TLSv1 when the distribution uses the CloudFront domain name, }, ], }, cfn_nag: { rules_to_suppress: [ { id: W70, reason: Since the distribution uses the CloudFront domain name, CloudFront automatically sets the security policy to TLSv1 regardless of the value of MinimumProtocolVersion, }, ], }, }, Properties: { DistributionConfig: { DefaultCacheBehavior: { AllowedMethods: [ GET, HEAD, ], CachePolicyId: { Ref: CachePolicy26D8A535, }, Compress: true, TargetOriginId: VideoOnDemandCloudFrontToS3CloudFrontDistributionOrigin1CC6EEFFD, ViewerProtocolPolicy: redirect-to-https, }, DefaultRootObject: index.html, Enabled: true, HttpVersion: http2, IPV6Enabled: true, Logging: { Bucket: { Fn::GetAtt: [ Logs6819BB44, RegionalDomainName, ], }, Prefix: cloudfront-logs/, }, Origins: [ { DomainName: { Fn::GetAtt: [ Destination920A3C57, RegionalDomainName, ], }, Id: VideoOnDemandCloudFrontToS3CloudFrontDistributionOrigin1CC6EEFFD, S3OriginConfig: { OriginAccessIdentity: { Fn::Join: [ , [ origin-access-identity/cloudfront/, { Ref: CloudFrontToS3CloudFrontDistributionOrigin1S3OriginB0637B8F, }, ], ], }, }, }, ], PriceClass: PriceClass_100, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::CloudFront::Distribution, }, CloudFrontToS3CloudFrontDistributionOrigin1S3OriginB0637B8F: { Properties: { CloudFrontOriginAccessIdentityConfig: { Comment: Identity for VideoOnDemandCloudFrontToS3CloudFrontDistributionOrigin1CC6EEFFD, }, }, Type: AWS::CloudFront::CloudFrontOriginAccessIdentity, }, CustomResource8CDCD7A7: { DependsOn: [ CustomResourcePolicy79526710, CustomResourceRoleAB1EF463, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W58, reason: Invalid warning: function has access to cloudwatch, }, { id: W89, reason: This CustomResource does not need to be deployed inside a VPC, }, { id: W92, reason: This CustomResource does not need to define ReservedConcurrentExecutions to reserve simultaneous executions, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Used to deploy resources not supported by CloudFormation, Environment: { Variables: { SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -custom-resource, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ CustomResourceRoleAB1EF463, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 30, }, Type: AWS::Lambda::Function, }, CustomResourcePolicy79526710: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: Resource ARNs are not generated at the time of policy creation, }, ], }, cfn_nag: { rules_to_suppress: [ { id: W12, reason: * is required to create CloudWatch logs and interact with MediaConvert / MediaPackage actions that do not support resource level permissions, }, { id: W76, reason: High complexity due to number of policy statements needed for creating all custom resources, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, { Action: [ s3:PutBucketNotification, s3:PutObject, s3:PutObjectAcl, ], Effect: Allow, Resource: { Fn::GetAtt: [ Source71E471F1, Arn, ], }, }, { Action: [ mediaconvert:CreatePreset, mediaconvert:CreateJobTemplate, mediaconvert:DeletePreset, mediaconvert:DeleteJobTemplate, mediaconvert:DescribeEndpoints, mediaconvert:ListJobTemplates, mediaconvert:TagResource, mediaconvert:UntagResource, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :mediaconvert:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :*, ], ], }, }, { Action: [ mediapackage-vod:DeleteAsset, mediapackage-vod:DeletePackagingConfiguration, ], Effect: Allow, Resource: [ { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :mediapackage-vod:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :assets/*, ], ], }, { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :mediapackage-vod:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :packaging-configurations/packaging-config-*, ], ], }, ], }, { Action: [ mediapackage-vod:DescribePackagingGroup, mediapackage-vod:DeletePackagingGroup, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :mediapackage-vod:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :packaging-groups/, { Ref: AWS::StackName, }, -packaging-group, ], ], }, }, { Action: [ mediapackage-vod:CreatePackagingConfiguration, mediapackage-vod:CreatePackagingGroup, mediapackage-vod:ListAssets, mediapackage-vod:ListPackagingConfigurations, mediapackage-vod:ListPackagingGroups, mediapackage-vod:TagResource, mediapackage-vod:UntagResource, ], Effect: Allow, Resource: *, }, { Action: [ cloudfront:GetDistributionConfig, cloudfront:UpdateDistribution, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :cloudfront::, { Ref: AWS::AccountId, }, :distribution/, { Ref: CloudFrontToS3CloudFrontDistribution241D9866, }, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: CustomResourcePolicy79526710, Roles: [ { Ref: CustomResourceRoleAB1EF463, }, ], }, Type: AWS::IAM::Policy, }, CustomResourceRoleAB1EF463: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is required to create CloudWatch logs and interact with MediaConvert / MediaPackage actions that do not support resource level permissions, }, { id: W76, reason: All policies are required by the custom resource., }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, Destination920A3C57: { DeletionPolicy: Retain, Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-S10, reason: Bucket is private and is not using HTTP, }, ], }, }, Properties: { BucketEncryption: { ServerSideEncryptionConfiguration: [ { ServerSideEncryptionByDefault: { SSEAlgorithm: AES256, }, }, ], }, CorsConfiguration: { CorsRules: [ { AllowedHeaders: [ *, ], AllowedMethods: [ GET, ], AllowedOrigins: [ *, ], MaxAge: 3000, }, ], }, LoggingConfiguration: { DestinationBucketName: { Ref: Logs6819BB44, }, LogFilePrefix: destination-bucket-logs/, }, PublicAccessBlockConfiguration: { BlockPublicAcls: true, BlockPublicPolicy: true, IgnorePublicAcls: true, RestrictPublicBuckets: true, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], VersioningConfiguration: { Status: Enabled, }, }, Type: AWS::S3::Bucket, UpdateReplacePolicy: Retain, }, DestinationPolicy7982387E: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-S10, reason: Bucket is private and is not using HTTP, }, ], }, cfn_nag: { rules_to_suppress: [ { id: F16, reason: Public website bucket policy requires a wildcard principal, }, ], }, }, Properties: { Bucket: { Ref: Destination920A3C57, }, PolicyDocument: { Statement: [ { Action: s3:*, Condition: { Bool: { aws:SecureTransport: false, }, }, Effect: Deny, Principal: { AWS: *, }, Resource: [ { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, /*, ], ], }, ], }, { Action: s3:GetObject, Effect: Allow, Principal: { CanonicalUser: { Fn::GetAtt: [ CloudFrontToS3CloudFrontDistributionOrigin1S3OriginB0637B8F, S3CanonicalUserId, ], }, }, Resource: { Fn::Join: [ , [ { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, /*, ], ], }, }, ], Version: 2012-10-17, }, }, Type: AWS::S3::BucketPolicy, }, DynamoDBTable59784FC0: { DeletionPolicy: Retain, Metadata: { cfn_nag: { rules_to_suppress: [ { id: W28, reason: Table name is set to the stack name, }, { id: W74, reason: The DynamoDB table is configured to use the default encryption, }, ], }, }, Properties: { AttributeDefinitions: [ { AttributeName: guid, AttributeType: S, }, { AttributeName: srcBucket, AttributeType: S, }, { AttributeName: startTime, AttributeType: S, }, ], BillingMode: PAY_PER_REQUEST, GlobalSecondaryIndexes: [ { IndexName: srcBucket-startTime-index, KeySchema: [ { AttributeName: srcBucket, KeyType: HASH, }, { AttributeName: startTime, KeyType: RANGE, }, ], Projection: { ProjectionType: ALL, }, }, ], KeySchema: [ { AttributeName: guid, KeyType: HASH, }, ], PointInTimeRecoverySpecification: { PointInTimeRecoveryEnabled: true, }, TableName: { Ref: AWS::StackName, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::DynamoDB::Table, UpdateReplacePolicy: Retain, }, DynamoUpdateLambda0DF14C26: { DependsOn: [ DynamoUpdatePolicy7828BC4E, DynamoUpdateRoleB73E97DD, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Updates DynamoDB with event data, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, DynamoDBTable: { Ref: DynamoDBTable59784FC0, }, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -dynamo, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ DynamoUpdateRoleB73E97DD, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, DynamoUpdatePolicy7828BC4E: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: dynamodb:UpdateItem, Effect: Allow, Resource: { Fn::GetAtt: [ DynamoDBTable59784FC0, Arn, ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -dynamo-role, ], ], }, Roles: [ { Ref: DynamoUpdateRoleB73E97DD, }, ], }, Type: AWS::IAM::Policy, }, DynamoUpdateRoleB73E97DD: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, EncodeCompleteRuleAllowEventRuleVideoOnDemandStepFunctionsLambda0CB4E0F5435F3721: { Properties: { Action: lambda:InvokeFunction, FunctionName: { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, Principal: events.amazonaws.com, SourceArn: { Fn::GetAtt: [ EncodeCompleteRuleE2F74999, Arn, ], }, }, Type: AWS::Lambda::Permission, }, EncodeCompleteRuleE2F74999: { Properties: { Description: MediaConvert Completed event rule, EventPattern: { detail: { status: [ COMPLETE, ], userMetadata: { workflow: [ { Ref: AWS::StackName, }, ], }, }, source: [ aws.mediaconvert, ], }, Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -EncodeComplete, ], ], }, State: ENABLED, Targets: [ { Arn: { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, Id: Target0, }, ], }, Type: AWS::Events::Rule, }, EncodeErrorRule4CB53BA6: { Properties: { Description: MediaConvert Error event rule, EventPattern: { detail: { status: [ ERROR, ], userMetadata: { workflow: [ { Ref: AWS::StackName, }, ], }, }, source: [ aws.mediaconvert, ], }, Name: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -EncodeError, ], ], }, State: ENABLED, Targets: [ { Arn: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, Id: Target0, }, ], }, Type: AWS::Events::Rule, }, EncodeErrorRuleAllowEventRuleVideoOnDemandErrorHandlerLambda7A429D30DEEF909F: { Properties: { Action: lambda:InvokeFunction, FunctionName: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, Principal: events.amazonaws.com, SourceArn: { Fn::GetAtt: [ EncodeErrorRule4CB53BA6, Arn, ], }, }, Type: AWS::Lambda::Permission, }, EncodeLambdaDADCB2BB: { DependsOn: [ EncodePolicy89CB6B7C, EncodeRole36198881, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Creates a MediaConvert encode job, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, EndPoint: { Fn::GetAtt: [ MediaConvertEndPoint, EndpointUrl, ], }, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, MediaConvertRole: { Fn::GetAtt: [ MediaConvertRole031A64A9, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -encode, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ EncodeRole36198881, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, EncodePolicy89CB6B7C: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: [ mediaconvert:CreateJob, mediaconvert:GetJobTemplate, mediaconvert:TagResource, mediaconvert:UntagResource, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :mediaconvert:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :*, ], ], }, }, { Action: iam:PassRole, Effect: Allow, Resource: { Fn::GetAtt: [ MediaConvertRole031A64A9, Arn, ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -encode-role, ], ], }, Roles: [ { Ref: EncodeRole36198881, }, ], }, Type: AWS::IAM::Policy, }, EncodeRole36198881: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, ErrorHandlerLambdaCloudWatchLambdaInvokeErrors73673741: { DependsOn: [ ErrorHandlerPolicyF920541C, ErrorHandlerRole361CFEB7, ], Properties: { Action: lambda:InvokeFunction, FunctionName: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, Principal: events.amazonaws.com, SourceArn: { Fn::GetAtt: [ EncodeErrorRule4CB53BA6, Arn, ], }, }, Type: AWS::Lambda::Permission, }, ErrorHandlerLambdaFC10367C: { DependsOn: [ ErrorHandlerPolicyF920541C, ErrorHandlerRole361CFEB7, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W58, reason: Invalid warning: function has access to cloudwatch, }, { id: W89, reason: This resource does not need to be deployed inside a VPC, }, { id: W92, reason: This resource does not need to define ReservedConcurrentExecutions to reserve simultaneous executions, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Captures and processes workflow errors, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, DynamoDBTable: { Ref: DynamoDBTable59784FC0, }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, SnsTopic: { Ref: SnsTopic2C1570A4, }, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -error-handler, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ ErrorHandlerRole361CFEB7, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, ErrorHandlerPolicyF920541C: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: sns:Publish, Condition: { Bool: { aws:SecureTransport: true, }, }, Effect: Allow, Resource: { Ref: SnsTopic2C1570A4, }, }, { Action: dynamodb:UpdateItem, Effect: Allow, Resource: { Fn::GetAtt: [ DynamoDBTable59784FC0, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -error-handler-role, ], ], }, Roles: [ { Ref: ErrorHandlerRole361CFEB7, }, ], }, Type: AWS::IAM::Policy, }, ErrorHandlerRole361CFEB7: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, IngestWorkflow58F2BCD4: { DeletionPolicy: Delete, DependsOn: [ StepFunctionsServiceRoleDefaultPolicy6AD67B91, StepFunctionsServiceRole2A83B843, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-SF1, reason: Logging handled by DynamoDB Update step and Error Handler lambda, }, { id: AwsSolutions-SF2, reason: Optional configuration for this solution, }, ], }, }, Properties: { DefinitionString: { Fn::Join: [ , [ {"StartAt":"Input Validate","States":{"Input Validate":{"Next":"MediaInfo","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ InputValidateLambdaA739FF97, Arn, ], }, "},"MediaInfo":{"Next":"DynamoDB Update (Ingest)","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ MediaInfoLambda172F634B, Arn, ], }, "},"DynamoDB Update (Ingest)":{"Next":"SNS Choice (Ingest)","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ DynamoUpdateLambda0DF14C26, Arn, ], }, "},"SNS Choice (Ingest)":{"Type":"Choice","Choices":[{"Variable":"$.enableSns","BooleanEquals":true,"Next":"SNS Notification (Ingest)"}],"Default":"Process Execute"},"Process Execute":{"End":true,"Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, "},"SNS Notification (Ingest)":{"Next":"Process Execute","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ SnsNotificationLambda1EA4A474, Arn, ], }, "}}}, ], ], }, RoleArn: { Fn::GetAtt: [ StepFunctionsServiceRole2A83B843, Arn, ], }, StateMachineName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -ingest, ], ], }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::StepFunctions::StateMachine, UpdateReplacePolicy: Delete, }, InputValidateLambdaA739FF97: { DependsOn: [ InputValidatePolicyAC31247E, InputValidateRole862FC6A2, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Validates the input given to the workflow, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, AcceleratedTranscoding: { Ref: AcceleratedTranscoding, }, ArchiveSource: { Ref: Glacier, }, CloudFront: { Fn::GetAtt: [ CloudFrontToS3CloudFrontDistribution241D9866, DomainName, ], }, Destination: { Ref: Destination920A3C57, }, EnableMediaPackage: { Fn::If: [ EnableMediaPackageCondition, true, false, ], }, EnableSns: { Fn::If: [ EnableSnsCondition, true, false, ], }, EnableSqs: { Fn::If: [ EnableSqsCondition, true, false, ], }, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, FrameCapture: { Fn::If: [ FrameCaptureCondition, true, false, ], }, InputRotate: DEGREE_0, MediaConvert_Template_1080p: { Fn::If: [ EnableMediaPackageCondition, { Fn::Join: [ , [ { Ref: AWS::StackName, }, _Ott_1080p_Avc_Aac_16x9_mvod_no_preset, ], ], }, { Fn::Join: [ , [ { Ref: AWS::StackName, }, _Ott_1080p_Avc_Aac_16x9_qvbr_no_preset, ], ], }, ], }, MediaConvert_Template_2160p: { Fn::If: [ EnableMediaPackageCondition, { Fn::Join: [ , [ { Ref: AWS::StackName, }, _Ott_2160p_Avc_Aac_16x9_mvod_no_preset, ], ], }, { Fn::Join: [ , [ { Ref: AWS::StackName, }, _Ott_2160p_Avc_Aac_16x9_qvbr_no_preset, ], ], }, ], }, MediaConvert_Template_720p: { Fn::If: [ EnableMediaPackageCondition, { Fn::Join: [ , [ { Ref: AWS::StackName, }, _Ott_720p_Avc_Aac_16x9_mvod_no_preset, ], ], }, { Fn::Join: [ , [ { Ref: AWS::StackName, }, _Ott_720p_Avc_Aac_16x9_qvbr_no_preset, ], ], }, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, Source: { Ref: Source71E471F1, }, WorkflowName: { Ref: AWS::StackName, }, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -input-validate, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ InputValidateRole862FC6A2, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, InputValidatePolicyAC31247E: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: s3:GetObject, Effect: Allow, Resource: { Fn::Join: [ , [ { Fn::GetAtt: [ Source71E471F1, Arn, ], }, /*, ], ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -input-validate-role, ], ], }, Roles: [ { Ref: InputValidateRole862FC6A2, }, ], }, Type: AWS::IAM::Policy, }, InputValidateRole862FC6A2: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, Logs6819BB44: { DeletionPolicy: Retain, Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-S1, reason: Used to store access logs for other buckets, }, { id: AwsSolutions-S10, reason: Bucket is private and is not using HTTP, }, ], }, cfn_nag: { rules_to_suppress: [ { id: W35, reason: Used to store access logs for other buckets, }, { id: W51, reason: Bucket does not need a bucket policy, }, ], }, }, Properties: { AccessControl: LogDeliveryWrite, BucketEncryption: { ServerSideEncryptionConfiguration: [ { ServerSideEncryptionByDefault: { SSEAlgorithm: AES256, }, }, ], }, OwnershipControls: { Rules: [ { ObjectOwnership: ObjectWriter, }, ], }, PublicAccessBlockConfiguration: { BlockPublicAcls: true, BlockPublicPolicy: true, IgnorePublicAcls: true, RestrictPublicBuckets: true, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], VersioningConfiguration: { Status: Enabled, }, }, Type: AWS::S3::Bucket, UpdateReplacePolicy: Retain, }, LogsPolicy90DB40C9: { Properties: { Bucket: { Ref: Logs6819BB44, }, PolicyDocument: { Statement: [ { Action: s3:*, Condition: { Bool: { aws:SecureTransport: false, }, }, Effect: Deny, Principal: { AWS: *, }, Resource: [ { Fn::GetAtt: [ Logs6819BB44, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ Logs6819BB44, Arn, ], }, /*, ], ], }, ], }, ], Version: 2012-10-17, }, }, Type: AWS::S3::BucketPolicy, }, MediaConvertEndPoint: { DeletionPolicy: Delete, Properties: { Resource: EndPoint, ServiceToken: { Fn::GetAtt: [ CustomResource8CDCD7A7, Arn, ], }, }, Type: AWS::CloudFormation::CustomResource, UpdateReplacePolicy: Delete, }, MediaConvertPolicy91CC58C0: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: /* required to get/put objects to S3, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: [ s3:GetObject, s3:PutObject, ], Effect: Allow, Resource: [ { Fn::Join: [ , [ { Fn::GetAtt: [ Source71E471F1, Arn, ], }, /*, ], ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, /*, ], ], }, ], }, { Action: execute-api:Invoke, Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :execute-api:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -mediatranscode-policy, ], ], }, Roles: [ { Ref: MediaConvertRole031A64A9, }, ], }, Type: AWS::IAM::Policy, }, MediaConvertRole031A64A9: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: /* required to get/put objects to S3, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: mediaconvert.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, MediaConvertTemplates: { DeletionPolicy: Delete, Properties: { EnableMediaPackage: { Fn::If: [ EnableMediaPackageCondition, true, false, ], }, EnableNewTemplates: true, EndPoint: { Fn::GetAtt: [ MediaConvertEndPoint, EndpointUrl, ], }, Resource: MediaConvertTemplates, ServiceToken: { Fn::GetAtt: [ CustomResource8CDCD7A7, Arn, ], }, StackName: { Ref: AWS::StackName, }, }, Type: AWS::CloudFormation::CustomResource, UpdateReplacePolicy: Delete, }, MediaInfoLambda172F634B: { DependsOn: [ MediaInfoPolicy1D8C0D8D, MediaInfoRole16C46683, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Runs mediainfo on a pre-signed S3 URL, Environment: { Variables: { ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -mediainfo, ], ], }, Handler: lambda_function.lambda_handler, Role: { Fn::GetAtt: [ MediaInfoRole16C46683, Arn, ], }, Runtime: python3.9, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, MediaInfoPolicy1D8C0D8D: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: s3:GetObject, Effect: Allow, Resource: { Fn::Join: [ , [ { Fn::GetAtt: [ Source71E471F1, Arn, ], }, /*, ], ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -mediainfo-role, ], ], }, Roles: [ { Ref: MediaInfoRole16C46683, }, ], }, Type: AWS::IAM::Policy, }, MediaInfoRole16C46683: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, MediaPackageAssetsLambda63EB0986: { DependsOn: [ MediaPackageAssetsPolicy84101CE2, MediaPackageAssetsRole5B26B67C, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Ingests an asset into MediaPackage-VOD, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, GroupDomainName: { Fn::GetAtt: [ MediaPackageVod, GroupDomainName, ], }, GroupId: { Fn::GetAtt: [ MediaPackageVod, GroupId, ], }, MediaPackageVodRole: { Fn::GetAtt: [ MediaPackageVodRole931E8163, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -media-package-assets, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ MediaPackageAssetsRole5B26B67C, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, MediaPackageAssetsPolicy84101CE2: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, cfn_nag: { rules_to_suppress: [ { id: W12, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: iam:PassRole, Effect: Allow, Resource: { Fn::GetAtt: [ MediaPackageVodRole931E8163, Arn, ], }, }, { Action: [ mediapackage-vod:CreateAsset, mediapackage-vod:TagResource, mediapackage-vod:UntagResource, ], Effect: Allow, Resource: *, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -media-package-assets-role, ], ], }, Roles: [ { Ref: MediaPackageAssetsRole5B26B67C, }, ], }, Type: AWS::IAM::Policy, }, MediaPackageAssetsRole5B26B67C: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, MediaPackageVod: { DeletionPolicy: Delete, Properties: { DistributionId: { Ref: CloudFrontToS3CloudFrontDistribution241D9866, }, EnableMediaPackage: { Fn::If: [ EnableMediaPackageCondition, true, false, ], }, GroupId: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -packaging-group, ], ], }, PackagingConfigurations: HLS,DASH,MSS,CMAF, Resource: MediaPackageVod, ServiceToken: { Fn::GetAtt: [ CustomResource8CDCD7A7, Arn, ], }, StackName: { Ref: AWS::StackName, }, }, Type: AWS::CloudFormation::CustomResource, UpdateReplacePolicy: Delete, }, MediaPackageVodPolicy1DC9ECF2: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: /* required to get/put objects to S3, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: [ s3:GetObject, s3:GetBucketLocation, s3:GetBucketRequestPayment, ], Effect: Allow, Resource: [ { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, /*, ], ], }, ], }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -mediapackagevod-policy, ], ], }, Roles: [ { Ref: MediaPackageVodRole931E8163, }, ], }, Type: AWS::IAM::Policy, }, MediaPackageVodRole931E8163: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is required to get objects from S3, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: mediapackage.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, OutputValidateLambda2645C4BB: { DependsOn: [ OutputValidatePolicy8D988909, OutputValidateRole553C8CD2, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Parses MediaConvert job output, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, DynamoDBTable: { Ref: DynamoDBTable59784FC0, }, EndPoint: { Fn::GetAtt: [ MediaConvertEndPoint, EndpointUrl, ], }, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -output-validate, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ OutputValidateRole553C8CD2, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, OutputValidatePolicy8D988909: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: dynamodb:GetItem, Effect: Allow, Resource: { Fn::GetAtt: [ DynamoDBTable59784FC0, Arn, ], }, }, { Action: s3:ListBucket, Effect: Allow, Resource: { Fn::GetAtt: [ Destination920A3C57, Arn, ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -output-validate-role, ], ], }, Roles: [ { Ref: OutputValidateRole553C8CD2, }, ], }, Type: AWS::IAM::Policy, }, OutputValidateRole553C8CD2: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, ProcessWorkflow95FAF321: { DeletionPolicy: Delete, DependsOn: [ StepFunctionsServiceRoleDefaultPolicy6AD67B91, StepFunctionsServiceRole2A83B843, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-SF1, reason: Logging handled by DynamoDB Update step and Error Handler lambda, }, { id: AwsSolutions-SF2, reason: Optional configuration for this solution, }, ], }, }, Properties: { DefinitionString: { Fn::Join: [ , [ {"StartAt":"Profiler","States":{"Profiler":{"Next":"Encoding Profile Check","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ ProfilerLambdaFAFF7893, Arn, ], }, "},"Encoding Profile Check":{"Type":"Choice","Choices":[{"Variable":"$.isCustomTemplate","BooleanEquals":true,"Next":"Custom jobTemplate"},{"Variable":"$.encodingProfile","NumericEquals":2160,"Next":"jobTemplate 2160p"},{"Variable":"$.encodingProfile","NumericEquals":1080,"Next":"jobTemplate 1080p"},{"Variable":"$.encodingProfile","NumericEquals":720,"Next":"jobTemplate 720p"}]},"Custom jobTemplate":{"Type":"Pass","Next":"Accelerated Transcoding Check"},"Accelerated Transcoding Check":{"Type":"Choice","Choices":[{"Variable":"$.acceleratedTranscoding","StringEquals":"ENABLED","Next":"Enabled"},{"Variable":"$.acceleratedTranscoding","StringEquals":"PREFERRED","Next":"Preferred"},{"Variable":"$.acceleratedTranscoding","StringEquals":"DISABLED","Next":"Disabled"}]},"jobTemplate 2160p":{"Type":"Pass","Next":"Accelerated Transcoding Check"},"jobTemplate 1080p":{"Type":"Pass","Next":"Accelerated Transcoding Check"},"jobTemplate 720p":{"Type":"Pass","Next":"Accelerated Transcoding Check"},"Enabled":{"Type":"Pass","Next":"Frame Capture Check"},"Frame Capture Check":{"Type":"Choice","Choices":[{"Variable":"$.frameCapture","BooleanEquals":true,"Next":"Frame Capture"},{"Variable":"$.frameCapture","BooleanEquals":false,"Next":"No Frame Capture"}]},"Preferred":{"Type":"Pass","Next":"Frame Capture Check"},"Disabled":{"Type":"Pass","Next":"Frame Capture Check"},"Frame Capture":{"Type":"Pass","Next":"Encode Job Submit"},"Encode Job Submit":{"Next":"DynamoDB Update (Process)","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ EncodeLambdaDADCB2BB, Arn, ], }, "},"No Frame Capture":{"Type":"Pass","Next":"Encode Job Submit"},"DynamoDB Update (Process)":{"End":true,"Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ DynamoUpdateLambda0DF14C26, Arn, ], }, "}}}, ], ], }, RoleArn: { Fn::GetAtt: [ StepFunctionsServiceRole2A83B843, Arn, ], }, StateMachineName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -process, ], ], }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::StepFunctions::StateMachine, UpdateReplacePolicy: Delete, }, ProfilerLambdaFAFF7893: { DependsOn: [ ProfilerPolicy71C838D4, ProfilerRole5E433579, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Sets an EncodeProfile based on mediainfo output, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, DynamoDBTable: { Ref: DynamoDBTable59784FC0, }, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -profiler, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ ProfilerRole5E433579, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, ProfilerPolicy71C838D4: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: dynamodb:GetItem, Effect: Allow, Resource: { Fn::GetAtt: [ DynamoDBTable59784FC0, Arn, ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -profiler-role, ], ], }, Roles: [ { Ref: ProfilerRole5E433579, }, ], }, Type: AWS::IAM::Policy, }, ProfilerRole5E433579: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, PublishWorkflowEF670320: { DeletionPolicy: Delete, DependsOn: [ StepFunctionsServiceRoleDefaultPolicy6AD67B91, StepFunctionsServiceRole2A83B843, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-SF1, reason: Logging handled by DynamoDB Update step and Error Handler lambda, }, { id: AwsSolutions-SF2, reason: Optional configuration for this solution, }, ], }, }, Properties: { DefinitionString: { Fn::Join: [ , [ {"StartAt":"Validate Encoding Outputs","States":{"Validate Encoding Outputs":{"Next":"Archive Source Choice","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ OutputValidateLambda2645C4BB, Arn, ], }, "},"Archive Source Choice":{"Type":"Choice","Choices":[{"Variable":"$.archiveSource","StringEquals":"GLACIER","Next":"Archive"},{"Variable":"$.archiveSource","StringEquals":"DEEP_ARCHIVE","Next":"Deep Archive"}],"Default":"MediaPackage Choice"},"MediaPackage Choice":{"Type":"Choice","Choices":[{"Variable":"$.enableMediaPackage","BooleanEquals":true,"Next":"MediaPackage Assets"}],"Default":"DynamoDB Update (Publish)"},"Archive":{"Next":"MediaPackage Choice","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ ArchiveSourceLambda320F09D9, Arn, ], }, "},"Deep Archive":{"Next":"MediaPackage Choice","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ ArchiveSourceLambda320F09D9, Arn, ], }, "},"DynamoDB Update (Publish)":{"Next":"SQS Choice","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ DynamoUpdateLambda0DF14C26, Arn, ], }, "},"MediaPackage Assets":{"Next":"DynamoDB Update (Publish)","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ MediaPackageAssetsLambda63EB0986, Arn, ], }, "},"SQS Choice":{"Type":"Choice","Choices":[{"Variable":"$.enableSqs","BooleanEquals":true,"Next":"SQS Send Message"}],"Default":"SNS Choice (Publish)"},"SNS Choice (Publish)":{"Type":"Choice","Choices":[{"Variable":"$.enableSns","BooleanEquals":true,"Next":"SNS Notification (Publish)"}],"Default":"Complete"},"SQS Send Message":{"Next":"SNS Choice (Publish)","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ SqsSendMessageLambda156FD22A, Arn, ], }, "},"Complete":{"Type":"Pass","End":true},"SNS Notification (Publish)":{"Next":"Complete","Retry":[{"ErrorEquals":["Lambda.ServiceException","Lambda.AWSLambdaException","Lambda.SdkClientException"],"IntervalSeconds":2,"MaxAttempts":6,"BackoffRate":2}],"Type":"Task","Resource":", { Fn::GetAtt: [ SnsNotificationLambda1EA4A474, Arn, ], }, "}}}, ], ], }, RoleArn: { Fn::GetAtt: [ StepFunctionsServiceRole2A83B843, Arn, ], }, StateMachineName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -publish, ], ], }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::StepFunctions::StateMachine, UpdateReplacePolicy: Delete, }, S3Config: { DeletionPolicy: Delete, DependsOn: [ StepFunctionsLambdaCloudWatchLambdaInvokeCompletes8CE78F7D, StepFunctionsLambda8B4F69C7, StepFunctionsLambdaS3LambdaInvokeVideo456192AA, ], Properties: { IngestArn: { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, Resource: S3Notification, ServiceToken: { Fn::GetAtt: [ CustomResource8CDCD7A7, Arn, ], }, Source: { Ref: Source71E471F1, }, WorkflowTrigger: { Ref: WorkflowTrigger, }, }, Type: AWS::CloudFormation::CustomResource, UpdateReplacePolicy: Delete, }, SnsNotificationLambda1EA4A474: { DependsOn: [ SnsNotificationPolicy26B12503, SnsNotificationRole48AE9F11, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Sends a notification when the encode job is completed, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, SnsTopic: { Ref: SnsTopic2C1570A4, }, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -sns-notification, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ SnsNotificationRole48AE9F11, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, SnsNotificationPolicy26B12503: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: sns:Publish, Condition: { Bool: { aws:SecureTransport: true, }, }, Effect: Allow, Resource: { Ref: SnsTopic2C1570A4, }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -sns-notification-role, ], ], }, Roles: [ { Ref: SnsNotificationRole48AE9F11, }, ], }, Type: AWS::IAM::Policy, }, SnsNotificationRole48AE9F11: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, SnsTopic2C1570A4: { Properties: { DisplayName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -Notifications, ], ], }, KmsMasterKeyId: alias/aws/sns, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::SNS::Topic, }, SnsTopicTokenSubscription1D5A46B4F: { Properties: { Endpoint: { Ref: AdminEmail, }, Protocol: email, TopicArn: { Ref: SnsTopic2C1570A4, }, }, Type: AWS::SNS::Subscription, }, Source71E471F1: { DeletionPolicy: Retain, Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-S10, reason: Bucket is private and is not using HTTP, }, ], }, cfn_nag: { rules_to_suppress: [ { id: W51, reason: Bucket does not need a bucket policy, }, ], }, }, Properties: { BucketEncryption: { ServerSideEncryptionConfiguration: [ { ServerSideEncryptionByDefault: { SSEAlgorithm: AES256, }, }, ], }, LifecycleConfiguration: { Rules: [ { Id: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -soure-archive, ], ], }, Status: Enabled, TagFilters: [ { Key: { Ref: AWS::StackName, }, Value: GLACIER, }, ], Transitions: [ { StorageClass: GLACIER, TransitionInDays: 1, }, ], }, { Id: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -source-deep-archive, ], ], }, Status: Enabled, TagFilters: [ { Key: { Ref: AWS::StackName, }, Value: DEEP_ARCHIVE, }, ], Transitions: [ { StorageClass: DEEP_ARCHIVE, TransitionInDays: 1, }, ], }, ], }, LoggingConfiguration: { DestinationBucketName: { Ref: Logs6819BB44, }, LogFilePrefix: source-bucket-logs/, }, PublicAccessBlockConfiguration: { BlockPublicAcls: true, BlockPublicPolicy: true, IgnorePublicAcls: true, RestrictPublicBuckets: true, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], VersioningConfiguration: { Status: Enabled, }, }, Type: AWS::S3::Bucket, UpdateReplacePolicy: Retain, }, SourcePolicyE5AB5F73: { Properties: { Bucket: { Ref: Source71E471F1, }, PolicyDocument: { Statement: [ { Action: s3:*, Condition: { Bool: { aws:SecureTransport: false, }, }, Effect: Deny, Principal: { AWS: *, }, Resource: [ { Fn::GetAtt: [ Source71E471F1, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ Source71E471F1, Arn, ], }, /*, ], ], }, ], }, ], Version: 2012-10-17, }, }, Type: AWS::S3::BucketPolicy, }, SqsQueue13597403: { DeletionPolicy: Delete, Properties: { KmsDataKeyReusePeriodSeconds: 300, KmsMasterKeyId: alias/aws/sqs, QueueName: { Ref: AWS::StackName, }, RedrivePolicy: { deadLetterTargetArn: { Fn::GetAtt: [ SqsQueueDlqFD591F76, Arn, ], }, maxReceiveCount: 1, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], VisibilityTimeout: 120, }, Type: AWS::SQS::Queue, UpdateReplacePolicy: Delete, }, SqsQueueDlqFD591F76: { DeletionPolicy: Delete, Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-SQS3, reason: This resource is a DLQ, }, ], }, }, Properties: { KmsDataKeyReusePeriodSeconds: 300, KmsMasterKeyId: alias/aws/sqs, QueueName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -dlq, ], ], }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], VisibilityTimeout: 120, }, Type: AWS::SQS::Queue, UpdateReplacePolicy: Delete, }, SqsQueueDlqPolicy601D5F1E: { Properties: { PolicyDocument: { Statement: [ { Action: sqs:*, Condition: { Bool: { aws:SecureTransport: false, }, }, Effect: Deny, Principal: { AWS: *, }, Resource: { Fn::GetAtt: [ SqsQueueDlqFD591F76, Arn, ], }, }, ], Version: 2012-10-17, }, Queues: [ { Ref: SqsQueueDlqFD591F76, }, ], }, Type: AWS::SQS::QueuePolicy, }, SqsQueuePolicy24A842E9: { Properties: { PolicyDocument: { Statement: [ { Action: sqs:*, Condition: { Bool: { aws:SecureTransport: false, }, }, Effect: Deny, Principal: { AWS: *, }, Resource: { Fn::GetAtt: [ SqsQueue13597403, Arn, ], }, }, ], Version: 2012-10-17, }, Queues: [ { Ref: SqsQueue13597403, }, ], }, Type: AWS::SQS::QueuePolicy, }, SqsSendMessageLambda156FD22A: { DependsOn: [ SqsSendMessagePolicy702314CC, SqsSendMessageRole23292716, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W89, reason: Lambda functions do not need a VPC, }, { id: W92, reason: Lambda do not need ReservedConcurrentExecutions in this case, }, { id: W58, reason: Invalid warning: function has access to cloudwatch, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Publish the workflow results to an SQS queue, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, SqsQueue: { Ref: SqsQueue13597403, }, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -sqs-publish, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ SqsSendMessageRole23292716, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, SqsSendMessagePolicy702314CC: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: sqs:SendMessage, Condition: { Bool: { aws:SecureTransport: true, }, }, Effect: Allow, Resource: { Fn::GetAtt: [ SqsQueue13597403, Arn, ], }, }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -sqs-publish-role, ], ], }, Roles: [ { Ref: SqsSendMessageRole23292716, }, ], }, Type: AWS::IAM::Policy, }, SqsSendMessageRole23292716: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, StepFunctionsLambda8B4F69C7: { DependsOn: [ StepFunctionsPolicy4DB3D133, StepFunctionsRole575CBBE2, ], Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-L1, reason: Lambda NodeJS 18 Runtime in development..., }, ], }, cfn_nag: { rules_to_suppress: [ { id: W58, reason: Invalid warning: function has access to cloudwatch, }, { id: W89, reason: This resource does not need to be deployed inside a VPC, }, { id: W92, reason: This resource does not need to define ReservedConcurrentExecutions to reserve simultaneous executions, }, ], }, }, Properties: { Code: { S3Bucket: { Fn::Sub: cdk-hnb659fds-assets-\${AWS::AccountId}-\${AWS::Region}, }, S3Key: [HASH REMOVED].zip, }, Description: Creates a unique identifer (GUID) and executes the Ingest StateMachine, Environment: { Variables: { AWS_NODEJS_CONNECTION_REUSE_ENABLED: 1, ErrorHandler: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, IngestWorkflow: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :states:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :stateMachine:, { Ref: AWS::StackName, }, -ingest, ], ], }, ProcessWorkflow: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :states:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :stateMachine:, { Ref: AWS::StackName, }, -process, ], ], }, PublishWorkflow: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :states:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :stateMachine:, { Ref: AWS::StackName, }, -publish, ], ], }, SOLUTION_IDENTIFIER: AwsSolution/SO0021/%%VERSION%%, }, }, FunctionName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -step-functions, ], ], }, Handler: index.handler, Role: { Fn::GetAtt: [ StepFunctionsRole575CBBE2, Arn, ], }, Runtime: nodejs18.x, Tags: [ { Key: SolutionId, Value: SO0021, }, ], Timeout: 120, }, Type: AWS::Lambda::Function, }, StepFunctionsLambdaCloudWatchLambdaInvokeCompletes8CE78F7D: { DependsOn: [ StepFunctionsPolicy4DB3D133, StepFunctionsRole575CBBE2, ], Properties: { Action: lambda:InvokeFunction, FunctionName: { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, Principal: events.amazonaws.com, SourceArn: { Fn::GetAtt: [ EncodeCompleteRuleE2F74999, Arn, ], }, }, Type: AWS::Lambda::Permission, }, StepFunctionsLambdaS3LambdaInvokeVideo456192AA: { DependsOn: [ StepFunctionsPolicy4DB3D133, StepFunctionsRole575CBBE2, ], Properties: { Action: lambda:InvokeFunction, FunctionName: { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, Principal: s3.amazonaws.com, SourceAccount: { Ref: AWS::AccountId, }, }, Type: AWS::Lambda::Permission, }, StepFunctionsPolicy4DB3D133: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: states:StartExecution, Effect: Allow, Resource: [ { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :states:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :stateMachine:, { Ref: AWS::StackName, }, -ingest, ], ], }, { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :states:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :stateMachine:, { Ref: AWS::StackName, }, -process, ], ], }, { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :states:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :stateMachine:, { Ref: AWS::StackName, }, -publish, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::GetAtt: [ ErrorHandlerLambdaFC10367C, Arn, ], }, }, { Action: [ logs:CreateLogGroup, logs:CreateLogStream, logs:PutLogEvents, ], Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :logs:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :log-group:/aws/lambda/*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -step-functions-role, ], ], }, Roles: [ { Ref: StepFunctionsRole575CBBE2, }, ], }, Type: AWS::IAM::Policy, }, StepFunctionsRole575CBBE2: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: lambda.amazonaws.com, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, StepFunctionsServicePolicy7123B955: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: * is used so that the Lambda function can create log groups, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: lambda:InvokeFunction, Effect: Allow, Resource: { Fn::Join: [ , [ arn:, { Ref: AWS::Partition, }, :lambda:, { Ref: AWS::Region, }, :, { Ref: AWS::AccountId, }, :function:*, ], ], }, }, ], Version: 2012-10-17, }, PolicyName: { Fn::Join: [ , [ { Ref: AWS::StackName, }, -stepfunctions-service-role, ], ], }, Roles: [ { Ref: StepFunctionsServiceRole2A83B843, }, ], }, Type: AWS::IAM::Policy, }, StepFunctionsServiceRole2A83B843: { Metadata: { cfn_nag: { rules_to_suppress: [ { id: W11, reason: The * resource is required since the functions need to be created before the state machine, }, ], }, }, Properties: { AssumeRolePolicyDocument: { Statement: [ { Action: sts:AssumeRole, Effect: Allow, Principal: { Service: { Fn::Join: [ , [ states., { Ref: AWS::Region, }, .amazonaws.com, ], ], }, }, }, ], Version: 2012-10-17, }, Tags: [ { Key: SolutionId, Value: SO0021, }, ], }, Type: AWS::IAM::Role, }, StepFunctionsServiceRoleDefaultPolicy6AD67B91: { Metadata: { cdk_nag: { rules_to_suppress: [ { id: AwsSolutions-IAM5, reason: Statements added to default policy by aws-stepfunctions.StateMachine class, }, ], }, cfn_nag: { rules_to_suppress: [ { id: W76, reason: testestesteslsdkfjsdlkfjlskdfklsdljf, }, ], }, }, Properties: { PolicyDocument: { Statement: [ { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ InputValidateLambdaA739FF97, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ InputValidateLambdaA739FF97, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ MediaInfoLambda172F634B, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ MediaInfoLambda172F634B, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ DynamoUpdateLambda0DF14C26, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ DynamoUpdateLambda0DF14C26, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ StepFunctionsLambda8B4F69C7, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ SnsNotificationLambda1EA4A474, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ SnsNotificationLambda1EA4A474, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ ProfilerLambdaFAFF7893, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ ProfilerLambdaFAFF7893, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ EncodeLambdaDADCB2BB, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ EncodeLambdaDADCB2BB, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ OutputValidateLambda2645C4BB, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ OutputValidateLambda2645C4BB, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ ArchiveSourceLambda320F09D9, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ ArchiveSourceLambda320F09D9, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ MediaPackageAssetsLambda63EB0986, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ MediaPackageAssetsLambda63EB0986, Arn, ], }, :*, ], ], }, ], }, { Action: lambda:InvokeFunction, Effect: Allow, Resource: [ { Fn::GetAtt: [ SqsSendMessageLambda156FD22A, Arn, ], }, { Fn::Join: [ , [ { Fn::GetAtt: [ SqsSendMessageLambda156FD22A, Arn, ], }, :*, ], ], }, ], }, ], Version: 2012-10-17, }, PolicyName: StepFunctionsServiceRoleDefaultPolicy6AD67B91, Roles: [ { Ref: StepFunctionsServiceRole2A83B843, }, ], }, Type: AWS::IAM::Policy, }, UUID: { DeletionPolicy: Delete, Properties: { Resource: UUID, ServiceToken: { Fn::GetAtt: [ CustomResource8CDCD7A7, Arn, ], }, }, Type: AWS::CloudFormation::CustomResource, UpdateReplacePolicy: Delete, }, }, } `;