Built during the hackathon window
FixRelay was created entirely within the Amazon Developer Hackathon submission period (August 31 – October 23, 2026). All source code, the MCP server, the Strands + Bedrock agent integration, the PostgreSQL schema, the approval-token security model, the React frontend, and the MCP Sentinel open-source CLI were written during the submission window.
Inspiration
Every time a household device breaks, the same frustrating loop begins: pull out the receipt to check the purchase date, search for the manual PDF, wonder if it is even still under warranty, watch an AI chatbot confidently recommend a fix it cannot verify, then realise you still do not know whether calling a technician is covered. The Model Context Protocol opened a cleaner path: expose those domain operations as real callable tools, let an agent compose them, and keep the user in control of what gets written.
What it does
- Device match — matches the device against a structured PostgreSQL inventory
- Evidence retrieval — full-text GIN-indexed search returns source-labelled excerpts. Every excerpt is marked as synthetic demo data or unverified.
- Warranty date window — computes expiry from purchase date and warranty duration; labelled as date arithmetic, not a manufacturer decision.
- Safety-first triage — detects emergency language (sparks, smoke, gas, electric shock) and surfaces safety guidance before troubleshooting.
- Service options — illustrative next steps with an explicit label that no provider has been contacted.
- Human-approved case draft — user approves the exact draft in a confirmation modal; a single-use HMAC token is issued and consumed in a DB transaction.
- MCP Lab — built-in developer panel showing the full Streamable HTTP handshake and raw JSON-RPC responses.
- MCP Sentinel — standalone open-source CLI smoke-tester for any MCP Streamable HTTP server.
How we built it
Frontend: React 19 + TypeScript + Tailwind CSS 4 compiled by Vite 7. The MCP Lab uses a browser-side JSON-RPC client that correctly handles SSE responses, multi-line data: frames, and empty HTTP 202 notification acknowledgements.
Backend: Node.js 22 + Express 5 + TypeScript with Helmet, hostname allowlist (DNS-rebinding prevention), CORS allowlist, rate limiter, and Zod 4 input validation on every route.
Database: PostgreSQL 16 with a GIN full-text index on manuals, idempotent migrations, and a row-level-locked approval token table. Tokens stored only as SHA-256 hashes, expire in 180 seconds.
MCP: Official MCP TypeScript SDK v2, 8 tools with Zod schemas and annotations (readOnlyHint, destructiveHint, idempotentHint). Handler mounted before express.json() — the critical Streamable HTTP ordering requirement.
AWS path: Strands Agents TypeScript SDK with BedrockModel and StreamableHTTPClientTransport. A 45-second Promise.race timeout wraps agent.invoke() so a hung Bedrock call never blocks indefinitely.
Challenges we ran into
MCP protocol version negotiation: Strict equality check on the version header failed silently when the SDK returned the version only in the body. Fixed by switching all three clients (browser, Sentinel CLI, AWS verifier) to startsWith('2025-11-25').
Empty notification acknowledgement: Browser client tried to parse the empty HTTP 202 body for notifications/initialized as JSON, throwing a silent SyntaxError. Fixed by detecting notification messages before attempting to parse.
Approval token binding: Initial token only covered device ID and issue text. A modified summary still consumed the token. Extended the hash to cover deviceId + normalised(issue) + normalised(summary) + sessionId.
Stop-word evidence leak: A query containing only stop words returned the most recent manual excerpts instead of an empty result. Fixed with a pre-filter and regression test.
Accomplishments that we're proud of
- A real, working MCP Streamable HTTP server with 8 tools — not a README-only claim
- Human-in-the-loop approval backed by a cryptographic single-use token that binds to the full normalised draft
- MCP Sentinel: a second, independent open-source client that exposed bugs invisible when only one client exists
- Safety-first triage that puts emergency guidance before any troubleshooting — built into the domain logic, not the UI
- Zero placeholder text in any document or code file
What we learned
- MCP Streamable HTTP has more edge cases than the getting-started guide shows: SSE framing, multi-line data: continuation, notification vs request response handling, and header vs body version placement are all silent failure points.
- Evidence provenance requires deliberate, explicit design at every layer — database column, UI badge, agent system prompt. "Source label" is not the same as "verified."
- Approval boundaries are a security control, not just a UX affordance. The single-use token started as a confirmation mechanism and became a replay-prevention control for the MCP mutation path.
- Timeout discipline matters for AI agents. Without an explicit Promise.race and a 45-second limit, a slow Bedrock response blocks a Node.js worker indefinitely.
What's next for FixRelay - Evidence-Grounded Home Repair Agent
Real licensed product-document ingestion, user identity and per-household tenancy, genuine support-channel integrations, accessibility audit, production observability, and expanding MCP Sentinel to cover authentication and transport-level conformance beyond current smoke-test scope.
Built With
- amazon-bedrock
- docker
- express.js
- model-context-protocol
- node.js
- postgresql
- react
- strands-agents-sdk
- streamable-http
- tailwind-css
- typescript
- vite
- vitest
- zod
Log in or sign up for Devpost to join the conversation.