Inspiration
Studying from a topic or a document and then testing yourself on it are usually two separate steps — open a book, then go find or write a quiz somewhere else. We wanted to collapse that into one step: drop in a topic, or your own notes, and get a quiz back in seconds.
What it does
QuizAI generates multiple-choice quizzes two ways:
- By topic — type anything ("Python Programming," "World History") and pick a difficulty and question count.
- From a document — upload a
.txt/.md/.csv/.html/.jsonfile and the AI reads it and writes questions based on its actual content.
You then take the quiz with a progress bar and a question jump-pad, submit it, and get a scored results page — a circular progress ring, a breakdown of correct/wrong/ skipped, and a per-question review showing your answer next to the correct one. Results are saved to MongoDB so they persist across sessions.
How we built it
- Frontend: React + Vite, styled with Tailwind CSS, with a small Context API
store to share quiz state (current quiz, answers, results) across pages without
prop-drilling. Dark mode is a manual toggle (not just OS preference) persisted in
localStorage. - Backend: Express + MongoDB (Mongoose), with two Mongoose models —
QuizandResult— and REST endpoints for generating, fetching, and scoring quizzes. - AI: Google's Gemini API does the actual question generation. We prompt it for
strict JSON output (
responseMimeType: "application/json") and validate every question server-side — exactly one correct answer must be present among the options — before anything touches the database, so a malformed AI response never corrupts a saved quiz.
Challenges we ran into
- Getting reliable structured output from the model. Free-text "give me a quiz" prompts occasionally drifted format. Forcing JSON mode and writing a validation layer that filters out any malformed question (rather than trusting the AI blindly) fixed this.
- MongoDB Atlas IP whitelisting. Classic "works on my machine" trap — the backend
would silently die on
connectDB()failure, which made early debugging confusing because every route looked broken, not just the database-backed ones. - Vite environment variables are build-time, not runtime. Changing
VITE_API_URLafter a production build requires a full rebuild — restarting the server alone does nothing, since there's no server, just static files. - CORS between separately deployed frontend/backend.
CLIENT_URLhas to exactly match the production frontend's origin, notlocalhost, or every API call gets silently blocked by the browser.
What's next
Question types beyond multiple-choice (true/false, fill-in-the-blank), a leaderboard for shared quizzes, exporting a quiz to PDF, and richer document support (PDF/DOCX uploads instead of plain text).
Built With
- ai
- axios
- express.js
- gen
- google-gemini-api
- javascript
- mongodb
- mongoose
- node.js
- react
- react-router
- sdk
- tailwind-css
- vite
Log in or sign up for Devpost to join the conversation.