{"id":19325984,"url":"https://github.com/linkorb/exo","last_synced_at":"2025-04-22T20:32:07.255Z","repository":{"id":21277197,"uuid":"24593086","full_name":"linkorb/exo","owner":"linkorb","description":"Exo: FaaS framework supporting externalized Actions and Triggers","archived":false,"fork":false,"pushed_at":"2024-11-13T16:46:48.000Z","size":189,"stargazers_count":1,"open_issues_count":4,"forks_count":4,"subscribers_count":4,"default_branch":"master","last_synced_at":"2025-04-02T04:01:37.812Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/linkorb.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2014-09-29T11:50:12.000Z","updated_at":"2024-10-02T10:47:32.000Z","dependencies_parsed_at":"2024-11-10T02:12:51.738Z","dependency_job_id":"b1a4d5ef-6f66-4ad5-9ce7-795eb68b7611","html_url":"https://github.com/linkorb/exo","commit_stats":{"total_commits":44,"total_committers":2,"mean_commits":22.0,"dds":"0.11363636363636365","last_synced_commit":"ab808f851c68fe12adbfc46d39a847798821bda1"},"previous_names":[],"tags_count":12,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/linkorb%2Fexo","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/linkorb%2Fexo/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/linkorb%2Fexo/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/linkorb%2Fexo/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/linkorb","download_url":"https://codeload.github.com/linkorb/exo/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":250318842,"owners_count":21410999,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-10T02:12:06.705Z","updated_at":"2025-04-22T20:32:06.957Z","avatar_url":"https://github.com/linkorb.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"Exo: FaaS framework supporting externalized Actions and Triggers\n================================================================\n\nInspired by the trends in Serverless / FaaS / Cloud Functions.\n\n## Features:\n\n* Provides a framework to build, call and test reusable, stateless, language agnostic functions (Exo Actions).\n* A language agnostic YAML format to define the metadata of your Exo Actions, specifying their name, description, tags and detailed `input` and `output` schemas.\n* Uses JSON Schema to validate every request, response, input and output.\n* An HTTP end-point server to serve your Exo Actions (exo-server).\n* A Console tool to help build, test and debug your Exo Actions.\n\n## Project status\n\nExo is currently in an experimental phase, and some of the features are under construction.\n\n## core-exo-actions:\n\nCheck out https://github.com/linkorb/core-exo-actions for a range of library of reusable common Exo actions.\n\nTo test it out:\n\n    cp .env.dist .env\n    edit .env # setup your EXO_ACTIONS path\n\n    # List all available actions\n    bin/exo action\n\n    # Inspect a particular action (hello-php)\n    bin/exo action hello-php -i greeting=Hello -i name=Alice\n\n    # Run a particular action (hello-php) with specified input values\n    bin/exo run hello-php -i greeting=Hello -i name=Alice\n\n    # Handle a full JSON request\n    bin/exo request \u003c request.json # load request from stdin\n    bin/exo request request.json # load request from file\n\n\n## Custom actions\n\nIt's easy to implement your own actions, in your language of choice, usually in just a few lines of code.\n\nCheck out the core-exo-actions repository for a set of \"hello world\" examples in PHP, node.js and Bash (most other common languages supported too).\n\nTo use your actions in Exo (CLI, Worker, Server), simply add the path to your actions to the EXO_ACTIONS environment variable.\n\n## Request/Response JSON\n\nExo transforms JSON requests into JSON responses.\n\n### Requests\n\nA request contains:\n\n1. the action name: determines which action to run\n2. an optional set of input variables (may be strings, integers, objects): passed as input to the action\n3. an optional list of output mappings: applied on output variables\n\n```json\n{\n    \"action\": \"random-number\",\n    \"input\": {\n        \"min\": \"100\",\n        \"max\": \"200\"\n    },\n    \"mapping\": {\n        \"result\": \"surprise\"\n    }\n}\n```\n\nYou can execute this request (and pretty-print + color-code it using `jq`) like this:\n\n    bin/exo request \u003c request.json | jq\n\nResponse:\n\n```json\n{\n    \"status\": \"OK\",\n    \"output\": {\n        \"surprise\": \"123\"\n    }\n}\n```\n\n\n### Handling a request\n\nWhen Exo receives the request, it will\n\n0. Find the action information (input/output variables)\n0. Validate the full request against data/request.schema.json\n0. Validate the input variables against the input JSON schema of the requested action\n0. Execute the action\n0. Validate the output variables againt the output JSON schema of the requested action\n0. Optionally apply output variable mapping (renaming)\n0. Validate the full response against data/response.schema.json\n0. Return the response JSON\n\n### Response\n\nExample response:\n\n```json\n{\n    \"status\": \"OK\",\n    \"output\": {\n        \"sentence\": \"Hello, Joe\"\n    }\n}\n```\n\nA response contains a `status` that contains either `OK` or `ERROR`.\n\nIf the action has any output variables, they are specified in the `output` object (optional mappings applied)\n\n## Variables (URLs, Credentials, etc)\n\nYou can variables and secrets to your exo instance as environment variables. Make sure the environment variables are prefixed with `EXO__VARIABLE__`. For example:\n\n    EXO__VARIABLE__MATTERMOST_URL=https://mattermost.example.com/hooks/xyz123abc\n\nYou can now use these variables in your input variables:\n\n    ./bin/exo run mattermost-send-message -i url={{MATTERMOST_URL}} -i channel=@alice -i text=Hi\n\nThe variables are only accessible by the Exo instance, but any request can refer to them. This makes it easy to call actions from client applications (i.e. Camunda) without passing around hardcoded URLs and credentials in your client code, processes, etc.\n\n## Workers\n\nYou can run Exo as a worker. In this mode, Exo waits for requests, executes them, and returns the responses.\n\nTo know where to find requests, you can specify the type of worker, and any options that worker needs to be instantiated.\n\nCurrently the [NATS](https://nats.io/) and [Camunda](https://camunda.com/) workers are available. In the future a Kafka, Rabbitmq, or any other type of worker can be implemented easily.\n\nTo run the worker, simply run:\n\n    bin/exo worker\n\n\n### NATS Worker\n\nThe Camunda worker requires the following environment variables:\n\n* `EXO__WORKER__TYPE`: Worker implementation: `Nats`\n* `EXO__WORKER__NATS__HOST`: Hostname of the NATS server, i.e. `nats.example.com`\n* `EXO__WORKER__NATS__PORT`: Port number of the NATS server, i.e. `4222` (defaut)\n* `EXO__WORKER__NATS__USERNAME`: Username to authenticate with, i.e. `exo`\n* `EXO__WORKER__NATS__PASSWORD`: Password to authenticate with\n* `EXO__WORKER__NATS__SSL__VERIFY_PEER`: Configure steam context SSL option `verify_peer` (defaults to `true`)\n\nYou can now publish requests onto the `exo:request` \"subject\".\n\nNote that the worker expects the payload to be a gzipped JSON string representing a regular Exo request.\n\nIt will use the NATS request/response mechanism to respond to the request with a gzipped JSON string representing a regular Exo response.\n\nTo test you can use the included `nats-request` command to send a request (as JSON over STDIN or by providing a filename), and receive a response on STDOUT. This command uses the worker's NATS environment variables to setup the connection to the NATS server.\n\n* `./bin/console nats-request \u003c request.json` # load request from STDIN\n* `./bin/console nats-request request.json` # load request from filename\n\n### Camunda Worker\n\nThe Camunda worker requires the following environment variables:\n\n* `EXO__WORKER__TYPE`: Worker implementation: `Camunda`\n* `EXO__WORKER__CAMUNDA__URL`: Base URL for the Camunda REST API, i.e. `http://127.0.0.1:8888/engine-rest`\n* `EXO__WORKER__CAMUNDA__USERNAME`: Username to authenticate with, i.e. `exo`\n* `EXO__WORKER__CAMUNDA__PASSWORD`: Password to authenticate with\n\nIt is recommended to create a dedicated user for Exo. This way each task is performed by the appropriate user, ensuring that Camunda permissions and logging are correctly related to Exo.\n\nOnce the worker is running, you can now create \"Service Tasks\" in your processes that trigger Exo actions.\n\nIn the Camunda modeler, create a \"Task\" and use the wrench to turn it into a \"Service Task\".\n\nIn the Properties Panel, set the Implementation as \"External\", and enter a topic. The Topic should always be prefixed with `exo:` followed by the action name you'd like to execute. For example: `exo:smtp-send`.\n\nOpen the Input/Output tab to specify input variables to your action. You can use any process variables and exo variables.\n\nExample inputs:\n\n* `to`: `joe@example.web`\n* `from`: `Exo bot`\n* `subject`: `Hello world!`\n* `body`: `This is a demo`\n* `dsn`: `smtp://user:pass@mail.example.web`\n\nYou can also specify an environment variable called `EXO__VARIABLES__SMTP_DSN` and specify `{{SMTP_DSN}}` as the `dsn` value. This way you don't need to hard-code the SMTP details in your BPMN process.\n\nYou can also specify `${someProcessVariable}` as a value to inject a process variable.\n\nFor actions that have output variables, you may wish to rename those before injecting them back into your process. For example, if a `get-user-data` action returns a `user` object, you may wish to rename this to `customer` (in order not to overwrite or handle multiple `user` variables in your process). This can be achieved by specifying an input variable `\u003euser` with value `customer`.\n\n## Reporting\n\nYou can optionally configure the Exo worker to report heartbeats and request details to an external system using HTTP webhook requests.\n\nExample configuration:\n\n```ini\nEXO_REPORTING_URL=https://my.example.com/reporting/1234567890\n```\n\nExo will append `/heartbeat`, `/success`, `/info`, etc to this URL where applicable, and report details as URL query parameters (i.e. `?message=...`)\n\n## Logging\n\nExo and all it's commands support PSR-3 based logging. To log to a file, specify the following environment variable:\n\n* `EXO_LOG=/var/log/exo.log`\n\nUnder the hood, Exo uses [monolog](https://github.com/Seldaek/monolog), meaning you can easily add [any of it's many handlers](https://seldaek.github.io/monolog/doc/02-handlers-formatters-processors.html) to log to email, slack, graylog, elastic, syslog, etc.\n\nWhen running Exo through `./bin/console` you can pass `-v` to send log output to STDOUT (in addition to the optional log file).\n\n## License\n\nMIT. Please refer to the [license file](LICENSE) for details.\n\n## Brought to you by the LinkORB Engineering team\n\n\u003cimg src=\"http://www.linkorb.com/d/meta/tier1/images/linkorbengineering-logo.png\" width=\"200px\" /\u003e\u003cbr /\u003e\nCheck out our other projects at [linkorb.com/engineering](http://www.linkorb.com/engineering).\n\nBtw, we're hiring!\n\n## Git hooks\n\nThere are some git hooks under `.hooks` directory. Feel free to copy \u0026 adjust \u0026 use them\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flinkorb%2Fexo","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flinkorb%2Fexo","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flinkorb%2Fexo/lists"}