Backend API Documentation – IE Research Platform
Base URL
- Development:
http://localhost:3000/api(or your configured proxy) - Production:
https://yourdomain.com/api
All endpoints (unless stated otherwise) return JSON. Authentication uses JWT (Bearer token) – include Authorization: Bearer <token> header for protected routes.
1. Authentication & User Management
POST /register
Register a new user.
- Body (JSON):
{
"username": "string (3-30 chars, alphanumeric + underscore)",
"password": "string (min 6 chars)",
"email": "string (optional, valid email)"
}
- Response (201):
{ "id": number, "username": string, "email": string, "createdAt": "ISO" } - Errors: 400 (validation), 409 (username taken)
POST /login
Authenticate user and get JWT.
- Body:
{ "username": string, "password": string } - Response (200):
{ "token": "JWT", "user": { ...user object } }
GET /users/me
Get current authenticated user profile.
- Auth: Required
- Response:
UserProfileobject (id, username, email, fullName, bio, avatarUrl, createdAt, etc.)
PUT /users/me
Update profile fields.
- Body:
{ "fullName": string, "bio": string, "affiliation": string, "orcid": string, "googleScholar": string, "isPrivate": boolean, "securityQuestion": string, "securityAnswer": string } - Response: updated
UserProfile
POST /users/me/avatar
Upload base64 avatar.
- Body:
{ "avatar": "data:image/png;base64,..." } - Response:
{ "avatarUrl": string }
PUT /users/me/password
Change password.
- Body:
{ "oldPassword": string, "newPassword": string }
GET /users/{username}
View public profile (or own if same user, respects privacy).
- Response:
UserProfile(public fields)
POST /users/{username}/follow / DELETE /users/{username}/follow
Follow/unfollow a user.
- Auth: Required
- Response: 204 No Content
GET /users/{username}/following
List users that the given user follows.
- Response:
{ "following": [{ username, fullName, avatarUrl }] }
GET /search/users?q=...
Search users by username/fullName.
- Response: array of
{ id, username, fullName, avatarUrl }
2. Articles & Content
POST /articles
Create a new article (published or draft).
- Auth: Required (author = current user)
- Body:
{
"title": "string (required)",
"abstract": "string (required)",
"body": "HTML content",
"tags": ["string"],
"status": "published | draft",
"relatedArticleIds": [number]
}
- Response:
Articleobject withid,createdAt,updatedAt,slug, etc.
GET /articles/{id}
Get a single article (public if published, or author only if draft).
- Response: full
Articleobject (title, abstract, body, author, likesCount, commentsCount, views, tags, status, etc.)
GET /articles/search
Search articles with filters.
- Query params:
q(title/abstract),author,tag,dateFrom,dateTo,status,page,limit - Response:
{ result: Article[], total: number }
GET /users/me/articles (or /articles?author={username})
Get articles by a specific author. Used in dashboard.
- Response: array of
Article
DELETE /articles/{id}
Delete article (author only).
- Response: 204
PUT /articles/{id}
Update article (author only). Body same as creation.
POST /articles/{id}/like / DELETE /articles/{id}/like
Like/unlike an article.
GET /articles/{id}/analytics
Get analytics for an article (views, likes, comments over time).
- Auth: Required for own articles.
- Query:
range=7d|30d|90d|1y|all - Response:
PaperAnalyticsobject.
3. Messaging & Chat
Private Conversations
GET /conversations List all private conversations for the current user.
- Response: array of
{ with: string, lastMessage: string, lastId: number, unread: number, updatedAt: string }
GET /conversations/{username}/messages Get messages with a specific user (paginated).
- Query:
before(message id),limit(default 20) - Response: array of
Messageobjects (id, body, sentAt, from, status, replyToId, attachments, etc.)
POST /conversations/{username}/messages Send a message (plain text or with attachments).
- Body:
{
"body": "string",
"messageType": "text|image|file|paper|note|sticker|voice|video|audio|poll|rich_text",
"replyToId": number (optional),
"attachments": [ { "name": "string", "url": "string", "type": "string" } ],
"ciphertext": "string" (if encrypted)
}
- Supports multipart/form-data when file attachments are uploaded.
Groups
GET /groups List groups the user is a member of.
- Response: array of
Groupobjects (id, name, memberCount, lastMessage, unread, isAdmin)
POST /groups Create a new group.
- Body:
{ "name": string, "members": [userId] } - Response:
Group
GET /groups/{groupId}/messages Get group messages (paginated same as private).
- Query:
before,limit
POST /groups/{groupId}/messages Send a message to a group.
GET /groups/{groupId}/members List group members.
POST /groups/{groupId}/members
Add a member (admin only). Body { "members": [userId] }
DELETE /groups/{groupId}/members/{userId} Remove member.
POST /groups/{groupId}/admins/{userId} Make user an admin.
DELETE /groups/{groupId} Delete group (admin only).
POST /groups/{groupId}/pin/{messageId} / GET /groups/{groupId}/pinned Pin/unpin messages.
General Messages
GET /messages/{messageId}/edits Get edit history of a message.
- Response: array of
{ id, messageId, body, editedAt }
POST /messages/{messageId}/reactions Add or remove a reaction (emoji).
- Body:
{ "emoji": string }
PUT /messages/{messageId}
Edit a message (author only). Body { "body": string }
DELETE /messages/{messageId} Soft delete (replace body with "[deleted]").
POST /messages/forward Forward one or multiple messages.
- Body:
{ "messageIds": [number], "targetChatId": string }(private username org-{groupId})
POST /messages/{messageId}/thread
Get thread replies (if using message threading). Body { "parentId": number }
Secret Chat (E2EE)
POST /secret-chat/init Initiate a secret chat (E2EE session). Uses Signal protocol.
Typing indicators, read receipts
Handled via WebSocket (see WebSocket section).
4. Notifications & Smart Notifications
GET /notifications
Get notifications for the current user.
- Query:
limit,offset - Response: array of
Notification(id, type, title, body, read, createdAt, link)
POST /notifications/{id}/read
Mark single notification as read.
POST /notifications/read-all
Mark all as read.
WebSocket – real‑time notifications
- Topic:
/user/queue/notifications - Message type:
{ "type": "new_notification", "notification": {...} }
Smart Notification Settings
- GET /users/me/notification-settings – fetch current settings
- POST /users/me/notification-settings – update (body matches
NotificationSettingsinterface)
5. Collaboration & Real‑time Editing (Yjs)
WebSocket signaling for collaborative editor: ws://localhost:9093 (or configurable).
Uses y-websocket protocol. Room names are document IDs.
API endpoints for document management:
- GET /documents/{docId}/references – get references list for a document
- POST /documents/{docId}/references – add a reference (DOI, BibTeX, etc.)
- PUT /documents/{docId}/references/{refId} – update
- DELETE /documents/{docId}/references/{refId}
Version history (if implemented):
- GET /documents/{docId}/versions – list versions
- POST /documents/{docId}/versions – create snapshot
- GET /documents/{docId}/versions/{versionId} – get content
6. Recommendations & Discovery
GET /recommendations/feed
Personalized article recommendations for logged‑in user.
- Query:
limit=15 - Response: array of
RecommendedArticle
GET /recommendations/trending
Global trending articles for non‑authenticated.
- Query:
limit=15 - Response: same format.
GET /recommendations/users
Suggested users to follow.
- Query:
limit=5 - Response: array of
SuggestedUser
GET /discovery/recommendations
General discovery feed (papers, grants, etc.)
POST /discovery/digest
Toggle daily digest email. Body { "enabled": boolean }
GET /discovery/summarize/{paperId}
Get AI‑generated summary of a paper.
- Query:
level=tldr|short|detailed - Response:
PaperSummary
7. Gap Analysis & Knowledge Graph
- GET /gap-analysis/nodes – fetch graph nodes (papers, concepts, gaps)
- GET /gap-analysis/edges – fetch relationships
- POST /gap-analysis/analyze – run gap analysis on a topic (AI)
8. Grant Assistant
- GET /grants/deadlines – upcoming deadlines
- GET /grants/templates – proposal templates
- POST /grants/generate – generate a draft proposal from RFP
- POST /grants/analyze – analyse RFP text
9. Peer Review
- GET /peer-review/submissions – list open submissions (anonymised)
- GET /peer-review/my-reviews – reviews assigned to me
- GET /peer-review/my-credentials – reviewer credentials (ORCID, expertise)
- POST /peer-review/submit – submit a paper for review (anonymous)
- POST /peer-review/submissions/{id}/claim – claim a review
- POST /peer-review/submissions/{id}/review – submit review (scores, comments)
10. Lab Inventory
- GET /inventory/chemicals – list chemicals (with filtering)
- POST /inventory/chemicals – add a chemical
- PUT /inventory/chemicals/{id} – update
- DELETE /inventory/chemicals/{id}
- GET /inventory/chemicals/{id}/incompatibilities – list incompatible chemicals
- GET /inventory/locations – list all location names
- POST /inventory/scan – process barcode scan
11. RAG Assistant (Research Assistant)
- POST /ai/rag-chat – chat with RAG (uses indexed documents)
- Body:
{ "messages": [...], "sources": [...] }– actual backend expectsmessagesarray and optionallysourcesmetadata. - Response:
{ "reply": "string", "sources": [...] }
- Body:
- POST /ai/chat – generic AI chat (LLM proxy)
- Body:
{ "provider": "ollama|openai|java-backend", "model": "string", "messages": [...] }
- Body:
- POST /ai/command-palette/predict – AI suggestions for command palette
- Body:
{ "query": "string", "context": {...} } - Response:
{ "predictions": [ { id, name, description, source, confidence, perform } ] }
- Body:
Document indexing (RAG)
- POST /documents/{docId}/rag-index – index a document (PDF, txt, etc.) – server‑side indexing.
- GET /documents/{docId}/rag-status – check indexing status.
12. Workspace & SmartGlass
- GET /workspace/panels – user's saved panel layouts (presets)
- POST /workspace/panels – save layout
- DELETE /workspace/panels/{id}
13. Data Hub & Research Objects
GET /protocols – list lab protocols
POST /protocols – create new protocol
PUT /protocols/{id} – update
POST /protocols/{id}/steps – add a step
PUT /protocols/{id}/steps/{stepId} – update step
POST /protocols/{id}/fork – fork a protocol
GET /repository/objects – list research objects (datasets, code, etc.)
POST /repository/objects – upload a file (multipart form data)
DELETE /repository/objects/{id}
GET /preregistrations – list preregistrations
POST /preregistrations – submit a preregistration (with timestamp)
14. Projects
- GET /projects – user's projects
- GET /projects/{projectId} – details (members, tasks, outputs)
- PUT /projects/{projectId} – update
- POST /projects – create project
- POST /projects/{projectId}/members – add member
- PUT /projects/{projectId}/members/{userId} – change role
- DELETE /projects/{projectId}/members/{userId}
- GET /projects/{projectId}/tasks – kanban tasks
- POST /projects/{projectId}/tasks – add task
- PUT /projects/{projectId}/tasks/{taskId} – update task (including column)
- DELETE /projects/{projectId}/tasks/{taskId}
- POST /projects/{projectId}/outputs – link an external output (article, dataset)
15. Two‑Factor Authentication (TOTP)
- POST /users/me/2fa/enable – generate TOTP secret and QR code
- Response:
{ "secret": "string", "qrCode": "data:image/png;base64,..." }
- Response:
- POST /users/me/2fa/verify – verify a TOTP code to enable 2FA
- Body:
{ "code": "string" }
- Body:
- POST /users/me/2fa/disable – disable 2FA
- GET /users/me/2fa/backup-codes – retrieve backup codes (after verification)
- Query:
?regenerate=trueto generate new ones
- Query:
16. Password Reset & Security
- POST /forgot-password – request security question
- Body:
{ "username": string } - Response:
{ "question": "string" }
- Body:
- POST /reset-password – reset password using answer
- Body:
{ "username": string, "answer": string, "newPassword": string }
- Body:
17. Polls & Quizzes
- GET /polls/{pollId} – get poll/quiz data
- POST /polls/{pollId}/vote – record vote(s)
- Body:
{ "optionIds": [number] }
- Body:
- POST /polls – create a poll (if implemented in your chat)
18. Event & Conference (WebRTC)
- GET /conference/{roomId}/token – get a TURN/STUN token (if using external service)
- WebSocket signaling for WebRTC:
/conference/{roomId}(using youruseSignalinghook)
19. Admin & Stats
- GET /admin/stats – platform stats (total users, articles, etc.) – admin only.
- GET /users/me/analytics – personalised analytics for dashboard
20. WebSocket Endpoints
- Main WebSocket for real‑time messaging and presence:
ws://localhost:8080/ws(or relative/ws) - Collaboration WebSocket (Yjs):
ws://localhost:9093 - Conference signaling WebSocket:
ws://localhost:8080/conference/{roomId}
WebSocket Message Types (for main chat)
new_message(private) –{ type: "new_message", message: Message }new_group_messagetyping–{ type: "typing", from: string, to: string, isTyping: boolean }message_status–{ type: "message_status", messageId: number, status: "sent|delivered|seen" }reaction–{ type: "reaction", messageId: number, userId: number, emoji: string }message_edited/message_deletedmessage_pinned–{ type: "message_pinned", groupId: number, pinned: PinnedMessage }new_notification–{ type: "new_notification", notification: Notification }presence–{ type: "presence", username: string, isOnline: boolean, lastSeen: string }presence_ping– client should send periodically to keep session alive.
Error Handling
All endpoints return standard HTTP status codes:
200– success201– created400– bad request (validation error)401– unauthorised (missing or invalid token)403– forbidden (e.g., trying to edit another user's article)404– resource not found409– conflict (e.g., duplicate username)500– internal server error
Error response body: { "error": "Description of the problem" }
Authentication
Except for login, register, password reset, and public article views, all endpoints require a valid JWT in the Authorization header.
The JWT should be obtained from /login. The token contains the user ID, username, and expiry.
Data Models (example)
UserProfile
{
id: number;
username: string;
email?: string;
fullName?: string;
bio?: string;
avatarUrl?: string;
affiliation?: string;
orcid?: string;
googleScholar?: string;
followersCount: number;
followingCount: number;
articlesCount: number;
isPrivate: boolean;
isEmailVerified: boolean;
securityQuestion?: string;
twoFactorEnabled: boolean;
createdAt: string;
}
Article
{
id: number;
title: string;
abstract: string;
body: string;
author: UserProfile;
tags: string[];
status: "published" | "draft";
views: number;
likesCount: number;
commentsCount: number;
createdAt: string;
updatedAt: string;
}
Message (private)
{
id: number;
body: string;
sentAt: string;
from: string;
fromUserId: number;
to?: string;
replyToId?: number;
replyToBody?: string;
status: "sending"|"sent"|"delivered"|"seen";
encrypted?: boolean;
ciphertext?: string;
reactions: Reaction[];
editedAt?: string;
deletedAt?: string;
attachments: UploadedFile[];
messageType: MessageType;
paperData?: PaperData;
}
Xet Storage Details
- Size:
- 17.1 kB
- Xet hash:
- 2ebf9e031a29a25127e3ce4e31f6cf9843cc0659bdbbfba89b714c14049a137f
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.