diff --git a/CLAUDE.md b/CLAUDE.md index be6e462..561098a 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -7,7 +7,7 @@ An open-source tool combining LLM intelligence + static analysis to produce inte - **Monorepo** with pnpm workspaces - **packages/core** — Shared analysis engine (types, persistence, tree-sitter plugin, LLM prompt templates) - **packages/dashboard** — React + TypeScript web dashboard (React Flow, Monaco Editor, Zustand, TailwindCSS) -- **packages/skill** — Claude Code skill (not yet implemented) +- **packages/skill** — Claude Code skill (`/understand-chat` command) ## Key Commands - `pnpm install` — Install all dependencies @@ -15,6 +15,20 @@ An open-source tool combining LLM intelligence + static analysis to produce inte - `pnpm --filter @understand-anything/core test` — Run core tests - `pnpm dev:dashboard` — Start dashboard dev server +## Key Commands (updated) +- `pnpm --filter @understand-anything/skill build` — Build skill package +- `pnpm --filter @understand-anything/skill test` — Run skill tests + +## Phase 2 Features +- Fuzzy search via Fuse.js (SearchEngine in core) +- Zod schema validation on graph loading +- Staleness detection + incremental graph merging +- Layer auto-detection (heuristic + LLM prompt) +- `/understand-chat` skill command +- Dashboard chat panel (Claude API integration) +- Dagre auto-layout for graph visualization +- Layer visualization with grouping and legend + ## Conventions - TypeScript strict mode everywhere - Vitest for testing diff --git a/README.md b/README.md index 33ca4c1..6d139ec 100644 --- a/README.md +++ b/README.md @@ -2,14 +2,29 @@ An open-source tool that combines LLM intelligence with static analysis to help anyone understand any codebase — from junior developers to product managers. +## Current Status + +**Phase 2 complete.** The core analysis engine, web dashboard, and Claude Code skill are all functional. The project includes fuzzy search, schema validation, staleness detection, layer auto-detection, and an interactive chat interface. + ## Features +### Phase 1 — Foundation - **Knowledge Graph** — Automatically maps your codebase into an interactive graph of files, functions, classes, and their relationships - **Multi-Panel Dashboard** — Graph view, code viewer, chat, and learn panels in a workspace layout - **Natural Language Search** — Search your codebase with plain English: "which parts handle authentication?" - **Tree-sitter Analysis** — Accurate structural analysis for TypeScript, JavaScript (more languages coming) - **LLM-Powered Summaries** — Every node gets a plain-English description of what it does and why +### Phase 2 — Intelligence +- **Fuzzy Search** — Fast, typo-tolerant search across all graph nodes via Fuse.js (SearchEngine in core) +- **Schema Validation** — Zod-based runtime validation when loading knowledge graphs, with detailed error messages +- **Staleness Detection** — Detects changed files via git diff and incrementally merges graph updates +- **Layer Auto-Detection** — Heuristic-based layer grouping (API, Service, Data, UI, Utility) with LLM refinement +- **`/understand-chat` Skill** — Ask questions about your codebase directly in the terminal via Claude Code +- **Dashboard Chat Panel** — Context-aware Q&A integrated into the web dashboard (Claude API) +- **Dagre Auto-Layout** — Automatic hierarchical graph layout for clean visualization +- **Layer Visualization** — Color-coded layer grouping with collapsible groups and a legend panel + ## Quick Start ```bash @@ -19,17 +34,41 @@ pnpm install # Build the core package pnpm --filter @understand-anything/core build +# Build the skill package +pnpm --filter @understand-anything/skill build + # Start the dashboard dev server pnpm dev:dashboard ``` +## Commands + +| Command | Description | +|---------|-------------| +| `pnpm install` | Install all dependencies | +| `pnpm --filter @understand-anything/core build` | Build the core package | +| `pnpm --filter @understand-anything/core test` | Run core tests | +| `pnpm --filter @understand-anything/skill build` | Build the skill package | +| `pnpm --filter @understand-anything/skill test` | Run skill tests | +| `pnpm --filter @understand-anything/dashboard build` | Build the dashboard | +| `pnpm dev:dashboard` | Start dashboard dev server | + +### Claude Code Skill + +Once installed as a Claude Code skill, use the `/understand-chat` command to ask questions about your codebase directly in the terminal: + +``` +/understand-chat How does authentication work in this project? +/understand-chat What files are related to the payment system? +``` + ## Project Structure ``` packages/ - core/ — Analysis engine: types, persistence, tree-sitter, LLM prompts - dashboard/ — React + TypeScript web dashboard - skill/ — Claude Code skill (coming soon) + core/ — Analysis engine: types, persistence, tree-sitter, search, schema, staleness, layers + dashboard/ — React + TypeScript web dashboard with chat panel + skill/ — Claude Code skill (/understand-chat command) ``` ## Tech Stack @@ -40,6 +79,9 @@ packages/ - Monaco Editor (code viewer) - Zustand (state management) - tree-sitter (static analysis) +- Fuse.js (fuzzy search) +- Zod (schema validation) +- Dagre (graph layout) ## License diff --git a/packages/dashboard/public/knowledge-graph.json b/packages/dashboard/public/knowledge-graph.json index 7051021..9ced329 100644 --- a/packages/dashboard/public/knowledge-graph.json +++ b/packages/dashboard/public/knowledge-graph.json @@ -1,46 +1,528 @@ { "version": "1.0.0", "project": { - "name": "sample-project", + "name": "taskflow-api", "languages": ["typescript"], - "frameworks": ["express"], - "description": "A sample Express API", - "analyzedAt": "2026-03-14T00:00:00.000Z", - "gitCommitHash": "abc123" + "frameworks": ["express", "prisma", "zod"], + "description": "A task management REST API built with Express and Prisma. Supports user authentication, project workspaces, task CRUD with assignments, and real-time notifications via WebSocket. Designed for team collaboration with role-based access control.", + "analyzedAt": "2026-03-14T12:00:00.000Z", + "gitCommitHash": "a1b2c3d4e5f6" }, "nodes": [ - {"id": "file:src/index.ts", "type": "file", "name": "index.ts", "filePath": "src/index.ts", "summary": "Application entry point, starts the Express server", "tags": ["entry", "server"], "complexity": "simple"}, - {"id": "file:src/auth/login.ts", "type": "file", "name": "login.ts", "filePath": "src/auth/login.ts", "summary": "Handles user authentication and login flow", "tags": ["auth", "login"], "complexity": "moderate"}, - {"id": "func:src/auth/login.ts:handleLogin", "type": "function", "name": "handleLogin", "filePath": "src/auth/login.ts", "lineRange": [10, 35], "summary": "Validates credentials and returns a JWT token", "tags": ["auth", "jwt"], "complexity": "moderate"}, - {"id": "func:src/auth/login.ts:validateEmail", "type": "function", "name": "validateEmail", "filePath": "src/auth/login.ts", "lineRange": [37, 42], "summary": "Checks if an email address is valid using regex", "tags": ["validation", "email"], "complexity": "simple"}, - {"id": "file:src/db/connection.ts", "type": "file", "name": "connection.ts", "filePath": "src/db/connection.ts", "summary": "Database connection pool using PostgreSQL", "tags": ["database", "postgres"], "complexity": "moderate"} + { + "id": "file:src/index.ts", + "type": "file", + "name": "index.ts", + "filePath": "src/index.ts", + "summary": "Application entry point. Initializes the Express server, applies middleware, mounts route handlers, and starts listening on the configured port.", + "tags": ["entry", "server", "express"], + "complexity": "moderate" + }, + { + "id": "file:src/routes/task.routes.ts", + "type": "file", + "name": "task.routes.ts", + "filePath": "src/routes/task.routes.ts", + "summary": "Defines REST endpoints for task CRUD operations: GET /tasks, POST /tasks, PATCH /tasks/:id, DELETE /tasks/:id. Validates request bodies with Zod schemas before delegating to TaskService.", + "tags": ["routes", "tasks", "rest"], + "complexity": "moderate" + }, + { + "id": "file:src/routes/auth.routes.ts", + "type": "file", + "name": "auth.routes.ts", + "filePath": "src/routes/auth.routes.ts", + "summary": "Authentication routes: POST /auth/login, POST /auth/register, POST /auth/refresh. Handles credential validation and JWT token issuance.", + "tags": ["routes", "auth", "jwt"], + "complexity": "moderate" + }, + { + "id": "file:src/routes/project.routes.ts", + "type": "file", + "name": "project.routes.ts", + "filePath": "src/routes/project.routes.ts", + "summary": "Project workspace endpoints: CRUD for projects plus member management. Enforces role-based access so only admins can modify project settings.", + "tags": ["routes", "projects", "rbac"], + "complexity": "moderate" + }, + { + "id": "file:src/services/task.service.ts", + "type": "file", + "name": "task.service.ts", + "filePath": "src/services/task.service.ts", + "summary": "Business logic for tasks. Handles creation, status transitions, assignment, due-date validation, and triggers notifications on state changes.", + "tags": ["service", "tasks", "business-logic"], + "complexity": "complex" + }, + { + "id": "func:src/services/task.service.ts:createTask", + "type": "function", + "name": "createTask", + "filePath": "src/services/task.service.ts", + "lineRange": [24, 58], + "summary": "Creates a new task in the database. Validates the assignee belongs to the project, sets default status to 'todo', and publishes a TASK_CREATED event to the notification service.", + "tags": ["create", "validation", "events"], + "complexity": "moderate" + }, + { + "id": "func:src/services/task.service.ts:transitionStatus", + "type": "function", + "name": "transitionStatus", + "filePath": "src/services/task.service.ts", + "lineRange": [60, 102], + "summary": "Moves a task through its lifecycle (todo -> in_progress -> review -> done). Enforces valid transitions and records the state change timestamp.", + "tags": ["state-machine", "workflow", "validation"], + "complexity": "complex" + }, + { + "id": "file:src/services/auth.service.ts", + "type": "file", + "name": "auth.service.ts", + "filePath": "src/services/auth.service.ts", + "summary": "Authentication service handling password hashing with bcrypt, JWT token generation/verification, and refresh token rotation.", + "tags": ["service", "auth", "security"], + "complexity": "complex" + }, + { + "id": "file:src/services/notification.service.ts", + "type": "file", + "name": "notification.service.ts", + "filePath": "src/services/notification.service.ts", + "summary": "Manages real-time notifications via WebSocket. Subscribes to domain events (task created, assigned, status changed) and broadcasts to relevant connected clients.", + "tags": ["service", "websocket", "events", "realtime"], + "complexity": "complex" + }, + { + "id": "class:src/models/Task.ts:Task", + "type": "class", + "name": "Task", + "filePath": "src/models/Task.ts", + "lineRange": [8, 45], + "summary": "Prisma model wrapper for tasks. Defines the schema fields (title, description, status, priority, dueDate, assigneeId, projectId) and provides static query helpers.", + "tags": ["model", "prisma", "database"], + "complexity": "moderate" + }, + { + "id": "class:src/models/User.ts:User", + "type": "class", + "name": "User", + "filePath": "src/models/User.ts", + "lineRange": [5, 38], + "summary": "Prisma model wrapper for users. Stores email, hashed password, display name, and role. Provides methods for credential verification and profile serialization.", + "tags": ["model", "prisma", "auth"], + "complexity": "moderate" + }, + { + "id": "file:src/db/prisma.ts", + "type": "file", + "name": "prisma.ts", + "filePath": "src/db/prisma.ts", + "summary": "Singleton Prisma client instance. Configures connection pooling, logging levels, and graceful shutdown hooks.", + "tags": ["database", "prisma", "connection"], + "complexity": "simple" + }, + { + "id": "file:src/middleware/auth.middleware.ts", + "type": "file", + "name": "auth.middleware.ts", + "filePath": "src/middleware/auth.middleware.ts", + "summary": "Express middleware that extracts and verifies JWT from the Authorization header. Attaches the decoded user payload to req.user for downstream handlers.", + "tags": ["middleware", "auth", "jwt"], + "complexity": "moderate" + }, + { + "id": "func:src/middleware/auth.middleware.ts:requireRole", + "type": "function", + "name": "requireRole", + "filePath": "src/middleware/auth.middleware.ts", + "lineRange": [28, 44], + "summary": "Higher-order middleware factory that checks if the authenticated user has one of the required roles. Returns 403 Forbidden if the role check fails.", + "tags": ["rbac", "authorization", "middleware"], + "complexity": "simple" + }, + { + "id": "file:src/utils/validate.ts", + "type": "file", + "name": "validate.ts", + "filePath": "src/utils/validate.ts", + "summary": "Shared Zod schemas and a validateBody middleware factory. Schemas cover task creation, user registration, and project settings validation.", + "tags": ["validation", "zod", "schemas"], + "complexity": "simple" + }, + { + "id": "file:src/utils/logger.ts", + "type": "file", + "name": "logger.ts", + "filePath": "src/utils/logger.ts", + "summary": "Structured logging utility built on pino. Provides log levels (debug, info, warn, error) and request-scoped child loggers with correlation IDs.", + "tags": ["logging", "pino", "observability"], + "complexity": "simple" + }, + { + "id": "file:src/config.ts", + "type": "file", + "name": "config.ts", + "filePath": "src/config.ts", + "summary": "Loads environment variables and exports typed configuration: port, database URL, JWT secret, token expiry, log level, and WebSocket settings.", + "tags": ["config", "env", "settings"], + "complexity": "simple" + }, + { + "id": "module:src/routes", + "type": "module", + "name": "routes", + "filePath": "src/routes", + "summary": "Route module aggregating all HTTP endpoint definitions. Each route file maps URL paths to controller logic with middleware chains.", + "tags": ["module", "routing", "api"], + "complexity": "simple" + }, + { + "id": "concept:authentication-flow", + "type": "concept", + "name": "Authentication Flow", + "summary": "The system uses JWT-based stateless authentication. Users log in with email/password, receive an access token (15 min) and refresh token (7 days). The auth middleware validates tokens on protected routes, and the refresh endpoint rotates tokens to maintain sessions.", + "tags": ["concept", "auth", "jwt", "security"], + "complexity": "complex" + }, + { + "id": "concept:task-lifecycle", + "type": "concept", + "name": "Task Lifecycle", + "summary": "Tasks follow a state machine: todo -> in_progress -> review -> done. Only valid forward transitions are allowed. Each transition triggers a notification event and records a timestamp. Tasks can also be archived after completion.", + "tags": ["concept", "workflow", "state-machine"], + "complexity": "moderate" + } ], "edges": [ - {"source": "file:src/index.ts", "target": "file:src/auth/login.ts", "type": "imports", "direction": "forward", "weight": 0.7}, - {"source": "file:src/auth/login.ts", "target": "func:src/auth/login.ts:handleLogin", "type": "contains", "direction": "forward", "weight": 1.0}, - {"source": "file:src/auth/login.ts", "target": "func:src/auth/login.ts:validateEmail", "type": "contains", "direction": "forward", "weight": 1.0}, - {"source": "func:src/auth/login.ts:handleLogin", "target": "func:src/auth/login.ts:validateEmail", "type": "calls", "direction": "forward", "description": "handleLogin calls validateEmail to check the email format", "weight": 0.8}, - {"source": "file:src/auth/login.ts", "target": "file:src/db/connection.ts", "type": "imports", "direction": "forward", "weight": 0.7} + { + "source": "file:src/index.ts", + "target": "file:src/routes/task.routes.ts", + "type": "imports", + "direction": "forward", + "description": "Mounts task routes at /api/tasks", + "weight": 0.8 + }, + { + "source": "file:src/index.ts", + "target": "file:src/routes/auth.routes.ts", + "type": "imports", + "direction": "forward", + "description": "Mounts auth routes at /api/auth", + "weight": 0.8 + }, + { + "source": "file:src/index.ts", + "target": "file:src/routes/project.routes.ts", + "type": "imports", + "direction": "forward", + "description": "Mounts project routes at /api/projects", + "weight": 0.8 + }, + { + "source": "file:src/index.ts", + "target": "file:src/config.ts", + "type": "imports", + "direction": "forward", + "description": "Reads server port and startup configuration", + "weight": 0.6 + }, + { + "source": "file:src/index.ts", + "target": "file:src/middleware/auth.middleware.ts", + "type": "middleware", + "direction": "forward", + "description": "Applies JWT auth middleware globally to protected routes", + "weight": 0.7 + }, + { + "source": "module:src/routes", + "target": "file:src/routes/task.routes.ts", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "module:src/routes", + "target": "file:src/routes/auth.routes.ts", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "module:src/routes", + "target": "file:src/routes/project.routes.ts", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "file:src/routes/task.routes.ts", + "target": "file:src/services/task.service.ts", + "type": "calls", + "direction": "forward", + "description": "Delegates task operations to the service layer", + "weight": 0.9 + }, + { + "source": "file:src/routes/task.routes.ts", + "target": "file:src/utils/validate.ts", + "type": "validates", + "direction": "forward", + "description": "Uses Zod schemas to validate incoming task payloads", + "weight": 0.7 + }, + { + "source": "file:src/routes/auth.routes.ts", + "target": "file:src/services/auth.service.ts", + "type": "calls", + "direction": "forward", + "description": "Delegates login, register, and token refresh to auth service", + "weight": 0.9 + }, + { + "source": "file:src/routes/project.routes.ts", + "target": "file:src/middleware/auth.middleware.ts", + "type": "depends_on", + "direction": "forward", + "description": "Requires authentication and role checking on all endpoints", + "weight": 0.8 + }, + { + "source": "file:src/services/task.service.ts", + "target": "func:src/services/task.service.ts:createTask", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "file:src/services/task.service.ts", + "target": "func:src/services/task.service.ts:transitionStatus", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "file:src/services/task.service.ts", + "target": "class:src/models/Task.ts:Task", + "type": "reads_from", + "direction": "forward", + "description": "Queries and mutates task records via the Task model", + "weight": 0.9 + }, + { + "source": "file:src/services/task.service.ts", + "target": "file:src/services/notification.service.ts", + "type": "publishes", + "direction": "forward", + "description": "Emits TASK_CREATED and STATUS_CHANGED events to the notification service", + "weight": 0.7 + }, + { + "source": "file:src/services/auth.service.ts", + "target": "class:src/models/User.ts:User", + "type": "reads_from", + "direction": "forward", + "description": "Looks up users for authentication and creates new user records", + "weight": 0.9 + }, + { + "source": "file:src/services/auth.service.ts", + "target": "file:src/config.ts", + "type": "configures", + "direction": "backward", + "description": "Reads JWT secret and token expiry from configuration", + "weight": 0.6 + }, + { + "source": "file:src/services/notification.service.ts", + "target": "file:src/utils/logger.ts", + "type": "depends_on", + "direction": "forward", + "description": "Logs WebSocket connection events and notification delivery", + "weight": 0.5 + }, + { + "source": "class:src/models/Task.ts:Task", + "target": "file:src/db/prisma.ts", + "type": "depends_on", + "direction": "forward", + "description": "Uses the shared Prisma client for all database queries", + "weight": 0.9 + }, + { + "source": "class:src/models/User.ts:User", + "target": "file:src/db/prisma.ts", + "type": "depends_on", + "direction": "forward", + "description": "Uses the shared Prisma client for user queries", + "weight": 0.9 + }, + { + "source": "file:src/middleware/auth.middleware.ts", + "target": "file:src/middleware/auth.middleware.ts", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "file:src/middleware/auth.middleware.ts", + "target": "func:src/middleware/auth.middleware.ts:requireRole", + "type": "contains", + "direction": "forward", + "weight": 1.0 + }, + { + "source": "concept:authentication-flow", + "target": "file:src/services/auth.service.ts", + "type": "related", + "direction": "forward", + "description": "Auth service implements the core authentication flow", + "weight": 0.9 + }, + { + "source": "concept:authentication-flow", + "target": "file:src/middleware/auth.middleware.ts", + "type": "related", + "direction": "forward", + "description": "Auth middleware enforces the authentication flow on routes", + "weight": 0.8 + }, + { + "source": "concept:task-lifecycle", + "target": "func:src/services/task.service.ts:transitionStatus", + "type": "related", + "direction": "forward", + "description": "The transitionStatus function implements the task state machine", + "weight": 0.9 + }, + { + "source": "concept:task-lifecycle", + "target": "file:src/services/notification.service.ts", + "type": "related", + "direction": "forward", + "description": "Lifecycle transitions trigger real-time notifications", + "weight": 0.7 + }, + { + "source": "func:src/services/task.service.ts:createTask", + "target": "file:src/utils/validate.ts", + "type": "validates", + "direction": "forward", + "description": "Validates task data before persisting", + "weight": 0.6 + } ], "layers": [ { "id": "layer:api", "name": "API Layer", - "description": "Entry points and route handlers for the Express API", - "nodeIds": ["file:src/index.ts", "file:src/auth/login.ts"] + "description": "HTTP route handlers and request/response processing. The entry point for all client interactions with the system.", + "nodeIds": [ + "file:src/index.ts", + "file:src/routes/task.routes.ts", + "file:src/routes/auth.routes.ts", + "file:src/routes/project.routes.ts", + "module:src/routes" + ] }, { - "id": "layer:auth", - "name": "Auth Logic", - "description": "Authentication and validation business logic", - "nodeIds": ["func:src/auth/login.ts:handleLogin", "func:src/auth/login.ts:validateEmail"] + "id": "layer:service", + "name": "Service Layer", + "description": "Core business logic and domain operations. Orchestrates data access, validation, event publishing, and enforces business rules.", + "nodeIds": [ + "file:src/services/task.service.ts", + "func:src/services/task.service.ts:createTask", + "func:src/services/task.service.ts:transitionStatus", + "file:src/services/auth.service.ts", + "file:src/services/notification.service.ts" + ] }, { "id": "layer:data", "name": "Data Layer", - "description": "Database connections and data access", - "nodeIds": ["file:src/db/connection.ts"] + "description": "Database models, Prisma client, and data access patterns. Provides the persistence foundation for all domain entities.", + "nodeIds": [ + "class:src/models/Task.ts:Task", + "class:src/models/User.ts:User", + "file:src/db/prisma.ts" + ] + }, + { + "id": "layer:middleware", + "name": "Middleware Layer", + "description": "Cross-cutting concerns applied to request pipelines: authentication, authorization, and request validation.", + "nodeIds": [ + "file:src/middleware/auth.middleware.ts", + "func:src/middleware/auth.middleware.ts:requireRole", + "file:src/utils/validate.ts" + ] + }, + { + "id": "layer:infrastructure", + "name": "Infrastructure Layer", + "description": "Configuration, logging, and shared utilities that support all other layers without containing business logic.", + "nodeIds": [ + "file:src/config.ts", + "file:src/utils/logger.ts", + "concept:authentication-flow", + "concept:task-lifecycle" + ] } ], - "tour": [] + "tour": [ + { + "order": 1, + "title": "Where It All Begins", + "description": "The application starts in index.ts, which wires up Express middleware and mounts all the route handlers. Think of it as the front door of the API.", + "nodeIds": ["file:src/index.ts"] + }, + { + "order": 2, + "title": "Handling Requests", + "description": "Incoming HTTP requests hit the route files. Each route file defines endpoints for a domain area (tasks, auth, projects) and validates input before passing it along.", + "nodeIds": [ + "file:src/routes/task.routes.ts", + "file:src/routes/auth.routes.ts", + "file:src/routes/project.routes.ts" + ] + }, + { + "order": 3, + "title": "Security Gate", + "description": "Before most routes run, the auth middleware checks the JWT token. The requireRole function adds role-based access control on top of basic authentication.", + "nodeIds": [ + "file:src/middleware/auth.middleware.ts", + "func:src/middleware/auth.middleware.ts:requireRole" + ], + "languageLesson": "JWT (JSON Web Token) is a compact token format that encodes user identity and permissions. It lets the server verify who you are without storing session data." + }, + { + "order": 4, + "title": "Business Logic", + "description": "Services contain the real brains of the application. TaskService manages task creation and status transitions, while AuthService handles password hashing and token management.", + "nodeIds": [ + "file:src/services/task.service.ts", + "func:src/services/task.service.ts:createTask", + "func:src/services/task.service.ts:transitionStatus", + "file:src/services/auth.service.ts" + ] + }, + { + "order": 5, + "title": "Data Persistence", + "description": "The Task and User models wrap Prisma queries. They talk to the database through a shared Prisma client configured in prisma.ts.", + "nodeIds": [ + "class:src/models/Task.ts:Task", + "class:src/models/User.ts:User", + "file:src/db/prisma.ts" + ], + "languageLesson": "Prisma is an ORM (Object-Relational Mapper) that lets you write database queries in TypeScript instead of raw SQL. It auto-generates types from your schema." + }, + { + "order": 6, + "title": "Real-Time Updates", + "description": "When tasks change state, the notification service broadcasts updates over WebSocket so connected clients see changes immediately without polling.", + "nodeIds": ["file:src/services/notification.service.ts"] + } + ] }