尚未偵測到更新。GitHub 發布版本後會顯示在這裡。
個人 GitHub 帳號下公開儲存庫的擁有者可以登入並驗證所有權,自行管理介紹,無需管理員核准。
登入並產生驗證檔案,在 30 分鐘內將其提交至此儲存庫的預設分支。其他分支或分叉儲存庫中的檔案無效。然後在下方檢查檔案,即可無需管理員核准直接管理專案。請保留檔案以維持管理權限。
如需登入,將前往登入頁面。登入後請回到此處,再次點擊所選的驗證按鈕。
在專案資料夾中執行 /nomorevibe verify,即可驗證所有權並自行管理介紹。
一分鐘完成驗證Opiniated SvelteKit/Flowbite LLM frontend to LangGraph Server's API.
翻譯準備中
取自儲存庫 README
正在載入完整 README。
檢視完整 README ↗Opinionated SvelteKit-based LLM frontend for LangGraph agents, served by Aegra — an open-source, self-hosted Agent Protocol server.
https://svelte-langgraph-demo.synergyai.nl/
This repo uses Proto with .prototools to pin moon (^1.41.8) and pnpm. Moon installs and manages the rest of the toolchain (Python 3.12, Node.js, uv).
Install Proto — see the Proto installation guide, or:
bash <(curl -fsSL https://moonrepo.dev/install/proto.sh)
Clone the repo and install pinned tools:
git clone https://github.com/synergyai-nl/svelte-langgraph.git
cd svelte-langgraph
proto install
Ensure PATH includes Proto and uv:
export PATH="$HOME/.proto/bin:$HOME/.local/bin:$PATH"
Add that line to your shell profile (e.g. ~/.zshrc) for persistence.
First-time setup (if needed):
moon setup
Do not run pnpm install or pnpm dev at the repo root — use moon tasks instead (see Getting Started).
The monorepo uses a single .env file at the root to configure both frontend and backend. Copy the example file and update it with your values:
cp .env.example .env
The .env file is organized into sections:
Common Variables:
AUTH_OIDC_ISSUER - Your OIDC provider's issuer URL (e.g., http://localhost:8080 for local mock)Backend Variables:
OPENAI_API_KEY - Your OpenAI-compatible API key (e.g., OpenAI, OpenRouter)OPENAI_BASE_URL - OpenAI-compatible API base URL (optional, defaults to OpenAI)CHAT_MODEL_NAME - OpenAI-compatible model to use (defaults to gpt-4o-mini)DATABASE_URL - PostgreSQL connection URL for Aegra. Leave unset for the common setups: moon backend:dev on the host defaults to localhost:5432/aegra (what moon backend:docker-postgres serves), and docker compose up points at the compose postgres service automatically. Set it only for your own/external database server. If you set up before this changed, see the caveat under Production — docker compose up now honors an explicit DATABASE_URL instead of overriding itAUTH_TYPE - Must be custom to enable OIDC authentication and per-user isolation (Aegra defaults to noop, which disables auth)OTEL_TARGETS - Optional OpenTelemetry tracing fan-out (e.g. LANGFUSE, with LANGFUSE_* keys)Frontend Variables:
AUTH_TRUST_HOST - Enable auth trust host (set to true for development)AUTH_OIDC_CLIENT_ID - Your OIDC client ID (e.g., svelte-langgraph)AUTH_OIDC_CLIENT_SECRET - Your OIDC client secretAUTH_SECRET - Random string for session encryption (generate with npx auth secret)PUBLIC_LANGGRAPH_API_URL - URL of your Aegra server (typically http://localhost:2026)PUBLIC_SENTRY_DSN - Public DSN for Sentry error tracking (optional)This application supports multiple OpenAI-compatible providers. Configure your preferred provider using the environment variables above.
To use OpenAI directly (no additional configuration needed):
# .env
OPENAI_API_KEY=your_openai_api_key
# OPENAI_BASE_URL not needed for OpenAI (uses default)
CHAT_MODEL_NAME=gpt-4o-mini # Default OpenAI model
Popular OpenAI models:
gpt-4o-mini - Fast, cost-effective model (default)gpt-4o - Most capable modelgpt-3.5-turbo - Legacy modelOpenRouter provides access to multiple AI models including free options:
# .env
OPENAI_API_KEY=your_openrouter_api_key
OPENAI_BASE_URL=https://openrouter.ai/api/v1
CHAT_MODEL_NAME=x-ai/grok-4-fast:free # Free Grok model
Popular OpenRouter models:
x-ai/grok-4-fast:free - Free Grok modelmeta-llama/llama-3.2-3b-instruct:free - Free Llama modelanthropic/claude-3.5-sonnet - Claude 3.5 Sonnet (paid)For local AI models using Ollama:
# .env
OPENAI_API_KEY=ollama # Can be any value for local usage
OPENAI_BASE_URL=http://localhost:11434/v1
CHAT_MODEL_NAME=llama3.2 # Your local Ollama model
The frontend shows LLM reasoning/thinking tokens in a collapsible block above AI messages, when the model provides them. Reasoning is picked up from additional_kwargs.reasoning_content (OpenRouter) and from {type: "reasoning"} / {type: "thinking"} content blocks (langchain v1 standard / Anthropic-native).
By default, CHAT_MODEL_NAME is routed through the generic OpenAI-compatible path (OPENAI_API_KEY/OPENAI_BASE_URL), unchanged from before. To use a langchain-native provider integration instead, prefix CHAT_MODEL_NAME with a provider known to init_chat_model (e.g. openrouter:deepseek/deepseek-r1); it's then routed through that provider's integration instead of the generic path. Provider-specific options go in CHAT_MODEL_KWARGS (JSON) and are forwarded to init_chat_model as keyword args (with defaults like temperature=0.9 applied; reserved keys like model/model_provider are rejected).
To enable reasoning output via OpenRouter — the openrouter: prefix and API key alone are not enough, OpenRouter only emits reasoning tokens when explicitly requested via the reasoning key in CHAT_MODEL_KWARGS:
# .env
OPENROUTER_API_KEY=your_openrouter_api_key
OPENROUTER_API_BASE=https://openrouter.ai/api/v1
CHAT_MODEL_NAME=openrouter:deepseek/deepseek-r1
CHAT_MODEL_KWARGS="{\"reasoning\": {\"effort\": \"medium\"}}"
CHAT_MODEL_KWARGS must be valid JSON, which requires double-quoted keys/strings. Wrap the value in double quotes and escape the inner ones as above; an unquoted value (CHAT_MODEL_KWARGS={"reasoning": ...}) fails to parse when loaded via moon's envFile task option (used by moon backend:dev/moon backend:up) and breaks on word-splitting if the variable is ever exported as a shell variable instead.
Caveat: the generic OpenAI-compatible path (ChatOpenAI pointed at OpenRouter via OPENAI_BASE_URL) drops reasoning tokens entirely — a known langchain limitation (langchain#34328). Reasoning display requires the openrouter: prefix above. Other langchain-integrated providers can expose reasoning the same way once their integration package is added to the backend dependencies.
Install pinned tools (from the repo root):
proto install
Configure environment:
cp .env.example .env
Edit .env with your API keys and auth settings (see Configuration above).
Start the full local stack:
moon :dev :oidc-mock
This starts the frontend, LangGraph backend, and OIDC mock provider with hot reload:
http://localhost:5173http://localhost:2024http://localhost:8080For local development and testing, the project includes a mock OIDC provider using oidc-provider-mock. This lightweight Python-based mock server simulates a real OIDC provider, allowing you to develop and test authentication flows without needing to set up a full OAuth2/OIDC provider.
The OIDC mock is not started by moon :dev alone — include :oidc-mock (as above) or run moon backend:oidc-mock in a separate terminal alongside moon :dev.
What it does:
.well-known/openid-configuration):oidc-mock target (see below)Configuration:
http://localhost:8080svelte-langgraph)secret)test-user (subject claim in JWT)The following command ensures dependencies are installed and starts dev servers for frontend, backend, Docker Postgres, and OIDC mock provider, with hot reload:
moon :dev :docker-postgres :oidc-mock
This automatically starts:
http://localhost:5173http://localhost:2026backend:docker-postgres task, which runs the compose postgres helper servicehttp://localhost:8080 (for local authentication):docker-postgres is the Docker-based Postgres helper — include it if you want Docker to manage Postgres for you. If you're running your own local PostgreSQL server instead, omit it and run moon :dev :oidc-mock.
Make sure to configure your .env file to point to the OIDC mock provider (see Configuration section above).
The backend only needs a reachable PostgreSQL server (≥ 13) — Docker isn't required:
aegra. With the default postgres:postgres@localhost:5432 credentials you don't need to set anything; otherwise point DATABASE_URL in .env at your serveraegra_e2e database is created/dropped automatically before each run by apps/backend/scripts/reset_test_db.py, configured via TEST_DATABASE_URL in .env.e2e — the role in that URL needs the CREATEDB attribute (or superuser) to drop/recreate it: ALTER ROLE <role> CREATEDB;pgvector is optional — only needed if Aegra's store semantic search is ever enabledRun all checks (linting, type checking, formatting, building, unit and E2E tests):
moon check --all
This requires Docker to be running for the backend Docker image build, and a running PostgreSQL server for the E2E tests — start one first with moon backend:docker-postgres unless you run your own.
On machines without Docker, run the non-Docker equivalent instead — with a local PostgreSQL server running:
moon check backend frontend
moon e2e:test
The backend uses LangGraph for AI workflow orchestration with the following key dependencies:
The frontend is built with modern web technologies:
End to end tests are written using Playwright with fixtures and page object models. They live in their own project in e2e/.
They can be run with:
moon e2e:test
Or, interactively, with:
moon e2e:test-ui
To run a Docker build of the project, use Docker Compose:
docker compose build
To run it:
docker compose up [--build]
This starts the frontend, the backend (Aegra), and PostgreSQL. The backend can also be built and run on its own:
moon backend:up
The frontend container receives an allowlisted set of variables interpolated from the root .env (auth and PUBLIC_* settings — backend secrets like API keys and DATABASE_URL are deliberately not passed to it). PUBLIC_LANGGRAPH_API_URL is consumed by the browser, not the container; it defaults to http://localhost:2026, which works when your browser runs on the Docker host. Point it elsewhere for any other setup:
PUBLIC_LANGGRAPH_API_URL=https://backend.example.com docker compose up --build
DATABASE_URL can be overridden the same way, to point the backend at an external or managed Postgres server instead of the bundled postgres service. It must be reachable from inside the backend container — a localhost URL there means the container itself, not your host.
A host-local Ollama (or other OpenAI-compatible provider bound to the Docker host) must be addressed as OPENAI_BASE_URL=http://host.docker.internal:11434/v1. Compose wires extra_hosts: host.docker.internal:host-gateway, so this resolves on Linux Docker Engine too (>= 20.10) — Docker Desktop provides it natively.
Caveat: if your root .env already sets DATABASE_URL=postgresql://postgres:postgres@localhost:5432/aegra (the old shipped default), docker compose up now honors it instead of silently overriding it — and that localhost resolves to the container itself, not Postgres. Comment out the line, or change the host to postgres, to fix it.
The backend image bakes in AUTH_TYPE=custom, so it always requires OIDC bearer tokens — it cannot silently fall back to Aegra's unauthenticated noop mode. Because every request must carry an Authorization header (no cookies), the API serves wildcard CORS, the standard posture for token-authenticated APIs. Operators who additionally want to pin allowed origins can mount their own Aegra config and point AEGRA_CONFIG at it, e.g. AEGRA_CONFIG=/etc/aegra/aegra.json with a concrete http.cors.allow_origins list.
This project uses Paraglide-JS for type-safe internationalization. Paraglide offers a developer-friendly approach where you can:
All translations are stored in apps/frontend/messages/:
Each file contains key-value pairs for all UI text:
{
"$schema": "https://inlang.com/schema/inlang-message-format",
"hello_world": "Hello, {name}!",
"local_name": "English"
}
The local_name key is special - it defines how each language refers to itself in the language switcher.
apps/frontend/messages/ (e.g., fr.json for French)en.json and translate all valuesapps/frontend/project.inlang/settings.json:{
"locales": ["en", "nl", "hi", "fr"]
}
That's it! The language will automatically appear in the language switcher with the name specified in local_name.