Skip to main content
Glama
Sharifi2220

OpenQuote Lite

by Sharifi2220

OpenQuote Lite

A small, self-hosted endpoint that lets AI agents send bounded, machine-readable quote requests to a service provider, where a person reviews every request.

Public source alpha: v0.1.1a1. The name is a working title; a commercial quoting product already uses “OpenQuote”. This project is independent and has no affiliation with it. See name and provenance.

person ──asks──▶ personal agent ──request_quote──▶ OpenQuote Lite ──▶ local inbox ──▶ person at the provider
                       ◀── receipt: "received, a person will follow up" (never a quote) ──┘

Why

Personal AI agents increasingly do errands for people: "get me offers for my gas boiler service". Today they phone businesses or scrape contact forms. OpenQuote Lite gives a small business one clean, safe door for exactly one action, the quote request:

  • it has commercial value (most service jobs start with one),

  • it is bounded: it cannot spend money, book a slot or commit a price,

  • a person already reads every request today.

It deliberately builds on existing standards instead of inventing a new protocol: plain HTTPS + JSON Schema, an MCP server for agents, schema.org AskAction for discovery on the website, and the RFC 9727 /.well-known/api-catalog.

Related MCP server: support-agent-mcp

What it does - and refuses to do

Does

Refuses

Accepts requests that match the provider profile (service, postal code, response types)

Accepting prices, confirming orders, booking appointments, carrying payment data: such fields reject the whole request (commitment_not_allowed)

Returns a fixed-wording receipt with is_quote: false, is_commitment: false

Emergencies: there is no emergency urgency; receipts say so

Keeps every request for human review in a local SQLite inbox

Fetching URLs, attachments, or running AI on request text

Idempotent retries, duplicate detection, per-client/contact/global rate limits, a kill switch

Echoing the requester's free text back to agents

Hash-chained pseudonymous audit log; manual/scheduled retention, export and partial erasure commands

Pretending profile data is verified (it is published as self_declared)

Quick start

git clone https://github.com/Sharifi2220/agent-rfq-inbox.git
cd agent-rfq-inbox
python -m pip install -e ".[mcp]"  # Python 3.11+; core has no runtime dependencies
openquote-lite init --dir my-office --base-url http://127.0.0.1:8787
cd my-office
# edit provider-profile.json (services, postal codes, privacy notice URL), then:
openquote-lite check-profile
openquote-lite serve                # HTTP API on 127.0.0.1:8787

Send a request (from another shell):

curl -s -X POST http://127.0.0.1:8787/api/v0/quote-requests \
     -H 'Content-Type: application/json' --data @../examples/quote-request.example.json

Work the inbox:

openquote-lite inbox list
openquote-lite inbox show oqr_...
openquote-lite inbox set oqr_... in_review
openquote-lite inbox set oqr_... follow_up_planned      # or: declined --reason no_capacity
openquote-lite pause --message "Holidays until 7 January"   # kill switch; `resume` to reopen

Connect an MCP client over stdio using examples/mcp-client-config.example.json. The MCP binding exposes get_provider_profile, request_quote, and get_request_status. The request_quote tool requires explicit confirmation that the person asked to send this request and agreed to contact. Streamable HTTP is also supported with openquote-lite mcp --transport streamable-http; secure that transport separately before remote use.

Put the discovery snippet on the provider's website:

openquote-lite jsonld > snippet.html     # <script type="application/ld+json"> with a schema.org AskAction

See the whole flow with four fictional providers: python examples/demo_agent_providers.py.

Architecture

HTTP (WSGI) ─┐
             ├─> validation + policy ─> SQLite inbox ─> local operator CLI
MCP tools ───┘          │                    │
                       └─ fixed receipt     └─ hash-chained audit log

provider-profile.json ─> public profile, JSON-LD and API catalog

The provider owns the profile, SQLite database and instance secret. HTTP and MCP call the same service layer, so both use the same validation, rate limits and non-binding receipts. Staff review and change statuses using the local CLI. See architecture and data flow.

HTTP API

Method

Path

Purpose

GET/HEAD

/.well-known/api-catalog

RFC 9727 API catalog (linkset+json)

GET

/api/v0/profile

provider profile (self-declared)

GET

/api/v0/profile.jsonld

schema.org JSON-LD

GET

/api/v0/openapi.json

OpenAPI 3.1

GET

/api/v0/schemas/{file}

JSON Schemas

POST

/api/v0/quote-requests

submit a request → 201 receipt, 200 on idempotent retry

GET

/api/v0/quote-requests/{id}

status: received, in_review, follow_up_planned, declined, closed

Errors always look like {"openquote": "0.1", "error": {"code": "...", "message": "...", "details": [...]}}. The normative description is in docs/SPEC.md and the JSON Schemas in src/openquote_lite/schemas/.

Deployment notes

  • The built-in server is for local evaluation. No public service is deployed by this repository. A future deployment needs a TLS reverse proxy, controlled X-Forwarded-For handling, abuse controls and operator review. Keep trust_proxy = false unless the proxy is trusted and appends the client address. A WSGI server can call openquote_lite.http_api:app_from_env with OPENQUOTE_CONFIG set.

  • Keep the data directory on a local disk (SQLite WAL does not work on network or cloud-synced folders) and back it up.

  • Run openquote-lite privacy purge --yes regularly (e.g. daily) and store openquote-lite audit head outside the database from time to time.

  • Read SECURITY.md (threat model) and docs/PRIVACY.md before going live.

Development

pip install -e ".[mcp,test]"
pytest

The tests include schema conformance against jsonschema, HTTP and MCP round trips, audit-chain concurrency and the demo. The alpha was tested on Windows with Python 3.11, 3.13 and 3.15; see test evidence for the exact results and GitHub Actions status.

Limits of this alpha

The software does not verify a sender's identity or consent. A request ID grants access to coarse status information. Erasure does not remove all traces from the audit log, SQLite WAL, backups or infrastructure logs. No production security, privacy or legal approval is claimed. Keep real requests off an internet-facing instance until these issues are addressed. See security, privacy, and current limitations.

License

Apache License 2.0. See LICENSE and NOTICE. No package is published to PyPI; install from this repository.

Related MCP Connectors

Related MCP Servers