 Hello and welcome everyone, my name is Rohit Kumar, I am a computer science graduate student at Northeastern University. This talk is about the prototype serverless platform that we developed for OpenStack as a part of our cloud computing course at Northeastern University. When we started with the project back in spring 2016, serverless or function as a service paradigm was relatively new and we did not have any open source implementation or a documentation to refer to. We wanted to implement the core functionality and test the feasibility of OpenStack. OpenStack did not have any explicit platform also at that time to support running function as a service. Briefly, I want to discuss about cloud computing in cloud. Commonly applications on cloud are deployed onto past platforms running virtual machines that interact with the common data store for data sharing. Virtual machines need to run service in a high available environment which needs to be maintained as well. This task becomes unfolded with microservices. Now, container-based services like Elastic Beanstalk work on similar pattern but they improve quite a bit upon the server management. But however, the notion of server was still there and servers are difficult to configure and manage over a longer period of time. You also end up paying a lot for the ideal CPU cycles in the server even when the application is not being used. Horizontal scaling is severely limited by the server startup time as well and quite a lot of time the servers are underutilized. So, serverless goes one step beyond the past platforms. In this model, we have one simple primitive. The user submits stateless functions that are executed into fmr containers and the outputs of these functions are accessed from shared remote storage. Now, the applications can now be viewed as a set of these stateless functions. By removing the notion of servers from the end users, serverless avoids significant management and configuration overhead that until now has been a prerequisite. These stateless functions can be triggered by events that can be configured by developers themselves. So, this gets rid of the complex task of configuring and managing servers. The notion of idle servers is not there anymore, at least for the users. So, you pay only for what you use and container virtualizations reduces, are fast and allow container scalability as well. This abstraction really resonated with us and we wanted to get a chance to create such a platform on OpenStack. So, the serverless we created runs on a container orchestration engine, which runs on top of an IAS, which is OpenStack in this case. We used Docker for the Docker container for running the handler functions console as the discovery service, RabbitMQ for event queue and MongoDB as our data store. So, this diagram over here gives a brief view about the whole user flow as well as the way different components interact with each other. The big blob called serverless engine over there interacts, takes care of all the logic of talking to MongoDB as well as talking to RabbitMQ and maintaining the Docker swarm services continuously. So, when we bootstrap it, we have only one virtual machine in the whole cluster, which is used to create the containers for running these functions. Now, a user can use a rest of web UI to upload the functions with the parameters like memory requirements, time taken to execute the function as well as the language or the platform dependencies. The serverless engine stores all these execution parameters along with the function in the MongoDB. RabbitMQ keeps a list of all the events that can be used to trigger the handler function. These events can be coming from multiple sources, but in our case, we just restricted them to come from GitHub commands for testing purposes. So, when the engine figures out an event, it fetches from MongoDB the corresponding event handler to execute, and it asks Docker swarm service to create a container. So, as soon as the container is created, we get a virtual machine ID which we use to export the function to that virtual machine and execute the function using remote RPC calls. So, at some point in time, we will need to expand the size of the cluster as well. To support elasticity, the size of the cluster has to be increased and decreased automatically based on the utilization. So, we added a new VM virtual machine whenever the utilization of the cluster goes beyond 70% in the memory area and delete the VM whenever the memory goes below 30% utilization. So, a new VM is created using OpenStack Nova services and is federated to the swarm cluster using console discovery. So, the Docker swarm service creates a list of all the IPs using console, which it can use to create the containers where the function handlers can be executed. So, the core part of the whole design is how we create the containers. The simplest way is to create a container for running each function handler that comes as an event. So, when the engine gets a request, it creates a new container and it purges the container after the function execution has been completed. So, this gave us an execution time of nearly four seconds, but it comes with the container startup time and it has a very high function environment setup time. So, obviously, this was not good and we started thinking that, can we keep the containers running to execute the functions which are concurrently coming? So, this, we also figured that the time to unpause a container is much lesser than the time to restart the container. The order is nearly around 300 millisecond. So, this gave us an idea to start with a new extension which was to keep the containers running to execute the stream of functions from the same event type. So, in this case, when the engine receives a request, it creates a container, executes the handler function on the container and saves the mapping between the container and the function. We had an in-memory mapping which had a list of all the containers and the functions which was executed on those containers. So, whenever a new request comes up now, we look up into the map and find out if a container is present already in the unpause state. If we find a container, then we unpause it, we execute the handler function on that container. We got an average time of 1.6 seconds in this case and this saves the container start-up time, but it comes up with the cost of managing the state as well as a high-memory cost. So, the point here to note is the difference between the time of execution between the method first and the second method. And this is also the norm today for the stream of service. For the stream of functions, the serverless platform performs much better than the discrete setup for the events which come in discrete way. So, looking at this graph as well, the bottleneck is there for the number of containers that can be kept in the running or in the pause state. So, when we keep containers in the pause state for a longer period of time, it increases the memory consumption and reduces the number of containers that can be kept running in the pause state. So, we just keep the containers in the pause state for five seconds and then we purge them because in five seconds, if the request has not come in the form of a stream, then the container does not need to be kept in the pause state in the memory. So, in closing, I would like to say that this project was a great learning experience for us. We implemented a complete functioning serverless prototype on OpenStack with a team of five members in a 13-week cloud computing course. And this is one of the 11 projects that we did in the course with NU and BU in association with MOC, which I just used OpenCloud. That's all for me. Thank you. Thank you for your time.