The full upstream README, mirrored here for reference. Install config, tool schemas, adoption signals, and an original overview live on the Namaste America listing page.
Agent-first, agent-only data layer for the Indian-American diaspora. Phase 1: Indian restaurants (USA). This repo is the walking skeleton from the architecture blueprint:
get_indian_restaurants,
get_restaurant_details, search_restaurants_by_text, find_unclaimed_restaurants,
draft_claim_outreach, submit_correction), temple capabilities
(get_indian_temples, get_temple_details, search_temples_by_text) and grocery
capabilities (get_indian_groceries, get_grocery_details, search_groceries_by_text)
professional capabilities (get_indian_professionals, …), salon capabilities
(get_indian_salons, …), and a cross-vertical search_all that searches every vertical
at once (each result tagged with its vertical).pgvector for future embedding search) via Docker Compose.The hosted server is remote (no install) over streamable‑HTTP:
https://namasteamerica.us/mcp (transport: streamable-http, auth: none, read‑only)https://namasteamerica.us/.well-known/mcp.json · Docs: https://namasteamerica.us/for-agentsTools (per vertical: restaurants, temples, groceries, professionals, salons, events, apparel,
sweets, studios, services, community, legal, education, real estate, finance):
get_indian_<category>, search_<category>_by_text, get_<category>_details, and a cross‑vertical
search_all. Each result is JSON with address, geo, hours, contact, ratings, and languages.
Publishing to the official MCP registry: the manifest is
server.json(namespaceus.namasteamerica, verified via DNS). Install the CLI (mcp-publisher), authenticate the domain (mcp-publisher login dns --domain namasteamerica.us, then add the TXT record it prints), and runmcp-publisher publish.
Low-risk new inserts are auto-applied (configurable); updates to claimed/featured listings are routed to the human approval queue.
Requires Docker Desktop and Python 3.11+.
| Command | Purpose |
|---|---|
init-db | Apply SQL migrations (extensions, tables, indexes). |
scrape --metro <name> | Run the OSM scraper for a metro bbox into restaurant_raw. |
process | Clean/score unprocessed raw rows; auto-apply low-risk, queue high-risk. |
approvals | List pending approval-queue items. |
approve <id> / reject <id> | Resolve an approval item. |
outreach [--limit N] | Draft claim outreach for unclaimed restaurants (creates claim links + messages). |
verify-claim <token> | Owner-side: verify a claim token and take ownership. |
agents | List the registered autonomous agents. |
agent <name> | Run one agent now (audited in agent_runs). |
agents-loop [--once] | Run the scheduler (worker loop over due agents). |
query [--city/--text/--lat --lng/--id/...] | Call the MCP tool functions from the terminal. |
seed | Load fictional seed restaurants for local testing (no scrape needed). |
enrich | Backfill region/dietary cultural tags on under-tagged restaurants. |
deactivate-stale [--days 60] | Mark unclaimed listings not seen recently as inactive. |
approval-digest | Human-readable summary of the pending approval queue. |
feedback --id N --field F --value V | Submit a field correction (applied by the feedback agent). |
scrape --metro usa | Nationwide sweep (occasional; slower than a single metro). |
feature --id N [--days 30 | --permanent] | Mark a paid featured listing. |
unfeature --id N | Remove a featured listing. |
backfill-embeddings [--all] | (Re)compute embeddings for canonical rows. |
stats | Row counts and coverage summary. |
feature/unfeature) — a paid tier; effectively-featured rows
(flagged and within their featured_until window) surface first in every tool result./stripe/webhook) auto-features them. Disabled
until STRIPE_SECRET_KEY is set (then it's pay-per-sale, no monthly fee). See DEPLOY.md..env (see .env.example) and the Outreach Agent will auto-send claim emails to
restaurants that have a public email; otherwise it stays draft-only.Coverage spans 15 metros (Bay Area, NYC/NJ, Dallas, Houston, Chicago, LA, Seattle, Atlanta,
Phoenix, Austin, Boston, Philadelphia, Raleigh, Detroit, Central NJ) plus an on-demand
nationwide sweep (scrape --metro usa).
WhatsApp outreach is delivered as free click-to-send wa.me links (message pre-filled);
true auto-send WhatsApp needs a paid API and is intentionally not used.
Then exercise the MCP tools (e.g. get_indian_restaurants near the Bay Area, or
search_restaurants_by_text "vegetarian dosa").
Records are optimized for agent retrieval:
description per record (e.g. "Saffron House is a Gujarati Indian
restaurant in Edison, NJ. Offers vegetarian, jain options. Price: $$.") — generated from
the structured fields, returned to agents, and used as the text that gets embedded.city/state are filled offline from coordinates
(reverse_geocoder), so "near me / in " queries work for every record.tags (e.g. biryani, dosa, halal, delivery, takeout,
outdoor-seating, wheelchair-accessible, wifi, cards-accepted, organic) — derived
from names and rich OSM attributes; agents filter with tag=..., and they boost embedding
recall + appear in the description ("Amenities: …").open_now — opening_hours are parsed into structured per-day intervals; each result
carries an open_now flag (true/false/null) and the tools accept an open_now=true filter,
enabling "what's open near me right now".search_*_by_text ranks by embedding cosine distance (pgvector <=>), falling back to
trigram. Providers (EMBEDDING_PROVIDER):
hashing (default) — feature-hashing, zero extra deps; lexical.fastembed (recommended, prod default) — real semantic embeddings via
BAAI/bge-small-en-v1.5 (384-dim, ONNX, no torch). The Docker image includes it and the
prod compose defaults EMBEDDING_PROVIDER=fastembed; after deploying run
python -m indo_usa_mcp.cli enhance-data once to re-embed existing rows. Set
EMBEDDING_PROVIDER=hashing if the VPS is RAM-constrained.sentence_transformers — all-MiniLM-L6-v2 (heavier, pulls torch).none — trigram only.enhance-data (re)generates descriptions, fills geocoding, and re-embeds existing rows —
run it after enabling a new embedder. New records get all of this automatically on ingest.
After claiming, owners get an edit page (/manage?token=...) to update their phone,
hours, menu, price, dietary tags, etc. — changes go live immediately and are protected from
scraper overwrites (scraper updates to claimed listings route to the approval queue).
Stale listings not re-seen for 60 days are auto-deactivated (is_active=false) and
reactivated if they reappear in a later scrape.
The Outreach Agent finds unclaimed restaurants (skipping anything with an open claim or
contacted within OUTREACH_COOLDOWN_DAYS), creates a single-use claim token + link, and
drafts an honest, opt-out-friendly message per restaurant. Messages are not auto-sent —
delivery needs channel integrations, and chains / featured / high-value targets are flagged
requires_human. Once an owner verifies, restaurants.is_claimed flips to true and future
scraper updates to that listing are routed to the approval queue. Agents can drive this via
the find_unclaimed_restaurants and draft_claim_outreach MCP tools.
Each agent wraps a pipeline step, is idempotent, and writes a full audit row to
agent_runs (errors captured, never half-written canonical data).
| Agent | Does |
|---|---|
discovery | Reports metro coverage and proposes scrape targets. |
scraper | Runs every scraper across every metro into restaurant_raw. |
cleaner | Processes raw → canonical via clean/score/approval. |
outreach | Drafts claim outreach for eligible unclaimed restaurants. |
monitoring | Detects anomalies (backlogs, scraper failures, stale data) → agent_alerts. |
submission | Submits the MCP to directories (manual stub for now). |
Two independent public scrapers feed the pipeline: osm_overpass (OpenStreetMap, ODbL)
and wikidata (Wikidata SPARQL, CC0). Pick one with scrape --source <name>; the
Scraper Agent runs both.
An independent vertical (Hindu/Sikh/Jain places of worship) sharing the same pipeline,
agents, embeddings and deployment — per the blueprint's "independent verticals, shared
infra" principle. Own table (temples), own OSM scraper (amenity=place_of_worship +
religion), own agents (temple_scraper, temple_cleaner), own MCP tools. Cultural
enrichment infers deity (Venkateswara, Krishna, Lakshmi…) and region (Punjabi for
Sikh, Gujarati for Swaminarayan, Telugu for Venkateswara…) from the name.
Same recipe as temples — independent groceries table + OSM scraper (grocery-type shops
whose name signals Indian groceries: Patel, India, Apna, Swad, Masala…) + own agents
(grocery_scraper, grocery_cleaner) + 3 MCP tools. Infers store_type and region_tag.
The web app (:8080) now serves three audiences:
/, /claim, /manage, /upgrade (existing)/admin/*, password-gated) — overview KPIs, cross-vertical data control
(browse/search/edit/feature/deactivate/soft-delete), Geography drill-down
(country → state → city, click to filter records), Quality control (records flagged for
missing region/contact/geo/city + duplicate groups, with a one-click city/state normalizer),
approvals & feedback queues, agents (last-run health, run-now, resolve alerts),
Traffic (every MCP tool call logged: by tool / agent-client / day, plus most-shown
listings), payments, and reports. Set ADMIN_PASSWORD to enable; blank disables it./portal/*) — owners sign in via passwordless magic-link email and
manage all their listings across verticals (edit, featured status, upgrade).Daily report: the reporting agent computes a health + growth snapshot nightly into
daily_reports, shows it on /admin/reports, and emails it (via SMTP) to REPORT_EMAIL.
Run on demand with python -m indo_usa_mcp.cli report.
Security: enable HTTPS (the Caddy
tlsprofile) and set a strongADMIN_PASSWORD+ randomSECRET_KEYbefore exposing/adminpublicly.
Indian-American healthcare professionals — doctors, dentists, clinics, pharmacies — found
from OSM healthcare amenities + an Indian-name signal (surnames / Ayurveda). Same recipe as
the other verticals: own professionals table, scraper, agents (professional_scraper,
professional_cleaner), 3 MCP tools, plus profession_type/speciality filters. Because
name-matching is heuristic, each record carries a confidence_score and the admin Quality
view helps curate false positives.
Indian beauty salons — eyebrow threading, henna/mehndi, hair, bridal — from OSM hairdresser/beauty shops with a strong South-Asian service/name signal. Same recipe; tags capture services (threading, henna, bridal…). Best OSM coverage of the verticals so far.
Indian-American community events (festivals, garba, concerts, puja). Fully automated —
an agent auto-discovers iCal feeds by scanning the websites of orgs already in the
database (temples first) for calendar links, and agents ingest events from those feeds plus
any in EVENT_ICAL_FEEDS. The
cleaner auto-approves high-confidence events and queues the rest under Admin → Events
for one-click approval (no manual entry). Past events are kept, not deleted — they're
date-filtered out of upcoming results (get_indian_events returns upcoming by default;
include_past=true for history) and an 18-month retention purges very old ones.
Point any MCP client (Claude Desktop, etc.) at:
The full hosted stack — Postgres + MCP server (HTTP) + agent worker — is in docker-compose.prod.yml:
streamable-http on :8000.Put a TLS-terminating reverse proxy (Caddy/nginx/Traefik) in front of :8000 for HTTPS,
and add a firewall + scheduled pg_dump backups. The MCP endpoint is https://<host>/mcp.
The standard visual way to exercise the tools:
is_featured is an explicit, visible flag.Phase 1 is implemented and runs end-to-end: schema + versioning + approval queue, the pipeline, two scrapers (OSM + Wikidata), all 5 MCP tools, semantic (pgvector) search, outreach & claiming, six autonomous agents with a scheduler, seed fixtures, and a hosted deployment stack. Remaining "last mile": real outreach channel delivery, a claim web page, the Approval-Assistant + Feedback agents, monetization logic, and production hardening (HTTPS, backups). Each future vertical (temples, events, groceries…) gets its own table/scrapers/tools but shares this infra.