All Projects → skitsanos → foxx-builder

skitsanos / foxx-builder

Licence: MIT License
ArangoDB Foxx Services in a super intuitive way

Programming Languages

javascript
184084 projects - #8 most used programming language

Projects that are alternatives of or similar to foxx-builder

Gemini
Model Driven REST framework to automatically generate CRUD APIs
Stars: ✭ 138 (+527.27%)
Mutual labels:  api-server, api-rest
dart-express
Express-like HTTP framework written in Dart
Stars: ✭ 34 (+54.55%)
Mutual labels:  api-server, api-rest
Appkernel
API development made easy: a smart Python 3 API framework
Stars: ✭ 152 (+590.91%)
Mutual labels:  api-server, api-rest
Json Server Heroku
Deploy json-server to Heroku & Azure 🆙 🆓
Stars: ✭ 310 (+1309.09%)
Mutual labels:  api-server, api-rest
FSharp.JsonApi
Use F# to create and consume flexible, strongly typed web APIs following the JSON:API specification
Stars: ✭ 20 (-9.09%)
Mutual labels:  api-server, api-rest
Aceql Http
AceQL HTTP is a framework of REST like http APIs that allow to access to remote SQL databases over http from any device that supports http.
Stars: ✭ 68 (+209.09%)
Mutual labels:  api-server, api-rest
Graphql2rest
GraphQL to REST converter: automatically generate a RESTful API from your existing GraphQL API
Stars: ✭ 181 (+722.73%)
Mutual labels:  api-server, api-rest
Spyne
A transport agnostic sync/async RPC library that focuses on exposing services with a well-defined API using popular protocols.
Stars: ✭ 992 (+4409.09%)
Mutual labels:  api-server, api-rest
liuye
柳叶清单开放 API 文档
Stars: ✭ 32 (+45.45%)
Mutual labels:  api-rest, api-service
Aliexpress-API
An Personal API For Fetching Product Details On Aliexpress.com
Stars: ✭ 60 (+172.73%)
Mutual labels:  api-server, api-service
elemental-lowcode
Elemental lowcode development platform.
Stars: ✭ 44 (+100%)
Mutual labels:  api-server, api-rest
ExpressWebJs
ExpressWebJs is a Node FrameWork with expressive and organised syntax that runs on all major operating systems. It provides the starting point for creating your node project, allowing you to focus more on developing your amazing solution. It takes the pain out of development by easing common tasks (Environment Setup, Code Structure, Robust routi…
Stars: ✭ 58 (+163.64%)
Mutual labels:  api-server, api-rest
Webgo
A minimal framework to build web apps; with handler chaining, middleware support; and most of all standard library compliant HTTP handlers(i.e. http.HandlerFunc).
Stars: ✭ 165 (+650%)
Mutual labels:  api-server, api-rest
reedelk-runtime
Reedelk Runtime Platform Community Edition
Stars: ✭ 25 (+13.64%)
Mutual labels:  api-server, api-rest
Asher.Ai
Welcome to the API side of Asher, where all the language processing happens.
Stars: ✭ 20 (-9.09%)
Mutual labels:  api-server, api-rest
Magento-Extra-RESTful
Many more REST resources for Magento's API
Stars: ✭ 32 (+45.45%)
Mutual labels:  api-server, api-rest
nova
Web framework for Erlang.
Stars: ✭ 175 (+695.45%)
Mutual labels:  api-server
maverick
Web API framework with a need for speed
Stars: ✭ 14 (-36.36%)
Mutual labels:  api-server
node-server
(@nestjs refactoring)⚡️My personal website's api server, a RESTful application that powered by @eggjs
Stars: ✭ 17 (-22.73%)
Mutual labels:  api-server
link-preview-api
Backed to provide information for link-prevue vue component
Stars: ✭ 31 (+40.91%)
Mutual labels:  api-rest

foxx-builder

ArangoDB allows application developers to write their data access and domain logic as microservices running directly within the database with native access to in-memory data. The Foxx microservice framework makes it easy to extend ArangoDB’s own REST API with custom HTTP endpoints using modern JavaScript running on the same V8 engine you know from Node.js and the Google Chrome web browser.

Unlike traditional approaches to storing logic in the database (like stored procedures), these microservices can be written as regular structured JavaScript applications that can be easily distributed and version controlled. Depending on your project’s needs Foxx can be used to build anything from optimized REST endpoints performing complex data access to entire standalone applications running directly inside the database.

-- Foxx Microservices

The idea behind this template is to help developers create and run ArangoDB Foxx Microservices with minimal effort and at no time by keeping each API endpoint method handler in its dedicated module.

So, instead of having complex logic describing complete API endpoint functionality, we split it into smaller blocks that are easier to maintain and provide a better overview of the whole application.

Getting started

  1. git clone the whole thing, and you are good to go.
$git clone https://github.com/skitsanos/foxx-builder.git

In package.json in scripts section you will find a number of shortcuts that will help you register your server with foxx-cli, and install or replace Foxx microservice on your server.

  1. Install foxx-cli if you don't have it yet https://github.com/arangodb/foxx-cli#install

  2. Register your ArangoDB server so you can install and replace your Foxx Microservices, for example:

    $foxx server set dev http://dev:sandbox@localhost:8529

By executing this command, we assume that you already created a user dev with password sandbox on localhost server, and we register this server to foxx-cli as dev.

If you define servers using the server commands, a .foxxrc file will be created in your $HOME directory, which is typically one of the following paths:

  • /home/$USER on Linux
  • /Users/$USER on macOS
  • C:\Users\$USER on Windows

This file contains sections for each server which may contain server credentials should you decide to save them.

  1. The example below shows how you can install this Foxx Microservice on dev server to dev database and mount it as /api endpoint.

    $foxx install /api . --server dev --database dev

Folder Structure

There are very few bits required to make your foxx services up and running. The folder structure defined in a way that will help you to have better control over API application architecture with a minimal coding effort from your side.

/builder/
/foxx/
manifest.json
package.json
index.js
setup.js

/builder is the actual Foxx Builder service with all its utils

/foxx is the folder where you will create your API service handlers with convention described below;

manifest.json is a Service Manifest file, as described on https://www.arangodb.com/docs/stable/foxx-reference-manifest.html;

setup.js - Setup script, as described on https://www.arangodb.com/docs/stable/foxx-guides-scripts.html#setup-script;

Inside the /foxx folder will be placed API endpoint path handlers, where every part of the path will be correspondent to a dedicated folder that contains an HTTP method handler.

Out of the box, foxx builder supports following HTTP methods:

  • GET
  • POST
  • PUT
  • DELETE

Creating your first API endpoint

For the sake of convention, let's assume that all our foxx services will be mounted on /api route.

For example, we need to create a handler that will accept all HTTP methods and respond to requests like this:

GET /api/echo
POST /api/echo
PUT /api/echo
DELETE /api/echo

To handle this case, we will add to foxx folder our handler in this way:

/foxx/
--/echo/
----all.js

Another example - we need to add a /api/users route that on GET method will reply with some data and on POST will accept data sent to API and then respond.

/foxx
--/echo
----all.js
--/users
----post.js
----post.js

In other words, file path your API route method handler mirrors your URL path

API endpoint Handler
GET /api/echo /api/echo/post.js
GET /api/users /api/users/post.js
POST /api/users /api/users/post.js
GET /api/users/:id/tasks /api/users/$id/tasks/post.js
GET /api/users/:id/tasks/:task /api/users/$id/tasks/$task/post.js

Parametrized path

Adding parameters to your URL point handling is pretty simple. Probably, you already noticed from the table above, when we require some parameter, we add its name with $ in front of it in our folder name. Just make sure you don't have duplicating parameters.

API endpoint Handler
GET /api/users/:id/tasks/:task /api/users/$id/tasks/$task/post.js
/foxx/
--/users/
----post.js
----post.js
----/$id/
------post.js
------/tasks/
--------post.js
--------post.js
--------/$task/
----------post.js

More on path parameters you can read on https://www.arangodb.com/docs/stable/foxx-getting-started.html#parameter-validation.

Validating payload sent to your endpoint

For HTTP methods like POST and PUT, you need to add to your handler additional property called body. If it is set to null, request payload will be rejected. If you want to enable request body/payload validation, you need to set body property with at least adding schema to it.

body defines the request body recognized by the endpoint. There can only be one request body definition per endpoint. The definition will also be shown in the route details in the ArangoDB's API documentation.

In the absence of a request body definition, the request object’s body property will be initialized to the unprocessed rawBody buffer

//users/post.js

module.exports = {
    contentType: 'application/json',
    name: 'Create new user',
    body: {model: joi.object().required()},
    handler: (req, res)=>
    {
        //your code here
        res.send({result: 'ok'});
    }
};

In the absence of a request body definition, the request object’s body property will be initialized to the unprocessed rawBody buffer.

As defined in ArangoDB's documentation, body accepts the following arguments that foxx-builder takes as object properties.

  • model: Model | Schema | null (optional)

    A model or joi schema describing the request body. A validation failure will result in an automatic 400 (Bad Request) error response.

    If the value is a model with a fromClient method, that method will be applied to the parsed request body.

    If the value is a schema or a model with a schema, the schema will be used to validate the request body and the value property of the validation result of the parsed request body will be used instead of the parsed request body itself.

    If the value is a model or a schema and the MIME type has been omitted, the MIME type will default to JSON instead.

    If the value is explicitly set to null, no request body will be expected.

    If the value is an array containing exactly one model or schema, the request body will be treated as an array of items matching that model or schema.

  • mimes: Array<string> (optional)

    An array of MIME types the route supports.

    Common non-mime aliases like “json” or “html” are also supported and will be expanded to the appropriate MIME type (e.g. “application/json” and “text/html”).

    If the MIME type is recognized by Foxx the request body will be parsed into the appropriate structure before being validated. Currently only JSON, application/x-www-form-urlencoded and multipart formats are supported in this way.

    If the MIME type indicated in the request headers does not match any of the supported MIME types, the first MIME type in the list will be used instead.

    Failure to parse the request body will result in an automatic 400 (Bad Request) error response.

  • description: string (optional)

    A human readable string that will be shown in the API documentation.

Context Utilities

foxx-builder comes with few Context Utilities that you can use to perform basic CRUD operations. Those are get, insert, update and remove.

const {get, insert, update, remove} = module.context;

Arguments used for context operations:

  • get(store, docId) - retrieves document from collection store by document _docId.
  • insert(store, doc) - inserts document docinto collection store. Adding createdOn and updatedOn properties set to current new Date().getTime(). Returns NEW.
  • update(store, docId, doc)- updates collection store document docIdwith new content passed in doc. Updates updatedOn properties set to current new Date().getTime(). Returns NEW.
  • remove(store, docId)- removes document by id docId from collection store. Returns OLD with only _key field in it.
  • runScript(scriptName, params) - launches task with the script defined in `manifest.json, Takes scriptName and params as arguments.

Using context utils

//users/$id/post.js

module.exports = {
    contentType: 'application/json',
    name: 'Get user by id',
    handler: (req, res) =>
    {
        const {id} = req.pathParams;

        const {get} = module.context;
        const doc = get('users', id).toArray();
        res.send({result: doc[0]});
    }
};

Using context utility runScript to send a message into Telegram Channel

The example below demonstrates how to send a message to Telegram Channel. Once we have our Telegram Bot token and Channel Id, we add into scripts folder this piece of code:

//scripts/telegram_chat_message.js

const request = require('@arangodb/request');

const {argv} = module.context;

const token = module.context.configuration.telegramToken;

request.post(`https://api.telegram.org/bot${token}/sendMessage`, {
    json: true,
    body: argv[0]
});

module.exports = true;

Now we can call it, for exmaple, from our middleware:

module.context.use((req, res, next) =>
{
    const {runScript} = module.context;
    runScript('telegram_chat_message', {
        chat_id: '-CHANNEL_ID',
        text: 'hi there from runScript'
    });

    next();
});

Now, on every request, we will receive a message in our Telegram Channel. You can use it, for example, for logging into channel any debug data or stack trace from exceptions fired by your API. Telegram sendMessage params are documented at Telegram Bot API web page.

Session Management

Foxx-Builder provides you with a generic Session Manager middleware that works via Headers Transport. To enable it, add the following lines into your index.js file:

const sessions = require('./sessions/index');
sessions.init();

By default, only /login, /logout, and /password-recovery resources are available without authentication once Session Manager is enabled. If you want to add more endpoints, you can do it in the following way:

const sessions = require('./sessions/index');
sessions.allowedResources = [
    ...sessions.allowedResources,
    '/echo'
];
sessions.init();

Integrations

Proxying requests on Netlify

netlify.toml example configuration

In case if you are using Netlify, here is the example for you how to proxy your URL API calls to ArangoDB Microservices.

[build]
    base = "."
    publish = "./dist"
    functions = "netlify-functions/"

[[redirects]]
    from = "/*"
    to = "/index.html"
    status = 200

[[redirects]]
    from = "/api/*"
    to = "http://{YOUR_HOSTNAME}:8529/_db/{YOUR_ENDPOINT}/api/:splat"
    status = 200
    force = true
    headers = {X-From = "Netlify"}

[[headers]]
    for = "/*"

    [headers.values]
        x-designed-by = "skitsanos, https://github.com/skitsanos"

Before deploying it on Netlify, make sure there are two variables replaced:

  • {YOUR_HOSTNAME} - the hostname where ArangoDb is running
  • {YOUR_ENDPOINT} - endpoint where your flex services are mounted

Also please refer to Exposing Foxx to the browser on ArangoDB documentation web site.

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].