124
⚫ LVL 05 — SENIOR DEVELOPERSESSION 124DAY 124

THE FINAL EXAM

🎯 BREAK && FIX
Final Assessment | 3 Hours | All Tools Allowed

You're handed a fresh PixelCraft instance that's been deliberately sabotaged. Six problems. Three hours. All tools allowed — including AI, but you must justify every use. Find the bugs. Fix the vulnerabilities. Optimize the bottleneck. Ship the feature. Document everything. This is your final proof of skill.
THE.SABOTAGE
🐛
Bug 1: CSS Layout Break
The toolbar overlaps the canvas on screens below 1024px. Something in the responsive layout is broken. Flexbox? Grid? Media query? Find it, fix it, verify on mobile, tablet, and desktop viewports.
🐛
Bug 2: JavaScript Logic Error
Undo works, but redo is broken — it replays the wrong state. The history index is off by one somewhere. Off-by-one errors are the most common bug in all of programming. Find exactly where.
🐛
Bug 3: Backend Crash
POST /api/images/upload crashes with "Cannot read properties of undefined." Only happens with certain file types. The error is in the upload middleware. Read the stack trace. Reproduce. Fix. Verify.
🔒
Security Vulnerability
Any user can view any other user's private images by changing the ID in the URL. Missing authorization check: the endpoint fetches the image but never verifies ownership. Classic IDOR (Insecure Direct Object Reference).
Performance Issue
Gallery page makes 1 database query per image to fetch the author name. 100 images = 100 queries. Classic N+1 problem. The page loads in 4 seconds instead of 200ms. Fix with a single aggregation or join.
Feature Request
Implement image bookmarks with tags. Users can bookmark images and tag them ("favorites", "inspiration", "reference"). Filter bookmarks by tag. Full CRUD. This is a mini feature from scratch.
EXAM.TASKS
01
Bug 1: CSS Layout Break
// YOUR DELIVERABLE: ## Diagnosis What did you observe? How did you reproduce it? What DevTools technique found it? ## Root Cause Which CSS rule is broken? Why does it only affect <1024px? ## Fix The exact CSS change. (Show the before and after) ## Verification Tested on: 320px, 768px, 1024px, 1440px viewports. Screenshot or description of each. ## Commit git commit -m "Fix toolbar overlap on mobile viewports (#BUG-1) The toolbar flex container was using flex-direction: row below 1024px instead of column, causing it to overflow the canvas area. Tested: 320px, 768px, 1024px, 1440px. Closes #BUG-1"
02
Bug 2: Redo Logic Error
// YOUR DELIVERABLE: ## Diagnosis Steps to reproduce: 1. Apply filter A 2. Apply filter B 3. Apply filter C 4. Undo (→ shows B ✅) 5. Undo (→ shows A ✅) 6. Redo (→ should show B, shows C ❌) ## Root Cause Where is the off-by-one? Is it in undo, redo, or pushHistory? Show the exact line with the error. ## Fix The corrected index logic. Explain WHY the fix is correct. ## Verification Tested the sequence above. Tested: undo all → redo all. Tested: undo 2, new edit, redo (should have nothing to redo). ## Unit Test Add a test that would have caught this bug. If the test passes, the bug can never return.
03
Bug 3: Upload Crash
// YOUR DELIVERABLE: ## Diagnosis Stack trace analysis: Which line? Which variable is undefined? Which file types trigger it? (Hint: try uploading a .svg or .webp) ## Root Cause The middleware accesses a property that doesn't exist for certain MIME types. Which property? Why does it exist for JPEG but not SVG? ## Fix Add a guard check or handle the missing property. Show code. ## Verification Tested: upload JPEG ✅ Tested: upload PNG ✅ Tested: upload SVG ✅ (was crashing) Tested: upload WebP ✅ Tested: upload invalid file → proper error message, no crash
04
Security: IDOR Vulnerability
// YOUR DELIVERABLE: ## Diagnosis Reproduce: logged in as User A, access GET /api/images/:idOfUserB → Returns User B's private image! ## Root Cause The endpoint fetches by image ID but never checks if the requesting user is the owner. ## Fix // BEFORE (vulnerable): app.get('/api/images/:id', async (req, res) => { const image = await db.collection('images') .findOne({ _id: id }); res.json(image); }); // AFTER (secure): app.get('/api/images/:id', async (req, res) => { const image = await db.collection('images') .findOne({ _id: id, $or: [ { userId: req.user.id }, { public: true }, ], }); if (!image) return res.status(404) .json({ error: 'Not found' }); res.json(image); }); ## Verification User A accessing own image: ✅ User A accessing User B private: 404 ✅ User A accessing public image: ✅ Unauthenticated accessing public: ✅ Unauthenticated accessing private: 404 ✅
05
Performance: N+1 Query
// YOUR DELIVERABLE: ## Diagnosis // BEFORE (N+1): const images = await db .collection('images') .find({ public: true }) .limit(100).toArray(); // 100 additional queries: for (const img of images) { img.author = await db .collection('users') .findOne({ _id: img.userId }); } // Total: 101 queries. 4 seconds. ## Fix // AFTER (aggregation pipeline): const images = await db .collection('images') .aggregate([ { $match: { public: true } }, { $limit: 100 }, { $lookup: { from: 'users', localField: 'userId', foreignField: '_id', as: 'authorInfo', }}, { $unwind: '$authorInfo' }, { $project: { title: 1, url: 1, 'author': '$authorInfo.name', }}, ]).toArray(); // Total: 1 query. 50ms. ## Verification Before: 101 queries, 4000ms After: 1 query, 50ms 80× improvement.
06
Feature: Image Bookmarks
// YOUR DELIVERABLE: ## Data Model interface Bookmark { userId: string; imageId: string; tags: string[]; createdAt: Date; } // Index: { userId: 1, imageId: 1 } // unique compound index ## API POST /api/bookmarks { imageId, tags } DELETE /api/bookmarks/:imageId GET /api/bookmarks ?tag=favorites GET /api/bookmarks/tags → ["favorites", "inspiration", ...] ## Frontend - Bookmark icon on each image card - Click → toggle bookmark (filled/empty) - Tag input: add/remove tags - Filter bar: click a tag to filter - "My Bookmarks" page ## Tests - Bookmark an image ✅ - Remove a bookmark ✅ - Filter by tag ✅ - Duplicate bookmark → 409 ✅ - Bookmark other user's public image ✅ - Bookmark other user's private → 404 ✅
CS.DEEP-DIVE

AI maturity: the real skill being tested.

Using AI isn't cheating. Using AI without understanding IS. The exam tests whether you can justify, verify, and take responsibility for AI-assisted solutions.

// AI maturity levels:

Level 0: "AI wrote this"
  Pastes without reading
  Can't explain the fix
  ❌ This is the exam failure mode

Level 1: "AI suggested, I verified"
  Reads the suggestion critically
  Tests before committing
  ✅ Acceptable

Level 2: "I diagnosed, asked AI to
  confirm my theory"
  Found the root cause yourself
  Used AI to validate approach
  ✅✅ Strong

Level 3: "I knew the fix, asked AI
  about edge cases I might miss"
  AI as a second pair of eyes
  ✅✅✅ Senior-level AI use

// Document every AI interaction:
// "I asked Claude X because Y,
// and verified by Z."
"Exam Checklist"
[ ]Bug 1: CSS layout fixed. Tested on 4 viewport sizes. Commit message includes root cause and verification.
[ ]Bug 2: Redo logic corrected. Off-by-one identified. Regression test added. Full undo/redo sequence verified.
[ ]Bug 3: Upload crash fixed. All file types tested. Error handling for invalid files verified.
[ ]Security: IDOR patched. Authorization check added. All 5 access scenarios verified (own, other-private, public, unauth-public, unauth-private).
[ ]Performance: N+1 eliminated. 101 queries → 1 query. Response time 4s → 50ms. Aggregation pipeline working.
[ ]Feature: Bookmarks implemented. CRUD API. Tag filtering. Frontend UI. Tests passing.
REF.MATERIAL
ARTICLE
OWASP
Official guide to Insecure Direct Object Reference vulnerabilities: how to find them, how to fix them, and how to test for them.
SECURITYOWASP
ARTICLE
MongoDB
MongoDB's equivalent of SQL JOIN: aggregate pipeline stage for combining documents from two collections. The fix for N+1 query problems.
MONGODBPERFORMANCE
VIDEO
Web Dev Simplified
The N+1 query problem explained: why it happens, how to detect it, and how to fix it with eager loading, joins, or aggregation.
N+1TUTORIAL
ARTICLE
Conventional Commits
A specification for structured commit messages: type(scope): description. The standard for clear, searchable Git history.
GITCOMMITS
ARTICLE
Martin Fowler
Understanding bugs, shortcuts, and accumulated design problems. The sabotaged codebase is technical debt made visible.
THEORYDEBT
// LEAVE EXCITED BECAUSE
6 problems. 3 hours. All solved. CSS debugged. Logic error found by tracing execution. Crash fixed with defensive coding. IDOR patched with authorization. N+1 eliminated with aggregation. Feature shipped with full CRUD. You can handle anything a codebase throws at you.