Note: This document talks about MongoDB support, but it is not yet supported (it only uses a local db (NeDB) at this time. This is somewhat of a design document.
Serverless is a simple task/functions runner that scales easily. It has a unique life cycle different from most (all that I've seen) other FAAS platforms.
- Develop your code in javascript (nodejs)
- Send your code to the server and have it encrypted
- Package the encrypted code from the server into your application
- Send your code with any parameters to the server when it needs to be executed.
The code is never stored on the server, only validated, encrypted, and the key to decrypt it is stored. There are several pros and cons, so you will have to decide if it is right for your project.
- Safe way to bundle code (including any data access keys) into your client application
- Client agnostic
- Scales easily
- More data transfer (each call has to post the code to run)
- Encryption and Decryption consume processing cycles
You can clone the repo and issue npm install
followed by npm start
to get up and running. For more advanced usage, you can configure the server.
The server can be configured to use a common MongoDB instance or a simple local JSON based database. JSON configuration file.
ssl: boolean (true default) port: number (3000 default) sslCert: string (generated default) sslKey: string (generated default) database: object (local database) database.type: local|mongo (local default) database.location: string (where to store data files only with "local" database) database.url: string (only with mongo database) database.username: string (mongo username) database.password: string (mongo password)
The server can be all self contained, it can run on a minimal server configuration. If you wanted to run it across multiple servers, you should configure a common MongoDB instance for data storage.
Install the libraries npm install
Change the salts at the top of index.js. You can change the strings to anything you want.
Then you can either run it once npm run
or use a process monitor like nodemon nodemon index.js
or forever forever index.js
You can add any files you want served to the public
folder in the root folder.
The default username and password for any authorized API calls is admin:admin123
You can use JWT or Basic Auth for authentication. To get a JWT Token, submit a POST request to /login
with the username
and password
and parameters.
Login Example using CURL
curl -X POST \ http://localhost:3000/login \ -d '{ "username": "admin", "password": "admin123" }'
/run
- POST - Unauthorized - Allows POSTed encrypted code
to be executed and the results returned.
/mycalls
- GET|POST|PUT|DELETE - Authorized - Allows a user to create, read, update, and delete calls they own/created. The server does not store the actual encrtyped code, but rather the key to decrypt the code. So it is important to keep the encrypted response.
/calls
- GET|POST|PUT|DELETE - Authorized (Server Admin) - Allows an admin to create/read/update/delete all encryption keys in the database.
/users
- GET|POST|PUT|DELETE - Authorized (Server Admin) - Allows an admin to create/read/update/delete all users in the system (including other admins)
/packages
- GET|POST|PUT|DELETE - Authorized (Server Admin) - Allows an admin to create/read/update/delete allowed NPM packages that user's code can run.
The code is ran as an expressjs call handler. It is function that passes in the request's Request and Response objects as variables reqesut
and response
.
They can be in two formats, as a module, or as function code. Either must contain response.send
.
Module: module.exports = function(request,response){ response.send("Hello world!"); }
Function Code: response.send("Hello world!");
Encrypt Code: curl -X POST \ http://localhost:3000/mycalls \ -H 'authorization: Basic YWRtaW46YWRtaW4xMjM=' \ -d '{ "name": "A simple request proxy", "code": "if (!request.query.url) return response.send('\''A URL is requried as a query parameter'\''); var requestModule = require('\''request'\''); requestModule(request.query.url, function (error, res, body) { if (!error && res.statusCode == 200) { response.send(body); }})" }'
Run Code: curl -X POST \ http://localhost:3000/run \ -d '{ "code": "5b16baaabdeba43379b27b70355579759bc857202f2caf0134a948e373f466dcfc6c8d81061cf7eeb1a6b6e0d5296985d26177db8813528139db8026f2933f17d4cd3dca66ffee33c0cf4dca19e7496b" }'
Lots.
- Implement MongoDB
- Build a more traditional feature of optionally storing the call code for bandwidth or size sensitive applications.
- Find a better way to handle NPM packages
- Support more languages
- ...Make it better 'n stuff...
- Nodemon - Development server reloader
- VM2 - The sandbox that runs the code
- ExpressJS - Server framework for route handling
- JWT - The new cool way to handle authentication without serverside sessions
Fork! Modify! Request Pull!
This project is licensed under the MIT License - see the LICENSE.md file for details