Engineering
Building an AI tutor with Gemini: our architecture
A tour through the MiaCortex stack: Gemini for tutoring, Pyodide for in-browser Python, Next.js in Docker for serving, and Prisma with SQLite for persistence.
MiaCortex is an AI-powered Socratic tutor for Python data structures and algorithms. From day one we optimized for three constraints: low infrastructure cost, fast response time from the model, and zero-install experience for students on any device.
The request path
A student types a question into the tutor chat. The browser sends the message, along with recent context (the current problem, their code, their attempt history), to our Next.js server, which runs in Docker on a single server we operate. The server constructs a prompt for Google Gemini that includes:
- A system instruction describing the Socratic persona and guardrails ("never give the solution directly").
- The problem statement and test cases.
- The student's latest code.
- Recent dialogue turns.
Gemini returns a response, and the server sends it back to the browser, which renders it in the chat UI. We use a fast, inexpensive Gemini model and short, structured answers (key idea, pseudo-code steps, one guiding question), which keeps replies quick and costs predictable. Every AI feature has a per-plan daily or monthly quota.
Why Pyodide for execution
Every student who writes code wants to run it immediately. The naive architecture is to send code to a sandboxed execution service; the sandbox service is the most expensive and most fragile component in any ed-tech stack.
Pyodide runs CPython compiled to WebAssembly directly in the student's browser. This moves the cost, latency, and security perimeter to where it belongs - the student's device. Practice runs never touch our server, and we pay no compute cost per run. (Contest submissions are the one exception: they are re-graded in an external Judge0 sandbox so results cannot be tampered with in the browser.) Students get instant feedback with no round-trip.
Visualization
For algorithm visualization, we generate Mermaid diagrams server-side using Gemini, then render them in the browser. This works surprisingly well for trees, graphs, and state machines. For list/array animations we use lightweight custom SVG animations.
Persistence
Progress tracking, submissions, payments and auth go through Prisma against SQLite. At our current scale a single-file database on the same server is the simplest thing that works, and it keeps the whole stack easy to back up and reason about.
What we'd change
As usage grows we expect to move learning analytics, which is an append-only workload, out of the main database, and to add streaming responses to the tutor chat. Neither is needed yet, so we have not built them.