interview-engine

Interview Engine

A private job-search command center. It finds high-fit roles, explains every score, and builds truthful application packages from a verified Claim Ledger. It tracks each application through an immutable audit trail and measures what actually produces interviews.

North-star metric: qualified interviews booked, not application volume.

Demo data: until you connect a live source, the app loads fictional postings from employers like “Harborline Bank (Demo)”. They carry a DEMO label everywhere, and “submissions” to them are simulated (confirmation DEMO-SIM-…). Nothing leaves the app.


Quick start (local, zero configuration)

npm install
npm run dev          # http://localhost:3000

With no environment variables set, the app runs entirely on your machine:

Concern Local mode
Database Embedded Postgres (PGlite) with pgvector, stored in .data/pglite
Auth Single-user workspace bound to this machine
Files Encrypted (AES-256-GCM) in .data/files; the key is generated in .data/local.key
Jobs Demo source plus any Greenhouse, Lever, or Ashby boards you connect
Email Drafts work locally (copy, mailto:, .eml download)

Onboarding walks you through these steps:

  1. Upload resume. The file is validated and parsed, and any prompt-injection text is flagged and ignored.
  2. Review the Claim Ledger. Every fact shows its source text and a status: Verified, User Approved, Inferred, or Missing.
  3. Set targets and constraints. Hard filters apply only after you confirm them.
  4. Build the answer bank.
  5. Choose a mode and thresholds. Copilot is the default.
  6. Connect email (optional).
  7. Add job sources.

Run only one process against a PGlite directory at a time. Use Settings → Run worker now locally. npm run worker is meant for a Postgres (DATABASE_URL) deployment.

Commands

Command Purpose
npm run dev Dev server
npm test Unit and integration tests (Vitest; the integration suite runs on in-memory Postgres)
npm run typecheck TypeScript
npm run lint ESLint
npm run db:migrate Apply migrations to DATABASE_URL, or to local PGlite if unset
npm run worker / worker:once Background worker loop (self-hosted Postgres deployments)
npm run build && npm start Production build

Production setup (Supabase + Vercel)

  1. Create a Supabase project. Use a personal organization, separate from any business org.
  2. Copy .env.example to .env.local (or your host’s env settings) and fill in:
    • DATABASE_URL: the Supabase Transaction pooler connection string.
    • NEXT_PUBLIC_SUPABASE_URL, NEXT_PUBLIC_SUPABASE_ANON_KEY, SUPABASE_SERVICE_ROLE_KEY.
    • APP_ENCRYPTION_KEY, generated with:
      node -e "console.log(require('crypto').randomBytes(32).toString('base64'))"
      
    • APP_URL (your deployed URL) and CRON_SECRET (any long random string).
  3. Migrate:
    npm run db:migrate
    

    This applies db/migrations/*.sql and, because Supabase is configured, db/migrations/supabase/*.sql: row-level security on every table, a private documents storage bucket, and OAuth tokens that are never exposed through the Data API.

  4. Supabase Auth: enable Email (magic link) and add {APP_URL}/auth/callback to the redirect URLs. Disable public sign-ups once your own account exists.
  5. Deploy to Vercel. vercel.json schedules /api/worker every 15 minutes. Vercel sends Authorization: Bearer $CRON_SECRET automatically.
  6. Optional email:
    • Gmail: create a Google Cloud OAuth client (Web). Scope https://www.googleapis.com/auth/gmail.compose, redirect {APP_URL}/api/oauth/google/callback.
    • Outlook: register an Entra app. Delegated scopes Mail.ReadWrite Mail.Send offline_access openid email, redirect {APP_URL}/api/oauth/microsoft/callback.

Moving from local to Supabase: set the env vars, run npm run db:migrate, then re-upload your resume. Local data in .data/ is not migrated automatically. Use Settings → Export if you want a copy.


What’s live vs. simulated

Capability Status
Resume upload and parsing (PDF/DOCX), Claim Ledger, versioned master and lane resumes Live
Prompt-injection detection on resumes, job descriptions, and pasted/fetched content Live
Greenhouse, Lever, and Ashby public job-board APIs; manual URL import (ATS links and schema.org JobPosting pages; paste for aggregators) Live, read-only
Dedupe, freshness verification, Fit/Confidence/Priority scoring, Workbench Live
Tailored packages with evidence check and diff; .docx/.txt export Live
Automatic drafts for Apply Now / Strong Review matches (resume, JD-matched cover letter, answers, hiring-manager intro email), capped per day; drafts only Live (Settings → Automatic drafts)
ATS keyword match: posting terms present / truthfully addable (proved by a verified fact) / gaps, with one-click add and rebuild Live
Hiring-manager finder: likely manager titles from the reporting line and level, names/emails the posting publishes, LinkedIn/Google search links you open Live, guided (no scraping, no guessed emails)
Copilot apply: deep link, copy-ready answers, idempotent submission record Live (you submit on the employer site)
Guarded Auto-Apply Engine live; only the demo connector is SUPPORTED, and its submissions are simulated. Real ATS application APIs require employer credentials, so every live source is MANUAL_ONLY.
Gmail/Outlook provider drafts and optional send Live once OAuth credentials are configured; otherwise local drafts only
Scheduled searches, stage-aging alerts, durable queue Live via cron/worker
Response/status detection from the inbox Not implemented (the Gmail scope is compose-only by design)

Safety model (enforced in code, covered by tests)

Scoring (defaults, editable in Settings)

Fit (0–100):

Component Points
Must-have coverage 24
Role family 18
Transferable competencies 14
Seniority/scope 12
Domain 10
Outcomes 8
Location 5
Compensation 4
Freshness 3
Source 2

Requirement weights are core-required ×3, required ×2, and preferred ×1. Evidence earns 1.0 (exact), 0.75 (strong transferable), 0.4 (adjacent), or 0 (none).

Confidence (description completeness, pay/location clarity, parse certainty, and evidence coverage) and Priority are computed separately. Recommendation tiers and auto-apply thresholds follow the product spec. After 20 resolved outcomes, Insights proposes reversible weight changes within ±15% of the defaults.

Project layout

db/migrations/            SQL (portable core + supabase/ hardening)
src/lib/engine/           Pure logic: parsing, taxonomy, scoring, dedupe, evidence, packages, outreach, gate, metrics, calibration
src/lib/server/           Data access & services (profile, jobs, packages, applications, outreach, autoapply, queue, insights, mail, storage)
src/lib/sources/          Source adapters + demo data
src/app/(app)/            Overview, Job Radar, Workbench, Review Queue, Applications, Outreach, Profile & Assets, Insights, Settings
src/app/api/              Export, resume download, OAuth, worker, .eml
tests/                    Engine unit tests + end-to-end integration test