Files
patch-pilot/README.md
T
2026-05-23 13:58:27 +02:00

10 KiB

PatchPilot

PatchPilot

Repair café tool inventory & AI repair assistant.

Next.js React TypeScript Material UI License

PatchPilot is a small but complete web app for a repair café. It combines a tool inventory with a reservation system and an AI assistant that helps diagnose problems, suggest repair approaches and answer questions about the tool database. It's designed to feel like a real product, not a wireframe.


🏆 About this project

This project was built during the Jade Hochschule AI Hackathon in May 2026 and reached 3rd place as a team submission.

The challenge: vibe-code an app idea around sustainability and/or health in a single day. A digital companion for repair cafés fits squarely in the sustainability bucket — repair cafés extend the lifespan of broken things instead of sending them to landfill, and the bottleneck is almost always tool access, expertise and coordination. PatchPilot tries to chip away at all three at once.


Features

For everyone

  • Tool inventory — 12 tools across 8 categories with search, filter, location, training requirements and rental period.
  • Reservation flow — modal with date picker, live availability calendar, validation against the maximum rental period.
  • AI assistant (RepairBuddy) — describe a problem in plain language and get a structured, Markdown-formatted answer. Supports image uploads for visual diagnosis.
  • Multi-language — German / English with browser locale detection and persistent choice.
  • Dark / light mode — with system-preference detection.
  • Responsive — full mobile layout with drawers, full-screen modals and collapsing sidebars.

For admins

  • Dashboard with live stats (tools, users, active reservations, pending requests).
  • Pending-requests banner with one-click approve / reject.
  • Tool CRUD — add / edit / delete with category, emoji, location, training requirements.
  • Knowledge base — upload manuals that are surfaced to the AI as context.
  • Reservation calendar — month / week / day view, colour-coded by status.

Behind the scenes

  • Role-aware AI — the system prompt is built per request and injects a live snapshot of tools + reservations. Admins see borrower names; regular users only see availability & return dates. Same backend, different views.
  • Vision via OpenAI-compatible API — image uploads are auto-downscaled (>2.5 MB → 1600 px JPEG) and sent as multimodal content.
  • Mock fallback — works without an API key. The chat engine drops back to a deterministic local responder if GEMINI_API_KEY is missing or the upstream fails.

🚀 Getting started

1. Clone & install

git clone git@github.com:MrFrostDev/patch-pilot.git
cd patch-pilot
npm install

2. Configure the AI provider

PatchPilot expects an OpenAI-compatible chat endpoint. It has been tested with Requesty routing to Google Gemini 3 Flash, but any OpenAI-compatible provider works (OpenRouter, LiteLLM, vLLM, your own gateway…).

Copy the example file and fill in your credentials:

cp .env.example .env.local
REQUESTY_BASE_URL=https://router.requesty.ai/v1
GEMINI_API_KEY=your-key-here
PATCHPILOT_MODEL=vertex/gemini-3-flash-preview   # optional, this is the default

If you leave the variables empty, PatchPilot uses its built-in mock engine — useful for demos without burning API credits.

3. Run

npm run dev

Open http://localhost:3000.

4. Sign in

Three demo accounts are bundled in the mock database:

Username Password Role Notes
admin admin Administrator Full access, tool CRUD, reservation actions
staff staff Staff Has drill + soldering training
guest guest Guest Read-only, no training

🛠 Tech stack

Layer Choice
Framework Next.js 13 (App Router)
Language TypeScript (strict-ish, strict: false for hack speed)
UI library Material UI v5 with custom theme
Animation Framer Motion 12
State Zustand 4 with persist middleware (localStorage)
Calendar FullCalendar (dayGrid, timeGrid, interaction)
Icons lucide-react
Markdown react-markdown + remark-gfm
AI API OpenAI-compatible (e.g. Requesty → Gemini 3 Flash, multimodal)
Fonts Inter via next/font/google

📁 Project structure

src/
├── app/
│   ├── api/chat/route.ts        # Chat API — routes to live LLM or mock
│   ├── globals.css              # Custom properties, FullCalendar theming
│   ├── layout.tsx               # Metadata, font, providers shell
│   ├── page.tsx                 # AppBar + drawer + view switch + login
│   └── providers.tsx            # Client-side providers (theme, i18n)
├── components/
│   ├── AIInput.tsx              # Single-shell chat input with attachments
│   ├── AdminCalendar.tsx        # Admin reservation calendar
│   ├── AdminDashboard.tsx       # Stats + CRUD + approvals
│   ├── AnimatedBackground.tsx   # GPU-composited blob background
│   ├── AvailabilityCalendar.tsx # In-modal availability view
│   ├── ChatSidebar.tsx          # Session list with rename / delete
│   ├── ChatWindow.tsx           # Messages, scroll-to-bottom, mode badge
│   ├── HeroSection.tsx          # Landing hero with AI input
│   ├── Logo.tsx                 # Logo component (used everywhere)
│   ├── MarkdownMessage.tsx      # Styled Markdown renderer
│   ├── Onboarding.tsx           # Interactive 4-step walkthrough
│   ├── ReservationModal.tsx     # Booking modal with sticky footer
│   └── ToolCard.tsx             # Inventory card with hover shine
├── config/theme.ts              # MUI theme (light/dark, glassmorphism)
├── services/
│   ├── auth-store.ts            # Mock auth + persist
│   ├── chat-engine.ts           # System prompt builder + live + mock + multimodal
│   ├── chat-store.ts            # Sessions, messages, attachments
│   ├── color-mode.tsx           # Theme provider with localStorage
│   ├── file-utils.ts            # Image → DataURL with auto-downscale
│   ├── i18n.tsx                 # DE/EN dictionary + provider
│   ├── mock-data.ts             # Initial tools, users, manuals
│   ├── reservation-store.ts     # Reservations + status updates
│   └── tools-store.ts           # Tool CRUD with persist
└── types/index.ts               # Tool, User, Reservation, Category types

🧠 How the AI integration works

  1. The system prompt is built per request (buildSystemPrompt in chat-engine.ts).
  2. The current user role (admin → "Verwalter", everyone else → "Nutzer") and a Markdown table of the live tool database (with current reservations) are injected. This is essentially poor-man's RAG without an embedding store.
  3. Multimodal: if the user message has image attachments, the request payload is sent as an OpenAI-style content array ({type: 'text'}, {type: 'image_url'}).
  4. Role-aware redaction is enforced by the prompt, not by post-processing — admins see borrower names, regular users see only availability + due date. The same backend data, two views.
  5. If the upstream fails (or no key is configured), the request transparently falls back to a deterministic local mock responder so the demo never breaks.

The system prompt itself is based on a "RepairBuddy" specification that prioritises safety: emergency redirection to 112 / utility hotlines, no step-by-step guides for gas / mains electricity / load-bearing structures, honest uncertainty markers.


🖼 Image upload

  • Up to 5 files per message
  • Images > 2.5 MB are automatically downscaled to max 1600 px JPEG (q 0.85)
  • Stored as Data-URLs in the chat store and persisted across reloads
  • Rendered as clickable thumbnails inside the user bubble

🎨 Design notes

  • One source of truth — colours, shadows and radii live in theme.ts and globals.css custom properties.
  • Glassmorphism AppBar with backdrop-filter: saturate(180%) blur(12px).
  • GPU-composited background — four blurred radial blobs animated via CSS keyframes (no JS per frame). Vignette + grid pattern for foreground readability.
  • No double bordersAIInput is a single shell with focus-ring; the hero just wraps it in a max-width container.

📦 Scripts

npm run dev      # development server on :3000
npm run build    # production build
npm run start    # serve production build
npm run lint     # next lint

🗺 Roadmap ideas

  • Real auth (NextAuth + provider)
  • Persistent database (Postgres + Prisma) instead of the mock store
  • Real RAG with an embeddings store for manuals
  • Email confirmations for approved reservations
  • QR code on each tool that opens the reservation flow
  • iCal export for personal reservations

📄 License

MIT — do whatever you like, just don't hold me liable.