...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
AWSTemplateFormatVersion: '2010-09-09' Transform: 'AWS::Serverless-2016-10-31' Description: >- Building Serverless development environment and CI/CD process for DevOps based on Cloud9 Globals: Function: Runtime: python2.7 Handler: lambda_function.lambda_handler MemorySize: 128 Timeout: 60 Resources: PostNews: Type: 'AWS::Serverless::Function' Properties: CodeUri: PostNews Description: Post news text to convert from text to speech Events: PostNewsApi: Type: Api Properties: Path: /news Method: POST Policies: - Version: '2012-10-17' Statement: - Effect: Allow Action: - 'logs:PutLogEvents' - 'logs:CreateLogStream' - 'dynamodb:PutItem' - 'sns:Publish' Resource: '*' |
...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
AWSTemplateFormatVersion: '2010-09-09'
Transform: 'AWS::Serverless-2016-10-31'
Description: >-
Building Serverless development environment and CI/CD process for DevOps based
on Cloud9
Globals:
Function:
Runtime: python2.7
Handler: lambda_function.lambda_handler
MemorySize: 128
Timeout: 60
Environment:
Variables:
DB_TABLE_NAME:
Ref: NewsTable
SNS_TOPIC:
Ref: NewsTopic
BUCKET_NAME:
Ref: PollyMp3Bucket
Resources:
NewsTable:
Type: 'AWS::Serverless::SimpleTable'
Properties:
PrimaryKey:
Name: id
Type: String
ProvisionedThroughput:
ReadCapacityUnits: 5
WriteCapacityUnits: 5
NewsTopic:
Type: 'AWS::SNS::Topic'
Properties:
DisplayName: NewsTopic
PollyMp3Bucket:
Type: 'AWS::S3::Bucket'
StaticWebBucket:
Type: 'AWS::S3::Bucket'
Properties:
AccessControl: PublicRead
WebsiteConfiguration:
IndexDocument: index.html
ErrorDocument: error.html
PostNews:
Type: 'AWS::Serverless::Function'
Properties:
CodeUri: PostNews
Description: Post news text to convert from text to speech
Events:
PostNewsApi:
Type: Api
Properties:
Path: /news
Method: POST
Policies:
- Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- 'logs:PutLogEvents'
- 'logs:CreateLogStream'
- 'dynamodb:PutItem'
- 'sns:Publish'
Resource: '*'
|
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
# -*- coding: utf-8 -*- from __future__ import print_function import boto3 import os from contextlib import closing from boto3.dynamodb.conditions import Key, Attr import re def lambda_handler(event, context): postId = event["Records"][0]["Sns"]["Message"] print ("Text to Speech function. Post ID in DynamoDB: ", postId) # Retrieving information about the post from DynamoDB table dynamodb = boto3.resource('dynamodb') table = dynamodb.Table(os.environ['DB_TABLE_NAME']) postItem = table.query( KeyConditionExpression=Key('id').eq(postId) ) text = postItem["Items"][0]["originText"] voice = postItem["Items"][0]["pollyVoice"] timbre = postItem["Items"][0]["pollyTimbre"] pitch = postItem["Items"][0]["pollyPitch"] rest = text # Because single invocation of the polly synthesize_speech api can # transform text with about 3,000 characters, we are dividing the # post into blocks of approximately 2,900 characters. textBlocks = [] while (len(rest) > 3000): begin = 0 end = rest.find(".", 2900) if (end == -1): end = rest.find(" ", 2900) textBlock = rest[begin:end] rest = rest[end:] textBlocks.append(textBlock) textBlocks.append(rest) #For each block, invoke Polly API, which will transform text into audio polly = boto3.client('polly') for textBlock in textBlocks: removeBrackets = re.sub(r'\([^)]*\)', '', textBlock) repTextBlock = re.sub('[·…]', '<break time="100ms"/>', removeBrackets) #repTextBlock = re.sub('["·\'…]', '<break time="100ms"/>', removeBrackets) ssmlBlock = "<speak><amazon:effect vocal-tract-length=\"" + timbre + "\"><prosody pitch=\"" + pitch + "\">" + repTextBlock + "</prosody></amazon:effect></speak>" #print (ssmlBlock) response = polly.synthesize_speech(OutputFormat='mp3', Text = ssmlBlock, VoiceId = voice, TextType = 'ssml') #Save the audio stream returned by Amazon Polly on Lambda's temp # directory. If there are multiple text blocks, the audio stream # will be combined into a single file. if "AudioStream" in response: with closing(response["AudioStream"]) as stream: output = os.path.join("/tmp/", postId) with open(output, "a") as file: file.write(stream.read()) s3 = boto3.client('s3') s3.upload_file('/tmp/' + postId, os.environ['BUCKET_NAME'], postId + ".mp3") s3.put_object_acl(ACL='public-read', Bucket=os.environ['BUCKET_NAME'], Key= postId + ".mp3") location = s3.get_bucket_location(Bucket=os.environ['BUCKET_NAME']) region = location['LocationConstraint'] if region is None: url_begining = "https://s3.amazonaws.com/" else: url_begining = "https://s3-" + str(region) + ".amazonaws.com/" \ url = url_begining \ + str(os.environ['BUCKET_NAME']) \ + "/" \ + str(postId) \ + ".mp3" #Updating the item in DynamoDB response = table.update_item( Key={'id':postId}, UpdateExpression= "SET #statusAtt = :statusValue, #urlAtt = :urlValue", ExpressionAttributeValues= {':statusValue': 'UPDATED', ':urlValue': url}, ExpressionAttributeNames= {'#statusAtt': 'pollyStatus', '#urlAtt': 'mp3Url'}, ) return |
...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
Resources:
...
ConvertAudio:
Type: 'AWS::Serverless::Function'
Properties:
CodeUri: ConvertAudio
Description: Convert Audio using Amazon Polly
Policies:
- Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- 'logs:PutLogEvents'
- 'logs:CreateLogStream'
- 'dynamodb:Query'
- 'dynamodb:UpdateItem'
- 's3:GetBucketLocation'
- 's3:PutObject'
- 's3:PutObjectAcl'
- 'polly:SynthesizeSpeech'
Resource: '*'
Events:
ConvertResource:
Type: SNS
Properties:
Topic:
Ref: NewsTopic
|
...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
Resources:
...
GetNews:
Type: 'AWS::Serverless::Function'
Properties:
CodeUri: GetNews
Description: Gather information from Ajax calls from web pages
Policies:
- Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- 'logs:PutLogEvents'
- 'logs:CreateLogStream'
- 'dynamodb:Query'
- 'dynamodb:Scan'
Resource: '*'
Events:
GetNewsApi:
Type: Api
Properties:
Path: /news
Method: GET |
...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
Resources:
...
DeleteNews:
Type: 'AWS::Serverless::Function'
Properties:
CodeUri: DeleteNews
Description: Delete news item in DynamoDB Table and mp3 file in S3 bucket.
Policies:
- Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- 'logs:PutLogEvents'
- 'logs:CreateLogStream'
- 'dynamodb:DeleteItem'
- 's3:DeleteObject'
Resource: '*'
Events:
DeleteNewsApi:
Type: Api
Properties:
Path: /news
Method: DELETE |
...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
Outputs:
WebsiteURL:
Description: Name of S3 bucket to hold website content
Value:
'Fn::Join':
- ''
- - 'https://'
- 'Fn::GetAtt':
- StaticWebBucket
- DomainName
APIEndpointURL:
Description: URL of your API endpoint
Value:
'Fn::Sub': >-
https://${ServerlessRestApi}.execute-api.${AWS::Region}.amazonaws.com/Prod/news/
S3WebBucket:
Description: S3 Bucket Name for web hosting
Value:
Ref: StaticWebBucket |
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
Globals:
...
Api:
# enable CORS; to make more specific, change the origin wildcard
# to a particular domain name, e.g. "'www.example.com'"
Cors:
AllowMethods: "'*'"
AllowHeaders: "'*'"
AllowOrigin: "'*'" |
...
코드 블럭 | ||||||||
---|---|---|---|---|---|---|---|---|
| ||||||||
AWSTemplateFormatVersion: '2010-09-09' Transform: 'AWS::Serverless-2016-10-31' Description: >- Building Serverless development environment and CI/CD process for DevOps based on Cloud9 Globals: Function: Runtime: python2.7 Handler: lambda_function.lambda_handler MemorySize: 128 Timeout: 60 Environment: Variables: DB_TABLE_NAME: Ref: NewsTable SNS_TOPIC: Ref: NewsTopic BUCKET_NAME: Ref: PollyMp3Bucket Api: # enable CORS; to make more specific, change the origin wildcard # to a particular domain name, e.g. "'www.example.com'" Cors: AllowMethods: "'*'" AllowHeaders: "'*'" AllowOrigin: "'*'" Resources: NewsTable: Type: 'AWS::Serverless::SimpleTable' Properties: PrimaryKey: Name: id Type: String ProvisionedThroughput: ReadCapacityUnits: 5 WriteCapacityUnits: 5 NewsTopic: Type: 'AWS::SNS::Topic' Properties: DisplayName: NewsTopic PollyMp3Bucket: Type: 'AWS::S3::Bucket' StaticWebBucket: Type: 'AWS::S3::Bucket' Properties: AccessControl: PublicRead WebsiteConfiguration: IndexDocument: index.html ErrorDocument: error.html PostNews: Type: 'AWS::Serverless::Function' Properties: CodeUri: PostNews Description: Post news text to convert from text to speech Events: PostNewsApi: Type: Api Properties: Path: /news Method: POST Policies: - Version: '2012-10-17' Statement: - Effect: Allow Action: - 'logs:PutLogEvents' - 'logs:CreateLogStream' - 'dynamodb:PutItem' - 'sns:Publish' Resource: '*' ConvertAudio: Type: 'AWS::Serverless::Function' Properties: CodeUri: ConvertAudio Description: Convert Audio using Amazon Polly Policies: - Version: '2012-10-17' Statement: - Effect: Allow Action: - 'logs:PutLogEvents' - 'logs:CreateLogStream' - 'dynamodb:Query' - 'dynamodb:UpdateItem' - 's3:GetBucketLocation' - 's3:PutObject' - 's3:PutObjectAcl' - 'polly:SynthesizeSpeech' Resource: '*' Events: ConvertResource: Type: SNS Properties: Topic: Ref: NewsTopic GetNews: Type: 'AWS::Serverless::Function' Properties: CodeUri: GetNews Description: Gather information from Ajax calls from web pages Policies: - Version: '2012-10-17' Statement: - Effect: Allow Action: - 'logs:PutLogEvents' - 'logs:CreateLogStream' - 'dynamodb:Query' - 'dynamodb:Scan' Resource: '*' Events: GetNewsApi: Type: Api Properties: Path: /news Method: GET DeleteNews: Type: 'AWS::Serverless::Function' Properties: CodeUri: DeleteNews Description: Delete news item in DynamoDB Table and mp3 file in S3 bucket. Policies: - Version: '2012-10-17' Statement: - Effect: Allow Action: - 'logs:PutLogEvents' - 'logs:CreateLogStream' - 'dynamodb:DeleteItem' - 's3:DeleteObject' Resource: '*' Events: DeleteNewsApi: Type: Api Properties: Path: /news Method: DELETE Outputs: WebsiteURL: Description: Name of S3 bucket to hold website content Value: 'Fn::Join': - '' - - 'https://' - 'Fn::GetAtt': - StaticWebBucket - DomainName APIEndpointURL: Description: URL of your API endpoint Value: 'Fn::Sub': >- https://${ServerlessRestApi}.execute-api.${AWS::Region}.amazonaws.com/Prod/news/ S3WebBucket: Description: S3 Bucket Name for web hosting Value: Ref: StaticWebBucket |
Cloud9 Code 창 하단의 Terminal로 접근
...