[PYTHON] AWS Lambda + Twilio Make Google Calendar reminders call with voice notifications

Try voice notification of Google Calendar reminders using AWS and Twilio

I usually receive various reminder notifications by email or push notification, but I tend to overlook it, so I thought it would be nice if you could notify me of Google Calendar reminders by voice.

What you need in advance other than AWS services

  1. Receiving address (original domain) used by AWS SES
  2. Twilio account
  3. Phone number purchase fee and call charge (so-called money)

Constitution

Constitution.png

I will write the general flow.

  1. Send a reminder email from Google Calendar to Gmail
  2. Forward from Gmail to another address (AWS SES)
  3. Data received by SES is PUT to S3
  4. Lambda fires on condition of S3 PUT
  5. Send call data to Twilio
  6. Call users from Twilio

There are many steps, but except for writing Lambda code, I just clicked on the screen.

Buy Phone Numbers on Twilio (Billing)

First, sign up at Twilio.

Confirmation of SID and TOKEN

twilio1.png

After signing up and logging in, go to the "Console Dashboard" and make a note of the contents of "ACCOUNT SID" and "AUTH TOKEN". This will be used later in the Lambda function.

Purchase a phone number

Then purchase the phone number you need to make the call. You need to charge for the purchase of the phone number, so charge the points in advance on the "Billing" page.

After charging points, go from "Console Dashboard" to "Buy a Number". Since the phone number search screen is displayed

  1. Select "Japan (or US)" from "Country"
  2. Check "Voice call" in "Available functions"
  3. Search

You should see a list of available phone numbers in the search results, so buy the number you like. twilio2.png

When you purchase a phone number, you should see the phone number you purchased in "Phone Number" and "Active Phone Number". This number is also used in the Lambda function, so keep it in mind.

___ * If you get a Twilio account, you will get one phone number for a free trial, so that may be fine. I've charged so quickly that I'm not sure how many calls I can make for free. ___

Transfer from Google Calendar to Gmail to SES

Notification settings from Google Calendar to Gmail are easy, so I won't write them.

Gmail sets the condition to "from: ([email protected])" etc. in "Settings"-> "Filters and blocked addresses"-> "Create new filter" and forwards to the following address It is OK if you set the forwarding address with.

AWS SES settings

For more information on AWS SES settings, please refer to the following articles in detail.

AWS Lambda Next, let's create a Lambda function.

code

First, write the code locally. $ mkdir voice_reminder
$ cd voice_reminder
$ vim lambda_function.py

lambda_function.py


# -*- coding: utf-8 -*-
import os
import re
import json
import email                                                                                                                                  
import base64
import urllib

import boto3
from twilio.rest import Client                                                                                                                
account_sid = os.environ['ACCOUNT_SID']
auth_token = os.environ['AUTH_TOKEN']

#Set the Account SID and Auth Token on your Twilio account page
client = Client(account_sid, auth_token)

s3 = boto3.client('s3')

def lambda_handler(event, context):
    bucket = event['Records'][0]['s3']['bucket']['name']
    key = urllib.unquote_plus(event['Records'][0]['s3']['object']['key']).decode('utf8')

    titleText = None
    timeText = None

    try:
        #Extract the mail data transferred from Gmail
        response = s3.get_object(Bucket=bucket, Key=key)
        b = email.message_from_string(response['Body'].read())

        titleRegex = re.compile("title: (.+)")
        timeRegex = re.compile("Date and time: \d{4}/\d{2}/\d{2} \(.+\) (\d{2}\:\d{2}) ~ (\d{2}\:\d{2}) .+")

        if b.is_multipart():
            for payload in b.get_payload():
                line = base64.b64decode(payload.get_payload())

                #Extract the title and date and time of the email body

                title = titleRegex.search(line)
                if title is not None:
                    titleText = title.group(1)

                time = timeRegex.search(line)
                if time is not None:
                    timeText = time.group(1)

    except Exception as e:
        print(e)
        raise e

    if titleText is not None and timeText is not None:
        twiml = "<Response><Pause length='3'/><Say voice='woman' language='ja-jp'>This is a reminder. today%From s%There is a schedule for s.</Say></Response>" % (timeText, titleText)

        #Remind text(Made TwiML)To Twimlets Echo and call the designated phone number
        call = client.api.account.calls\
                .create(to=os.environ['REMIND_TO'],
                        from_=os.environ['REMIND_FROM'],
                        url="http://twimlets.com/echo?Twiml="+urllib.quote(twiml.encode("utf-8")))
        print(call.sid)

After writing the code, install the SDK called twilio-python in the same directory as your Lambda function.

$ pip install twilio -t /path/to/voice_reminder

After installing the SDK, create a Zip file.

$ zip -r voice_reminder.zip .

Create a Lambda function on AWS

Next, create a Lambda function.

  1. "Creating a Lambda function"

  2. Select "Blank Function"

  3. In "Trigger settings", specify the S3 Bucket created when setting SES. lambda-trigger.png

  4. Select the trigger as S3

  5. Select the pre-created S3 in "Bucket"

  6. Set "Event Type" to "Put"

  7. Set the prefix (if the Object key prefix was set when setting SES, make it the same)

  8. Check the activation of the trigger

  9. Set each item in "Function settings". スクリーンショット 2017-04-19 18.35.14.png

  10. Enter the name of the function

  11. Select Python 2.7 for "Runtime"

  12. Select "Upload .ZIP file" in "Code entry type" and select the Zip file created earlier.

  13. Enter the following items in the environment variables. lambda-env.png

  14. Set "ACCOUNT_SID" to the Account SID obtained by Twilio

  15. Set "AUTH_TOKEN" to the Auth Token you got with Twilio

  16. Set the phone number you want to remind "REMIND_TO" (+8190 ******** etc.)

  17. Set "REMIND_FROM" to the phone number you purchased from Twilio (+8150 ********, etc.)

  18. Specify "Role" and "Existing role" as appropriate. (Since S3 access, make it in advance with IAM)

  19. Set "Timeout" in "Detailed Settings" to about 30 seconds.

  20. Create a function

Set a schedule in Google Calendar

Then set an appointment in Google Calendar and see if Twilio sends a voice reminder.

I will not explain Google Calendar in particular, but you can set the notification timing by selecting "Edit notification"-> "Notification of appointment" from "Calendar settings", so please set your favorite time.

in conclusion

When I first touched Twilio this time, I felt that it would be interesting to combine it with a serverless architecture like AWS Lambda (now).

Recommended Posts

AWS Lambda + Twilio Make Google Calendar reminders call with voice notifications
Make Lambda Layers with Lambda
Make ordinary tweets fleet-like with AWS Lambda and Python
Operate limited shared Google Calendar with Lambda (Python) [cloudpack Osaka]
AWS Lambda with PyTorch [Lambda import]
[AWS] Create API with API Gateway + Lambda
Using Lambda with AWS Amplify with Go
Notify HipChat with AWS Lambda (Python)