Skip to content

svcho/wegweis

Repository files navigation

Wegweis

Situation-first, grounded, multilingual assistant for Vienna municipal processes.

A newcomer describes their situation in plain language — in English, German, Ukrainian, Arabic, or Bosnian/Croatian/Serbian — and Wegweis returns an ordered, verified checklist of what to do next: offices, documents, appointment links, freshness badges, and a direct NGO handoff when the case needs a human.

Why this exists

Most "chat with the city" tools answer with plausible prose. Newcomers don't need plausible — they need verified, in the right order, with source URLs they can forward to an employer or a school. Wegweis is built around that constraint:

  • Two-stage, prose-free. Stage 1 is a small Anthropic Haiku call in forced tool-use mode that returns closed-vocabulary structured facets (topic, situation tags, language, ambiguity score) — never free text. Stage 2 is a deterministic router that maps those facets to a checklist assembled from author-controlled scenario metadata. Document names, phone numbers, and URLs are never synthesised. Hallucinated enum values are Zod-rejected and the route falls through to a deterministic retrieve baseline.
  • Cached. A 6 h KV-backed prompt cache makes repeat queries return in tens of milliseconds. Only fully grounded answers are cached; clarifier cards, no-coverage fallbacks, and safety-blocked queries are never cached.
  • Situation-first, not topic-first. Users describe their situation ("I just arrived from Ukraine with two children") rather than guessing the right form name. Sequences encode the real journeys; scenarios are their steps.
  • Honest about coverage. When the system doesn't know, it says so and hands off to an NGO list — rather than confidently hallucinating an answer to a stressed newcomer. When the question is genuinely ambiguous, it surfaces a clarifier card rather than guessing.

How it works

          ┌────────────────┐     ┌────────────────────────────────────────┐
          │  apps/web      │     │  apps/api  (Cloudflare Worker)         │
 user ──▶ │  Next.js       │ ──▶ │                                        │
          │  static export │ SSE │   safety regex → cache lookup          │
          │                │ ◀── │     → Stage-1 (Anthropic Haiku, tool)  │
          │  checklist |   │     │     → Stage-2 router (pure)            │
          │  clarifier |   │     │       direct | sequence | clarifier |  │
          │  NGO handoff   │     │       retrieve (embed + rerank)        │
          └────────────────┘     │     → buildChecklist → cache write     │
                                 └────────────────────────────────────────┘
                                       │            │             │
                                       ▼            ▼             ▼
                              ┌────────────┐ ┌────────────┐ ┌────────────┐
                              │  Anthropic │ │ Vectorize  │ │    KV      │
                              │  Haiku 4.5 │ │ bge-m3,    │ │  scenarios │
                              │  enum-only │ │ 1024 cos   │ │  sequences │
                              │  tool-use  │ │ + reranker │ │  ngos      │
                              └────────────┘ └────────────┘ │  cache:*   │
                                                            │  feedback  │
                                                            └────────────┘

   Knowledge base  ──▶  packages/content/scripts/index.ts  ──▶  Vectorize + KV
   (21 scenarios, 7 sequences, 5 locales)

See docs/ARCHITECTURE.md for the full pipeline, the coverage gates, and the content model.

Stack

Cloudflare Workers · Cloudflare Pages · Vectorize · Workers AI (bge-m3 embeddings + bge-reranker-base) · Anthropic Haiku 4.5 (forced tool-use, prompt-cached) · Next.js 15 + Tailwind · pnpm monorepo.

Quick start

pnpm install
cp apps/api/.dev.vars.example apps/api/.dev.vars          # Anthropic key (reserved)
cp apps/api/wrangler.toml.example apps/api/wrangler.toml  # paste KV namespace ID

pnpm dev:api    # Cloudflare Worker on http://localhost:8787
pnpm dev:web    # Next.js frontend on http://localhost:3000

Requires Node 20+, pnpm 9+, Wrangler, and a Cloudflare account with Workers, Vectorize, KV, and Workers AI enabled.

Scripts

pnpm lint:content        # validate KB content (schema, URL allowlist, tags)
pnpm test                # Vitest
pnpm test:e2e            # Playwright
pnpm test:adversarial    # adversarial prompt suite against a deployed preview
pnpm index               # embed content and upsert to Vectorize + KV
pnpm deploy:api          # deploy Worker
pnpm deploy:web          # build + deploy Pages

Repo layout

apps/api         Cloudflare Worker — /api/query, /api/feedback, /api/health
apps/web         Next.js 15 static export — landing, checklist, language switcher
packages/shared  Zod schemas + TypeScript types + pure helpers (shared contract)
packages/content Knowledge base Markdown + indexer + content lint + NGO list
docs/            ARCHITECTURE.md

Contributing content

Scenarios and sequences live in packages/content/. Each scenario is a Markdown file with YAML frontmatter; each sequence references scenarios by ID and can branch on situation tags. The schema is enforced by pnpm lint:content, the URL allowlist is in packages/content/scripts/lint-content.ts, and the situation-tag vocabulary is closed (see packages/content/SITUATION_TAGS.md).

For conventions, invariants, and the agent contract see CLAUDE.md and docs/ARCHITECTURE.md.

License

Licensed under the Apache License, Version 2.0. Content under packages/content/ is authored for the Wegweis project; reuse outside it should credit the source URLs listed on each scenario.

About

A newcomer describes their situation in plain language — in English, German, Ukrainian, Arabic, or Bosnian/Croatian/Serbian — and Wegweis returns an ordered, verified checklist of what to do next: offices, documents, appointment links, freshness badges, and a direct NGO handoff when the case needs a human.

Topics

Resources

License

Stars

Watchers

Forks

Contributors