Welcome to Part 4 of the PJSIP and RingCentral article series. In Part 1 we introduced PJSIP to you and we also showed you a simple demo on how you use PJSIP for making phone calls through RingCentral. In Part 2 we focused on medias, we talked about both using a media player and recorder, we also provided code snippets to use wav files in a phone call. In part 3, we talked about DTMF. In this part, we are going to try AWS Lambda.
This article is just a pure technical experiment. It is by no means the best practice. It is just to try and evaluate the possibility to host a telephone service on AWS Lambda. AWS Lambda is not designed for long-running services. So our telephone service will make an outbound call and quit which takes merely a couple of seconds.
Create a docker image
Creating a docker image will be the very first step, because PJSIP cannot run directly on AWS Lambda. To do this we need to put it into a docker container. Here is the Dockerfile:
LABEL maintainer="Tyler Liu (email@example.com)"
RUN apt-get update && apt-get install -y wget build-essential pkg-config
RUN wget https://github.com/pjsip/pjproject/archive/2.10.tar.gz && tar -zxvf 2.10.tar.gz
RUN ./configure && make dep && make && make install
COPY ./src/* /src/
The Dockerfile is pretty self-explanatory. We start with a base Ubuntu image, then we compile PJSIP, and last we copy our source code into the image and set the startup command.
For the source code part, there are two main files, the first is the C++ PJSIP file: index.cpp. It starts a PJSIP phone, makes an outbound call to a pre-defined number, plays a pre-recorded audio file and quits. We recommend you read the first three articles, so you can easily do this.
./src/run.sh is of the following content:
g++ -o /tmp/a.out ./index.cpp $(pkg-config --cflags --libs libpjproject)
export LD_LIBRARY_PATH=/pjproject-2.10/pjsip/lib:/pjproject-2.10/pjlib/lib:/pjproject-2.10/pjmedia/lib:/pjproject-2.10/pjlib-util/lib:/pjproject-2.10/pjnath/lib:/pjproject-2.10/third_party/lib /tmp/a.out
It simply compiles the
index.cpp file and runs it.
Use the following command to build the docker image:
docker build -t rc-pjsip-aws-lambda-demo:latest .
Test the docker image locally
To do that make sure to run this:
docker run -it --rm rc-pjsip-aws-lambda-demo
If everything goes well, the target phone should ring. When you pickup the phone call you should be able to hear the pre-recorded audio playing. After about 20 seconds the call should hang up itself.
Push docker image to AWS ECR
First you will need to create an AWS ECR repo:
aws ecr create-repository --repository-name rc-pjsip-aws-lambda-demo --image-scanning-configuration scanOnPush=true
In the output message of the command above, you can find your AWS account ID, something like
1234567890.dkr.ecr.us-east-1.amazonaws.com in which
1234567890 is your AWS account ID.
In the content below, we will use
1234567890 as sample/fake AWS account ID. You need to replace it with a real one.
Next you will to tag the docker image:
docker tag rc-pjsip-aws-lambda-demo:latest 1234567890.dkr.ecr.us-east-1.amazonaws.com/rc-pjsip-aws-lambda-demo:latest
Finally you will push it to remote:
aws ecr get-login-password | docker login --username AWS --password-stdin 1234567890.dkr.ecr.us-east-1.amazonaws.comdocker push 1234567890.dkr.ecr.us-east-1.amazonaws.com/rc-pjsip-aws-lambda-demo:latest
Deploy to AWS Lambda
It’s just like normal AWS Lambda functions, but with a docker image as the executable:
- http: 'GET /call'
One command to deploy everything to remote:
yarn sls deploy .
To do that use this code:
AWS API Gateway has a maximum timeout value of 30 seconds. So your phone call can only last around 20 seconds(because the app startup costs around 10 seconds). To workaround it, you can define a proxy method.
In this article, we created a docker image for RingCentral with PJSIP. And we also covered how to deploy this docker image as an AWS Lambda function. It might not be the best practice to host a telephone service but it is quite interesting to learn all the technical details. I hope you enjoy reading this article as much as I did writing it.
Please let us know what you think by leaving your questions and comments below. To learn even more about other features we have make sure to visit our developer site and if you’re ever stuck make sure to go to our developer forum.
Want to stay up to date and in the know about new APIs and features? Join our Game Changer Program and earn great rewards for building your skills and learning more about RingCentral!