Functions as a Service (FaaS)

Phillip Tribble edited this page Sep 13, 2017 · 16 revisions

FaaS capabilities available in PiCluster 2.2

Sample Function Application that prints "Hello, World".

This function is a simple Node.js application that returns "Hello, World" to the server and then the container is killed. Package the Dockerfile and Application to your PiCluster Docker directory.You can also upload a zip file of the folder directly into the web console for simplicity.

Dockerfile

FROM alpine
RUN apk update;apk add nodejs nodejs-npm
ADD * /
RUN cd /;npm install
CMD cd /;node /main.js

Application

var request = require('request');
var server = process.env.SERVER;
var token = process.env.TOKEN;
var uuid = process.env.UUID;
var output = '';

function sendOutput(what) {

  const body = JSON.stringify({
    token,
    output: what,
    uuid
  });

  const options = {
    url: server + '/function',
    method: 'POST',
    headers: {
      'Content-Type': 'application/json',
      'Content-Length': body.length
    },
    body
  };

  request(options, (error, response) => {
    if (error) {
      console.log('An error has occurred.' + error);
    }
  });
}

sendOutput('Hello, World!');

Run the function

Use your PiCluster token and container name that matches the folder to the Docker files in your PiCluster Docker directory.

# curl "127.0.0.1:3000/function?token=1234567890ABCDEFGHJKLMNOP&function=test";
      http://127.0.0.1:3000/getfunction?token=1234567890ABCDEFGHJKLMNOP&uuid=6128550

PiCluster will set the token and server ENVAR's in the container for you when it is created so that the function will be able to return the output to the server. After the container is built and started, the output will be stored on the server. The output of the command above will return a URL that can be polled by an application to retrieve the output from the function.

Retrieve the output of the function

http://127.0.0.1:3000/getfunction?token=1234567890ABCDEFGHJKLMNOP&uuid=6128550

You should see "Hello, World" as the output. If you run that too early, no output will be given. Once the output is downloaded by an application, the data is removed from PiCluster.

Sample Node.js Application that creates and delivers the output from the server

Let's explore how a real application would use a function. The code below is a sample application that tells the server to execute the function. The app will poll the server every few seconds to check if the container delivered the output to the server. When the app receives the output from the server, you will see it in the terminal.

const http = require('http');
const express = require('express');
const request = require('request');
const app = express();
const port = '3005';

app.get('/create', (req, res) => {
  const get_function = req.query.function;
  const get_token = req.query.token;
  const server = req.query.server;
  let function_url = '';
  let check_output = '';

  const options = {
    url: server + '/function?token=' + get_token + '&function=' + get_function
  };

  request(options, (error, response) => {
    if (!error && response.statusCode === 200) {
      function_url = response.body;

      const check_output_options = {
        url: function_url
      };

      var poll = setInterval(function() {
        request(check_output_options, (error, response) => {
          if (response.body.length > 1) {
            check_output = response.body;
            res.end(response.body);
          }
        });

        if (check_output) {
          clearInterval(poll);
        }
      }, 3000);
    } else {
      res.end('\nError connecting with server.\n' + error);
    }
  });
});

app.listen(port, () => {
  console.log('Listening on port: ' + port);
});

To have the sample app create the function and display the output:

curl 'http://127.0.0.1:3005/create?token=1234567890ABCDEFGHJKLMNOP&function=function-sample&server=http://127.0.0.1:3003'

Passing additional container arguments for a function

Depending on the function, you may need to pass additional Docker arguments to the container. This is possible with in the /function GET request with parameter "container_args".

You can’t perform that action at this time.
You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.
Press h to open a hovercard with more details.