Files
n8n-openai-adapter/lib/n8n_openai_adapter/application.ex
T
hermes-agent 5197b6ece6 OpenAI-compatible adapter for n8n chat agents (Elixir)
Exposes self-hosted n8n chat agents behind /v1/chat/completions and
/v1/models. Model -> n8n webhook routing via a GenServer registry, so
multiple agents map to multiple models. Plug + Bandit, req for the
n8n webhook call, Bearer auth (ADAPTER_API_KEY). Ships a flake.nix
(beamPackages.mixRelease) so it can be consumed as a NixOS flake input.
2026-09-09 21:43:21 +00:00

45 lines
1.4 KiB
Elixir

defmodule N8nOpenaiAdapter.Application do
@moduledoc """
OTP application entrypoint. Starts the AgentRegistry (model -> n8n webhook
mapping, loaded from config) and the Bandit HTTP server behind the Plug router.
"""
use Application
@impl true
def start(_type, _args) do
children = [
{N8nOpenaiAdapter.AgentRegistry, configured_agents()},
{Bandit, plug: N8nOpenaiAdapter.Router, scheme: :http, port: port()}
]
opts = [strategy: :one_for_one, name: N8nOpenaiAdapter.Supervisor]
Supervisor.start_link(children, opts)
end
defp port, do: String.to_integer(System.get_env("PORT", "8000"))
defp configured_agents do
# Prefer application env (:agents) — settable from config/*.exs, which loads
# before the app boots. Falls back to the AGENTS env var (JSON map of
# model -> n8n chat webhook URL).
case Application.fetch_env(:n8n_openai_adapter, :agents) do
{:ok, agents} when is_map(agents) ->
agents
_ ->
case System.get_env("AGENTS") do
nil ->
# single agent from old N8N_WEBHOOK_URL / MODEL_NAME env
model = System.get_env("MODEL_NAME", "default-agent")
case System.get_env("N8N_WEBHOOK_URL") do
nil -> %{}
webhook -> %{model => webhook}
end
json ->
Jason.decode!(json)
end
end
end
end