Skip to content

Vandool/grillme

Repository files navigation

GrillMe

Context-aware, local-first AI interview simulator that grounds every question in your actual CV and job description.

Status: Under active development. Architecture and infrastructure are complete. Core interview logic is in progress.

License: MIT Python 3.12 CI Docker

Why GrillMe

Most interview simulators are generic chatbots. They ask the same behavioral questions regardless of the role, the company, or the candidate's background. You deserve a simulator that actually knows your application.

GrillMe reads your CV, the specific job description, and optionally researches the target company — then conducts an adaptive mock interview grounded in that context. No generic questions. No wasted practice time. Every question targets what matters for this role and your gaps.

  • Grounded in your application — questions are derived from your CV matched against the specific JD, with gap analysis before the session starts
  • Adaptive follow-up depth — configurable knobs control how deep the interviewer pushes on each topic before switching
  • Fully local — runs entirely on your machine with Ollama + faster-whisper + edge-tts. No cloud account, no API keys, no data leaving your laptop
  • MCP server — works natively in Claude Desktop, Cursor, and any MCP-compatible host. No existing open-source simulator offers this
  • Session persistence — full history with transcripts and exportable feedback reports (or opt out entirely for stateless mode)

Architecture

Transports (REST, WebSocket, MCP)
        |  <- thin adapters, zero business logic
        v
  InterviewService  <- owns ALL business logic
   |-- Session State Machine
   |-- Prompt Builder (3-layer context assembly)
   +-- Feedback Generator (structured LLM output)
        |
   Abstraction layers (interface + swappable backends)
   |-- Inference: Ollama / OpenAI / Anthropic
   |-- ASR: faster-whisper (local) / OpenAI Whisper (cloud)
   +-- TTS: edge-tts (local) / OpenAI TTS (cloud)
        |
   Persistence: SQLAlchemy + SQLite

All business logic lives in InterviewService. Transports (REST, WebSocket, MCP) are thin adapters that validate input, call the service, and return responses. Inference, ASR, and TTS sit behind abstraction layers with swappable backends selected at startup.

Design decisions are documented in 15 Architectural Decision Records.

Tech Stack
Layer Choice
Backend Python 3.12, FastAPI, Pydantic v2
Persistence SQLAlchemy + Alembic, SQLite
Inference openai SDK (covers Ollama + Groq) + anthropic SDK
Structured output instructor (JSON-repair fallback for small models)
ASR faster-whisper + silero-vad (local), OpenAI Whisper (cloud)
TTS edge-tts (local), OpenAI/ElevenLabs (cloud)
Logging structlog
Frontend React 19 + TypeScript + Vite
State TanStack Query + Zustand
UI shadcn/ui
Containers Docker Compose (3 variants)
MCP mcp Python SDK
Linting ruff (select = ["ALL"])
Type checking ty
Package managers uv (Python), pnpm (frontend)
Task runner Makefile

Deliberately not used:

  • LangChain / LangGraph — the interview loop is a function call and a state machine, not a chain. Plain Python keeps context assembly explicit and debuggable.
  • RAG / vector database — CV + JD fit entirely in context. RAG solves a problem this project doesn't have.
  • Postgres — SQLite is sufficient for a single-user local tool. SQLAlchemy makes the switch trivial if needed later.

Quick Start

Local mode (Ollama — no API keys needed)

git clone https://github.com/Vandool/grillme.git
cd grillme
docker compose -f docker/docker-compose.local.yml up

Prerequisites: Docker with Compose, and a GPU supported by Ollama (or CPU — slower but works).

Cloud mode (OpenAI / Anthropic / Groq)

docker compose -f docker/docker-compose.cloud.yml up

Set your API key via environment variable before starting.

The Docker infrastructure runs today. Core interview features are under active development — see Roadmap for current progress.

Development

Prerequisites: Python 3.12, uv, Node 22+, pnpm, Docker

make install    # Install all dependencies
make dev-be     # Backend dev server (uvicorn --reload)
make dev-fe     # Frontend dev server (vite)
make check      # Run all checks (lint + test)
make help       # Show all available targets

Roadmap

  • Project architecture and ADRs (15 decisions documented)
  • Monorepo setup (uv + pnpm + Makefile)
  • Docker Compose (base, local with Ollama, cloud-only, dev)
  • CI/CD pipeline (GitHub Actions)
  • Backend scaffold (FastAPI app factory, health endpoint)
  • Frontend scaffold (React 19 + Vite, backend connectivity)
  • Linting and type checking (ruff, ty, ESLint)
  • Core config and dependency injection
  • InterviewService and session state machine
  • Prompt builder (3-layer context assembly)
  • Document ingestion (CV, JD, cover letter parsing)
  • Inference abstraction (Ollama, OpenAI, Anthropic adapters)
  • ASR integration (faster-whisper + silero-vad)
  • TTS integration (edge-tts)
  • Feedback generator (structured scoring + gap analysis)
  • Web UI (Init, Interview, Feedback, History views)
  • MCP server adapter
  • CLI install wizard with hardware detection
  • Session persistence and history browsing
Project Structure
grillme/
├── backend/
│   ├── src/grillme/              # Python package
│   │   ├── main.py               # FastAPI app factory
│   │   ├── api/
│   │   │   ├── rest/             # FastAPI routers
│   │   │   ├── ws/               # WebSocket handlers
│   │   │   └── mcp/              # MCP server adapter
│   │   ├── core/                 # Config, DI, logging
│   │   ├── services/
│   │   │   ├── interview/        # InterviewService, state machine
│   │   │   ├── inference/        # LLM abstraction + adapters
│   │   │   ├── asr/              # ASR backends
│   │   │   ├── tts/              # TTS backends
│   │   │   ├── prompt/           # Prompt builder
│   │   │   └── feedback/         # Feedback generation
│   │   ├── models/               # SQLAlchemy models
│   │   └── schemas/              # Pydantic schemas
│   └── tests/
├── frontend/
│   └── src/
│       ├── components/           # Reusable UI components
│       ├── views/                # Init, Interview, Feedback, History
│       └── stores/               # Zustand session store
├── docker/                       # Dockerfiles + Compose variants
├── docs/
│   ├── PROJECT_v0.0.1.md         # Full project brief
│   └── adr/                      # 15 Architectural Decision Records
├── Makefile                      # Task runner
├── pyproject.toml                # Python project config
└── compose.yaml                  # Docker Compose base

Contributing

GrillMe is under active development. Contributions are welcome once the core interview flow is stable. In the meantime, feel free to open an issue for feature ideas or architecture discussions.

Please review the architectural decisions before proposing changes.

License

MIT

Acknowledgments

Built with FastAPI, Ollama, faster-whisper, edge-tts, instructor, and shadcn/ui.

About

Context-aware, local-first AI interview simulator that grounds every question in your actual CV and job description.

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages