How prahang/research-management-system works
1. System shape
- RAMS is a two-tier application: a Next.js frontend and a Flask API backend, backed by a relational database.
- The frontend is a presentation and interaction layer; the backend owns authentication, authorization, business rules, persistence, and analytics aggregation.
2. Frontend boundary
- The frontend/src/app tree shows an App Router structure with distinct pages for dashboard, login, signup, projects, publications, and user profiles.
- Shared UI is split into reusable components such as Charts, OrgChart, navigation, theme controls, and a small shadcn/ui component set.
- frontend/src/lib/api.ts is the main client-side integration point to the backend, so the browser talks to the API through a centralized fetch wrapper rather than ad hoc network calls.
3. Backend boundary
- The Flask app is organized around route blueprints in backend/app/routes: auth, projects, publications, dashboard, users, and search.
- backend/app/__init__.py likely wires the app factory, CORS, SQLAlchemy, and JWT-related setup.
- The API surface is clearly domain-oriented rather than REST-for-everything; each route module maps to one major business area.
4. Core data model
- backend/app/models.py is the architectural center of the backend.
- The key entities are:
- User for faculty, student, and admin identities
- Project for research groups/initiatives
- ProjectMember for membership and role within a project
- ProjectJoinRequest for student/collaborator requests with notes and status
- Publication for papers and metadata
- ActivityEvent for platform audit/activity history
- These models encode the main domain boundaries: identity, project collaboration, publication management, and platform activity.
5. Authentication and authorization flow
- Authentication is JWT-based and stateless.
- The auth subsystem handles registration, login, and the current-user lookup (/me), which the frontend uses to establish session context.
- Authorization is role-driven at two levels:
- platform roles: Faculty, Student, Admin
- project roles: lead, collaborator, student
- That split is important for the architecture: some permissions are global, while others are specific to a project membership.
6. Project collaboration workflow
- Projects are not just records; they are collaboration spaces with membership state and request review.
- Students can submit join requests with a note, leads can review pending requests, and leads can accept/decline them.
- The system also supports lead elevation and a guard against the last lead leaving, which means the backend enforces membership invariants, not just UI rules.
- The frontend OrgChart component visualizes this hierarchy as Lead → Collaborator → Student.
7. Publications workflow
- Publications can be created manually or imported through Crossref sync.
- The backend publications route and tasks/publication_sync.py indicate a split between synchronous CRUD and asynchronous enrichment/import logic.
- The frontend separates “My Publications” from “Discover Community,” so publication data is used both for personal ownership and institution-wide browsing.
8. Analytics and dashboard flow
- The dashboard is built around aggregated backend data rather than client-side calculation.
- backend/app/routes/dashboard.py provides counts and chart-ready datasets such as publication trends and department comparisons.
- The frontend consumes this data in Charts.tsx, which suggests the backend is responsible for shaping the analytics response into a directly renderable form.
9. Background processing
- backend/celery_worker.py, backend/app/celery_utils.py, and backend/app/tasks/publication_sync.py show a separate async worker subsystem.
- This is the architectural boundary for longer-running or external-API-bound work, especially publication synchronization against Crossref.
- The worker is distinct from the Flask web process, so web requests stay responsive while sync jobs run out-of-band.
10. Persistence and schema management
- The repository uses SQLAlchemy plus Flask-Migrate/Alembic for schema evolution.
- There are migrations for the initial schema and later join-request changes, showing that the data model is actively versioned.
- seed.py suggests a bootstrap path for local/demo data, while the runtime setup supports SQLite locally and PostgreSQL in production.
11. Deployment topology
- The repo is split for deployment: frontend on Vercel, backend on Render, and PostgreSQL on Render.
- render.yaml defines backend infrastructure, while frontend/vercel.json and the frontend env var point the browser app at the API origin.
- The presence of CORS and separate frontend/backend URLs means the diagram should show two independently deployed services communicating over HTTP.
12. What to draw as the main architecture
- Draw the browser-facing Next.js app as the presentation layer.
- Draw the Flask API as the domain/service layer with route modules grouped by feature.
- Place the database as the authoritative persistence layer behind SQLAlchemy.
- Add a separate Celery worker for async publication sync.
- Show Crossref as an external data source only for the publication-import path.
Main entry points: __init__.py App Setup · models.py Domain Models · projects.py Projects API · publications.py Publications API
Components 21
Frontend
Next.js presentation and interaction layer
- App Router · Browser entrypoint with routed screens for auth, projects, publications, and users.
frontend/src/app - UI Components · Reusable presentation pieces including charts, navigation, theme, and org chart views.
frontend/src/components - API Client · Central browser-to-backend integration point used by the frontend.
frontend/src/lib/api.ts - Projects Page · Frontend surface for project browsing and collaboration workflows.
frontend/src/app/projects/page.tsx - Publications Page · Frontend surface for my publications and community discovery.
frontend/src/app/publications/page.tsx - Profile Page · Frontend surface for viewing individual user profiles.
frontend/src/app/users/[id]/page.tsx
Backend
Flask API, domain logic, and persistence
- App Setup · Wires the Flask application, CORS, auth, and database setup.
backend/app/__init__.py - Auth API · Registration, login, and current-user session lookup.
backend/app/routes/auth.py - Projects API · Project membership, join requests, and role management.
backend/app/routes/projects.py - Publications API · CRUD and import-facing publication endpoints.
backend/app/routes/publications.py - Dashboard API · Aggregated counts and chart-ready analytics payloads.
backend/app/routes/dashboard.py - Users API · User lookup and profile-related endpoints.
backend/app/routes/users.py - Search API · Search endpoints for discovering records across the system.
backend/app/routes/search.py - Domain Models · Core entities for users, projects, memberships, join requests, publications, and activity history.
backend/app/models.py
Async Worker
Background job processing for external sync
- Publication Sync · Asynchronous Crossref import and publication enrichment workflow.
backend/app/tasks/publication_sync.py - Celery Worker · Separate process that executes background jobs out of band from HTTP requests.
backend/celery_worker.py - Celery Utils · Shared Celery configuration and task wiring helpers.
backend/app/celery_utils.py
Data Layer
Database schema and migrations
- Migrations · Alembic migration history for the relational schema.
backend/migrations - Seed Data · Local/demo data loading entrypoint.
backend/seed.py - Database · Authoritative persistence for users, projects, publications, and activity.
External
Outside systems integrated by the app
- Crossref · External publication metadata service used for sync/import.
Connections 25
- App Router → UI Components: uses UI · Pages compose shared interface elements.
- App Router → API Client: calls API · Screens fetch and mutate data through the centralized client.
- Projects Page → Projects API: projects data · Project screens consume project collaboration endpoints.
- Publications Page → Publications API: publications data · Publication screens consume CRUD and discovery endpoints.
- Profile Page → Users API: profile data · Profile screens load user details from the API.
- UI Components → Dashboard API: charts · Chart components render backend-shaped analytics payloads.
- API Client → App Setup: HTTP · Browser client communicates with the Flask service over HTTP.
- App Setup → Auth API: registers · App factory mounts auth routes.
- App Setup → Projects API: registers · App factory mounts project routes.
- App Setup → Publications API: registers · App factory mounts publication routes.
- App Setup → Dashboard API: registers · App factory mounts dashboard routes.
- App Setup → Users API: registers · App factory mounts user routes.
- App Setup → Search API: registers · App factory mounts search routes.
- Auth API → Domain Models: users · Auth logic reads and writes user identity records.
- Projects API → Domain Models: membership · Project workflows depend on project, member, and join-request models.
- Publications API → Domain Models: publications · Publication endpoints persist and query publication entities.
- Dashboard API → Domain Models: aggregates · Dashboard metrics are derived from stored domain records.
- Users API → Domain Models: profiles · User endpoints read profile and role data.
- Search API → Domain Models: searches · Search spans the core persisted domain objects.
- Publication Sync → Crossref: syncs · Background job pulls publication metadata from Crossref.
- Celery Worker → Publication Sync: executes · Worker process runs publication sync tasks.
- Celery Utils → Publication Sync: configures · Shared Celery setup enables task execution.
- Domain Models → Database: persists · SQLAlchemy stores domain state in the relational database.
- Migrations → Database: evolves · Migrations version the database schema over time.
- Seed Data → Database: loads · Seed script populates initial or demo records.