Full-stack learning portal with a React/Vite frontend and a Java Spring Boot backend. The app supports role-based access, subjects/classes, syllabus upload, Ollama-assisted content generation, subject Q&A, LLM dialogs, understanding analytics, and lightweight student peer threads.
- Frontend: React 19, TypeScript, Vite, Tailwind CSS
- Backend: Java 21, Spring Boot 3, Spring Security, JDBC
- Database: PostgreSQL with Flyway migrations
- LLM: Ollama-compatible local model API
- Auth: JWT bearer tokens
- File storage: local disk for v1
- Node.js and npm
- Java 21
- Maven 3.9+
- PostgreSQL 15+
- Ollama running locally if you want live LLM generation
Create a PostgreSQL database:
createdb knowledge_portalRun the backend:
cd backend
mvn spring-boot:runDefault backend URL:
http://localhost:8080/api
Useful environment variables:
DB_URL=jdbc:postgresql://localhost:5432/knowledge_portal
DB_USERNAME=postgres
DB_PASSWORD=postgres
JWT_SECRET=change-this-development-secret-at-least-32-characters
UPLOAD_DIR=uploads
OLLAMA_URL=http://localhost:11434
OLLAMA_MODEL=llama3.1
CORS_ORIGINS=http://localhost:5173
Flyway creates the schema automatically on backend startup. Demo users are seeded when the database is empty:
Student: alex@student.com / student123
Teacher: sarah@quickquery.com / teacher123
Admin: admin@quickquery.com / admin123
Install/pull a model:
ollama pull llama3.1
ollama serveIf Ollama is unavailable, syllabus processing still stores fallback generated content with ready_for_review status so the workflow remains testable.
Install dependencies:
cd frontend
npm installCreate .env.development or update the existing file:
VITE_API_URL=http://localhost:8080/api
VITE_APP_ENV=development
VITE_ENABLE_DEBUG=true
Run the frontend:
cd frontend
npm run devDefault frontend URL:
http://localhost:5173
GET /api/healthPOST /api/auth/registerPOST /api/auth/loginGET /api/meGET /api/classesPOST /api/classesGET /api/subjectsPOST /api/subjectsPOST /api/subjects/{subjectId}/enrollmentsPOST /api/subjects/{subjectId}/syllabiGET /api/subjects/{subjectId}/syllabiPOST /api/subjects/{subjectId}/materialsGET /api/subjects/{subjectId}/materialsGET /api/subjects/{subjectId}/generated-contentPATCH /api/generated-content/{contentId}POST /api/syllabi/{syllabusId}/regenerateGET /api/subjects/{subjectId}/questionsPOST /api/subjects/{subjectId}/questionsPOST /api/questions/{questionId}/repliesGET /api/subjects/{subjectId}/conversationsPOST /api/subjects/{subjectId}/conversationsPOST /api/conversations/{conversationId}/messagesGET /api/peer-threadsPOST /api/peer-threadsPOST /api/peer-threads/{threadId}/repliesPOST /api/subjects/{subjectId}/understandingGET /api/subjects/{subjectId}/understanding/meGET /api/subjects/{subjectId}/analytics/understanding
Frontend type check:
cd frontend
npx tsc -bFrontend production build:
cd frontend
npm run buildBackend tests/build:
cd backend
mvn test- PDF and image text extraction are placeholders. Add Apache PDFBox and OCR when richer document ingestion is needed.
- LLM processing is synchronous for v1. Move syllabus processing to a background job queue before production use.
- Local disk file storage is suitable for development only.
- Peer threads are intentionally minimal and do not include advanced moderation or real-time updates.
- Generated content requires teacher approval before students see it as approved material.