Research Platform 2.0 - Decoupled Enterprise Academic Repository & Scientific Collaboration Portal
Welcome to the comprehensive technical documentation for Research Platform 2.0. This document serves as the single source of truth for developers, system architects, and DevOps engineers working on, maintaining, or deploying the platform.
1. Project Overview
Research Platform 2.0 is an enterprise-grade academic repository and scientific collaboration ecosystem. Going far beyond traditional archive databases (like arXiv or SSRN), Research Platform 2.0 integrates advanced features designed to facilitate the entire lifecycle of scientific research.
The ecosystem is engineered to support:
- Intelligent Hypothesis & Literature Discovery: Powered by customized citation analytics and semantic search.
- Collaborative Research Workspaces: Shared project spaces with granular access controls and dataset repositories.
- Real-Time Synchronous Co-Authoring: Leveraging WebSockets and Operational Transformation algorithms.
- Double-Blind Peer Review Workflows: State-machine-based pipelines governing reviewer matching, structure feedback, and editor decisions.
- Extensible Sandboxed Tools Store: Allowing developers to build, validate, and deploy modular tools (e.g., custom citation count visualizations, format converters) directly inside the platform's iframe sandbox.
Core Architecture Goals
- High Modularity: Separation of concerns through a three-tier decoupled architecture.
- Observability: Complete transparency into system health using OpenTelemetry, Prometheus, Grafana, and Tempo.
- Developer Productivity: Custom developer CLI tools implemented in both Node.js and Go to bootstrap, validate, and deploy extensions seamlessly.
- High Resource-Efficiency: Tailored Docker and deployment strategies to run performantly on developer workstations or cloud containers.
2. Table of Contents
- Project Overview
- Ecosystem Architecture
- Technology Stack
- Docker & Container Deployment
- Database Architecture & Entity-Relationship Schema
- Complete Database Migration DDL Script
- Backend Service Layer Deep Dive
- API Specifications & REST Reference
- Real-time Collaboration & WebSocket Protocol
- Developer CLI Specification (Node.js & Go)
- CLI Interactive Command Walkthroughs
- Observability, APM & Observability Configuration
- Testing Infrastructure & Mocking Profiles
- Troubleshooting & DevOps Runbook
3. Ecosystem Architecture
Research Platform 2.0 is designed around a modern, decoupled client-server architecture. The system separation guarantees high maintainability and security.
System Topography
The platform follows a three-tier topology:
graph TD
Client[Web Browser / Developer CLI]
Nginx[NGINX Front-End Web Server]
Backend[Spring Boot Backend JVM]
Database[(MySQL 8 Database)]
OtelCollector[OpenTelemetry Collector]
Jaeger[Jaeger Distributed Tracing]
Prometheus[Prometheus Metrics]
Loki[Grafana Loki Logs]
Client -->|HTTP/WebSockets| Nginx
Nginx -->|Static Assets| Nginx
Nginx -->|Reverse Proxy /api| Backend
Backend -->|JDBC Driver| Database
Backend -->|gRPC Spans| OtelCollector
OtelCollector --> Jaeger
OtelCollector --> Prometheus
OtelCollector --> Loki
Decoupled Subsystems
Frontend Presentation Tier:
- Implemented as a Single Page Application (SPA) using React 18 and Vite.
- Builds into static HTML/JS/CSS assets which are served efficiently via NGINX.
- Integrates with the backend exclusively via RESTful APIs and secure STOMP-over-WebSocket connections.
Backend Application Tier:
- Powered by Spring Boot 2.7.x running on Java 17 (Eclipse Temurin JRE).
- Provides stateless REST endpoints protected via a JSON Web Token (JWT) filter layer.
- Embeds business rules, database transactions, automated workflows, and WebSocket brokers.
Data Tier:
- Relational schema managed by MySQL 8.
- Contains indexed tables for high-performance retrieval of metadata, user records, tags, and reviews.
- The database is isolated within the internal Docker container network, unreachable from the public internet.
Monitoring & Observability Tier:
- Runs sidecar containers for Prometheus, Grafana, OpenTelemetry Collector, Loki, Promtail, and Tempo.
- Collects system metrics, trace logs, span context, and database query executions to provide real-time dashboard visibility.
4. Technology Stack
Backend Application Tier
- Language: Java 17 (LTS)
- Framework: Spring Boot 2.7.12
- Data Mapper: Spring Data JPA / Hibernate Core 5.6
- Security: Spring Security (JWT Stateless Auth)
- API Documentation: Springfox Swagger 2 / OpenAPI 2.0
- Serialization: Jackson JSON Databind
- WebSocket Protocol: Spring WebSocket MessageBroker with STOMP support
- Testing: JUnit 5, Mockito, AssertJ, Spring Boot Test (MockMvc)
- Build Engine: Apache Maven 3.8.x
Frontend Presentation Tier
- Language: TypeScript / ECMAScript 6+
- Framework: React 18.2
- Build Tool: Vite 4.x
- Router: React Router DOM 6.x
- HTTP Client: Axios (with custom interceptors for JWT injection)
- WebSocket Client:
@stomp/stompjs&sockjs-client - Styling Engine: Vanilla CSS with modern custom variables, CSS Grid, and Flexbox layouts.
DevOps & Observability
- Virtualization: Docker Engine 24+ / Docker Compose V2
- Front-End Proxy: NGINX 1.27 (Alpine distribution)
- Distributed Tracing: OpenTelemetry Javaagent 1.25.0 / Tempo
- Metrics Aggregator: Prometheus 2.45
- Log Aggregator: Grafana Loki 2.8.2 / Promtail
- Dashboards: Grafana 10.0.1
5. Docker & Container Deployment
To facilitate easy local setups and eliminate dependency mismatch issues across macOS, Windows, and Linux, the entire application stack is containerized.
Backend Dockerfile (Dockerfile)
The backend Dockerfile avoids running heavy Maven builds inside virtualized disks (which cause severe IO bottlenecks on macOS Colima environments). Instead, it copies the pre-built jar file compiled on the host.
FROM eclipse-temurin:17-jre-alpine
WORKDIR /app
COPY target/*.jar app.jar
RUN mkdir -p /app/uploads
RUN mkdir -p /app/data
EXPOSE 9092 9093
ENV SPRING_PROFILES_ACTIVE=prod
ENTRYPOINT ["java", "-jar", "app.jar"]
Frontend Dockerfile (front/Dockerfile)
Similarly, the frontend Dockerfile relies on the host compiling the production build. The image simply encapsulates NGINX and the built HTML assets.
FROM nginx:1.27-alpine
COPY nginx.conf /etc/nginx/conf.d/default.conf
COPY dist /usr/share/nginx/html
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
Global Orchestration (docker-compose.yml)
The orchestration links the subsystems together over an isolated virtual bridge network.
version: '3.8'
services:
db:
image: mysql:8.0.33
container_name: projects-db
restart: always
environment:
MYSQL_DATABASE: projects
MYSQL_ROOT_PASSWORD: root_password_sec
MYSQL_USER: projects_user
MYSQL_PASSWORD: projects_password
ports:
- "3306:3306"
volumes:
- db-data:/var/lib/mysql
healthcheck:
test: ["CMD", "mysqladmin", "ping", "-h", "localhost", "-u", "root", "-p$$MYSQL_ROOT_PASSWORD"]
timeout: 10s
retries: 5
backend:
build:
context: ./
dockerfile: Dockerfile
container_name: projects-backend
restart: always
ports:
- "9092:9092"
- "9093:9093"
environment:
- SPRING_DATASOURCE_URL=jdbc:mysql://db:3306/projects?useSSL=false&allowPublicKeyRetrieval=true&serverTimezone=UTC
- SPRING_DATASOURCE_USERNAME=projects_user
- SPRING_DATASOURCE_PASSWORD=projects_password
depends_on:
db:
condition: service_healthy
volumes:
- uploads-data:/app/uploads
- app-sqlite:/app/data
frontend:
build:
context: ./front
dockerfile: Dockerfile
container_name: projects-frontend
restart: always
ports:
- "80:80"
depends_on:
- backend
volumes:
db-data:
uploads-data:
app-sqlite:
networks:
default:
name: projects_ierepo-network
6. Database Architecture & Entity-Relationship Schema
The platform relies on a normalized relational database schema modeled in MySQL 8. Below is the detailed structural description of the tables, indexes, and relationships.
Database ER Diagram
+------------------+ +------------------+ +------------------+
| users |1 1| profiles | | tool_installs |
+------------------+----------+------------------+ +------------------+
| id (PK) | | id (PK) | +--->| id (PK) |
| username (Unique)| | user_id (FK) | | | user_id (FK) |
| email (Unique) | | bio | | | tool_id (FK) |
| password_hash | | affiliation | | | active |
| role | +------------------+ | +------------------+
+--------+---------+ |
|1 |
| |
v * |
+--------+---------+ +------------------+ | +------------------+
| articles |1 *| comments | | | tools |
+------------------+----------+------------------+ | +------------------+
| id (PK) | | id (PK) | | | id (PK) |
| title | | article_id (FK) | +----+ author_id (FK) |
| abstract | | user_id (FK) | | name |
| author_id (FK) | | content | | code (TEXT) |
| status | | parent_id (FK) | | is_public |
+--------+---------+ +------------------+ | requires_pro |
|1 +------------------+
|
v *
+--------+---------+
| peer_reviews |
+------------------+
| id (PK) |
| article_id (FK) |
| reviewer_id (FK) |
| score |
| decision |
+------------------+
Table Definitions & Constraints
1. users
Stores security credentials, platform roles, and authentication status.
- Fields:
id: BIGINT (PK, Auto-Increment)username: VARCHAR(50) (Unique, Not Null)email: VARCHAR(100) (Unique, Not Null)password: VARCHAR(255) (Not Null - contains BCrypt hash)role: VARCHAR(20) (Not Null -STUDENT,RESEARCHER,PROFESSOR,ADMIN)subscription_plan: VARCHAR(20) (Not Null -FREE,PRO)created_at: TIMESTAMP (Default CURRENT_TIMESTAMP)
- Indexes:
idx_users_usernameonusernameidx_users_emailonemail
2. profiles
Biographical and institutional information linked 1-to-1 with a user.
- Fields:
id: BIGINT (PK, Auto-Increment)user_id: BIGINT (FK referencingusers.id, Unique, Not Null)first_name: VARCHAR(50)last_name: VARCHAR(50)affiliation: VARCHAR(255)biography: TEXTorcid: VARCHAR(19) (Orcid academic ID format, e.g.0000-0002-1825-0097)
- Constraints:
- Foreign key
fk_profiles_userON DELETE CASCADE
- Foreign key
3. articles
Core document storage entity containing preprints or published articles.
- Fields:
id: BIGINT (PK, Auto-Increment)author_id: BIGINT (FK referencingusers.id, Not Null)title: VARCHAR(255) (Not Null)abstract: TEXT (Not Null)content_path: VARCHAR(255) (Path to PDF file in upload directory)doi: VARCHAR(100) (Unique)status: VARCHAR(30) (Not Null -DRAFT,SUBMITTED,UNDER_REVIEW,ACCEPTED,REJECTED)category: VARCHAR(50)downloads: INT (Default 0)created_at: TIMESTAMPupdated_at: TIMESTAMP
- Indexes:
idx_articles_authoronauthor_ididx_articles_statusonstatus- Fulltext index
idx_articles_texton (title,abstract)
4. tools
Custom modular scripts uploaded via developer CLI that run inside the platform sandbox.
- Fields:
id: BIGINT (PK, Auto-Increment)author_id: BIGINT (FK referencingusers.id, Not Null)name: VARCHAR(100) (Not Null)description: VARCHAR(255)version: VARCHAR(20) (Not Null)category: VARCHAR(50)tags: VARCHAR(255) (Comma-separated tag list)icon: VARCHAR(10) (Default "🔧")is_public: BOOLEAN (Default TRUE)requires_pro: BOOLEAN (Default FALSE)code: LONGTEXT (The sandboxed HTML/JS contents executed in sandbox)license: VARCHAR(50) (Default "MIT")downloads: INT (Default 0)rating: DOUBLErating_count: INT (Default 0)created_at: TIMESTAMP
- Indexes:
idx_tools_authoronauthor_ididx_tools_categoryoncategory
5. tool_installations
Tracks which custom tools users have added to their active workspace panels.
- Fields:
id: BIGINT (PK, Auto-Increment)user_id: BIGINT (FK referencingusers.id, Not Null)tool_id: BIGINT (FK referencingtools.id, Not Null)installed_at: TIMESTAMPactive: BOOLEAN (Default TRUE)
- Constraints:
- Composite Unique constraint
uq_user_toolon (user_id,tool_id)
- Composite Unique constraint
7. Complete Database Migration DDL Script
To aid developers setting up a fresh MySQL installation without relying on JPA Hibernate DDL auto-generation (which is bad practice in production environments), the complete DDL schema is provided below:
-- Disable foreign key checks to allow clean table creation
SET FOREIGN_KEY_CHECKS = 0;
-- -----------------------------------------------------
-- Table `users`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `users` ;
CREATE TABLE IF NOT EXISTS `users` (
`id` BIGINT NOT NULL AUTO_INCREMENT,
`username` VARCHAR(50) NOT NULL,
`email` VARCHAR(100) NOT NULL,
`password` VARCHAR(255) NOT NULL,
`role` VARCHAR(20) NOT NULL DEFAULT 'STUDENT',
`subscription_plan` VARCHAR(20) NOT NULL DEFAULT 'FREE',
`created_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (`id`),
UNIQUE INDEX `uq_users_username` (`username` ASC),
UNIQUE INDEX `uq_users_email` (`email` ASC)
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COLLATE = utf8mb4_unicode_ci;
-- -----------------------------------------------------
-- Table `profiles`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `profiles` ;
CREATE TABLE IF NOT EXISTS `profiles` (
`id` BIGINT NOT NULL AUTO_INCREMENT,
`user_id` BIGINT NOT NULL,
`first_name` VARCHAR(50) NULL,
`last_name` VARCHAR(50) NULL,
`affiliation` VARCHAR(255) NULL,
`biography` TEXT NULL,
`orcid` VARCHAR(19) NULL,
PRIMARY KEY (`id`),
UNIQUE INDEX `uq_profiles_user_id` (`user_id` ASC),
CONSTRAINT `fk_profiles_user`
FOREIGN KEY (`user_id`)
REFERENCES `users` (`id`)
ON DELETE CASCADE
ON UPDATE CASCADE
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COLLATE = utf8mb4_unicode_ci;
-- -----------------------------------------------------
-- Table `articles`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `articles` ;
CREATE TABLE IF NOT EXISTS `articles` (
`id` BIGINT NOT NULL AUTO_INCREMENT,
`author_id` BIGINT NOT NULL,
`title` VARCHAR(255) NOT NULL,
`abstract` TEXT NOT NULL,
`content_path` VARCHAR(255) NULL,
`doi` VARCHAR(100) NULL,
`status` VARCHAR(30) NOT NULL DEFAULT 'DRAFT',
`category` VARCHAR(50) NULL,
`downloads` INT NOT NULL DEFAULT 0,
`created_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
`updated_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
PRIMARY KEY (`id`),
UNIQUE INDEX `uq_articles_doi` (`doi` ASC),
INDEX `idx_articles_author` (`author_id` ASC),
INDEX `idx_articles_status` (`status` ASC),
FULLTEXT INDEX `idx_articles_text_search` (`title`, `abstract`),
CONSTRAINT `fk_articles_author`
FOREIGN KEY (`author_id`)
REFERENCES `users` (`id`)
ON DELETE RESTRICT
ON UPDATE CASCADE
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COLLATE = utf8mb4_unicode_ci;
-- -----------------------------------------------------
-- Table `tools`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `tools` ;
CREATE TABLE IF NOT EXISTS `tools` (
`id` BIGINT NOT NULL AUTO_INCREMENT,
`author_id` BIGINT NOT NULL,
`name` VARCHAR(100) NOT NULL,
`description` VARCHAR(255) NULL,
`version` VARCHAR(20) NOT NULL DEFAULT '1.0.0',
`category` VARCHAR(50) NOT NULL DEFAULT 'utility',
`tags` VARCHAR(255) NULL,
`icon` VARCHAR(10) NOT NULL DEFAULT '🔧',
`is_public` BOOLEAN NOT NULL DEFAULT TRUE,
`requires_pro` BOOLEAN NOT NULL DEFAULT FALSE,
`code` LONGTEXT NOT NULL,
`license` VARCHAR(50) NOT NULL DEFAULT 'MIT',
`downloads` INT NOT NULL DEFAULT 0,
`rating` DOUBLE NULL,
`rating_count` INT NOT NULL DEFAULT 0,
`created_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (`id`),
INDEX `idx_tools_author` (`author_id` ASC),
INDEX `idx_tools_category` (`category` ASC),
CONSTRAINT `fk_tools_author`
FOREIGN KEY (`author_id`)
REFERENCES `users` (`id`)
ON DELETE CASCADE
ON UPDATE CASCADE
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COLLATE = utf8mb4_unicode_ci;
-- -----------------------------------------------------
-- Table `tool_installations`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `tool_installations` ;
CREATE TABLE IF NOT EXISTS `tool_installations` (
`id` BIGINT NOT NULL AUTO_INCREMENT,
`user_id` BIGINT NOT NULL,
`tool_id` BIGINT NOT NULL,
`installed_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
`active` BOOLEAN NOT NULL DEFAULT TRUE,
PRIMARY KEY (`id`),
UNIQUE INDEX `uq_user_tool_install` (`user_id` ASC, `tool_id` ASC),
INDEX `idx_installations_tool` (`tool_id` ASC),
CONSTRAINT `fk_installs_user`
FOREIGN KEY (`user_id`)
REFERENCES `users` (`id`)
ON DELETE CASCADE
ON UPDATE CASCADE,
CONSTRAINT `fk_installs_tool`
FOREIGN KEY (`tool_id`)
REFERENCES `tools` (`id`)
ON DELETE CASCADE
ON UPDATE CASCADE
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COLLATE = utf8mb4_unicode_ci;
-- Enable foreign key checks again
SET FOREIGN_KEY_CHECKS = 1;
8. Backend Service Layer Deep Dive
The Spring Boot backend delegates business logic to specialized Java services. Below are class representations and detailed service layer interface summaries.
UserService
Defines the management boundaries for user registrations, updates, and profile configurations.
package ir.ac.ut.ece.ie.service;
import ir.ac.ut.ece.ie.model.User;
import ir.ac.ut.ece.ie.dto.UserDTO;
import java.util.Optional;
public interface UserService {
User registerUser(UserDTO registrationDto);
Optional<User> findUserById(Long id);
Optional<User> findUserByUsername(String username);
void updatePassword(Long userId, String oldPassword, String newPassword);
void deleteUser(Long id);
}
GapAnalysisService
Implements natural language and reference analysis to find unexplored academic avenues.
package ir.ac.ut.ece.ie.service;
import ir.ac.ut.ece.ie.dto.GapReportDTO;
import java.io.InputStream;
public interface GapAnalysisService {
GapReportDTO analyzeText(String fullText);
GapReportDTO analyzePdf(InputStream pdfStream);
void crossReferenceDataHubs(GapReportDTO draftReport);
}
PeerReviewService
Governs the state transitions of articles through review cycles.
package ir.ac.ut.ece.ie.service;
import ir.ac.ut.ece.ie.model.PeerReview;
import ir.ac.ut.ece.ie.dto.ReviewFeedbackDTO;
import java.util.List;
public interface PeerReviewService {
PeerReview assignReviewer(Long articleId, Long reviewerId);
PeerReview submitFeedback(Long reviewId, ReviewFeedbackDTO feedback);
List<PeerReview> getReviewsForArticle(Long articleId);
void updateReviewDecision(Long reviewId, String decision);
}
ToolService
Integrates the custom iframe widgets store and supports developer CLI interactions.
package ir.ac.ut.ece.ie.service;
import ir.ac.ut.ece.ie.model.Tool;
import ir.ac.ut.ece.ie.dto.ToolDTO;
import java.util.List;
import java.util.Map;
public interface ToolService {
Tool createTool(Tool tool, List<Object> screenshots, Long userId, String username);
Tool updateTool(Long id, Tool updates, List<Object> screenshots, Long userId, boolean isAdmin);
void deleteTool(Long id, Long userId, boolean isAdmin);
List<Tool> getTrendingTools(int limit);
List<Tool> getPopularTools(int limit);
Map<String, Object> getUserToolState(Long toolId, Long userId);
Object installTool(Long toolId, Long userId);
void uninstallTool(Long toolId, Long userId);
String downloadTool(Long id, Long userId, String username, Object request);
}
9. API Specifications & REST Reference
All authenticated routes require a Bearer <token> string inside the Authorization header.
9.1 Authentication Controller (/api/auth)
1. POST /api/auth/register
- Description: Registers a new researcher or student account.
- Request Body:
{ "username": "tahamajs", "password": "SecurePassword123!", "email": "tahamajs@ece.ut.ac.ir", "role": "RESEARCHER" } - Responses:
201 Created: Contains success flag and generated ID.400 Bad Request: Email validation failed.409 Conflict: Username or Email already registered.
2. POST /api/auth/login
- Description: Verifies credentials and generates a JWT session token.
- Request Body:
{ "username": "tahamajs", "password": "SecurePassword123!" } - Responses:
200 OK:{ "success": true, "token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...", "username": "tahamajs", "role": "RESEARCHER" }401 Unauthorized: Invalid credentials.
3. GET /api/auth/me
- Description: Retrieves current user session metadata.
- Responses:
200 OK:{ "success": true, "user": { "id": 105, "username": "tahamajs", "email": "tahamajs@ece.ut.ac.ir", "role": "RESEARCHER", "subscriptionPlan": "PRO" } }
9.2 Custom Tools Controller (/api/tools)
1. POST /api/tools/deploy
- Description: Deploys a new sandboxed HTML component to the platform.
- Request Body:
{ "name": "Bibtex Converter", "description": "Transforms plain bibliography texts to BibTeX entries.", "version": "1.0.0", "category": "productivity", "tags": "productivity,citation", "icon": "📊", "isPublic": true, "requiresPro": false, "code": "<!DOCTYPE html><html><body><script>...</script></body></html>" } - Responses:
201 Created:{ "success": true, "message": "Tool deployed successfully", "toolId": 42, "tool": { "id": 42, "name": "Bibtex Converter" }, "deploymentUrl": "http://localhost:5173/tools/42", "timestamp": "2026-07-11T11:15:00" }401 Unauthorized: Session token expired or missing.
2. PUT /api/tools/{id}
- Description: Updates the configuration and code layout of a tool.
- Content-Type: Supports
application/jsonpayload (aligned for CLI updates) ormultipart/form-data. - Request Body:
{ "name": "Bibtex Converter Pro", "description": "Premium bibliography translation engine.", "version": "1.1.0", "category": "productivity", "isPublic": true, "requiresPro": true, "code": "<!DOCTYPE html><html><body>Enhanced logic here...</body></html>" } - Responses:
200 OK:{ "success": true, "message": "Tool updated successfully", "tool": { "id": 42, "name": "Bibtex Converter Pro", "version": "1.1.0" }, "timestamp": "2026-07-11T11:15:30" }403 Forbidden: User is not the author of this tool and is not an Administrator.404 Not Found: Tool ID does not exist.
3. GET /api/tools
- Description: Queries all public tools with pagination and search limits.
- Query Parameters:
page: default0limit: default20(max100)search: filters by tool name or category.
- Responses:
200 OK:{ "success": true, "tools": [ { "id": 42, "name": "Bibtex Converter Pro", "category": "productivity", "version": "1.1.0", "isPublic": true, "downloads": 15 } ], "total": 1, "page": 0, "limit": 20 }
4. GET /api/tools/{id}
- Description: Retrieves complete configuration, ratings, and download analytics for a specific tool.
- Responses:
200 OK:{ "success": true, "tool": { "id": 42, "name": "Bibtex Converter Pro", "version": "1.1.0", "category": "productivity", "authorUsername": "tahamajs", "isPublic": true, "requiresPro": true, "downloads": 15, "rating": 4.8, "ratingCount": 5, "createdAt": "2026-07-10T14:30:00Z", "updatedAt": "2026-07-11T11:15:30Z" } }
5. DELETE /api/tools/{id}
- Description: Permanently removes a tool from the repository.
- Responses:
200 OK:{ "success": true, "message": "Tool deleted successfully", "toolId": 42 }403 Forbidden: User has no permission to remove this tool.
6. GET /api/tools/{id}/logs
- Description: Queries sandbox deployment and execution log traces for a specific tool.
- Query Parameters:
limit: default20
- Responses:
200 OK:{ "success": true, "logs": [ { "timestamp": "2026-07-11T11:32:37Z", "level": "INFO", "message": "Initiating sandbox tool build pipeline..." } ], "count": 1, "timestamp": "2026-07-11T11:32:47Z" }401 Unauthorized: Session token is expired or missing.
7. GET /api/tools/logs
- Description: Queries general system-level deployment and registry synchronization logs.
- Query Parameters:
limit: default20
- Responses:
200 OK:{ "success": true, "logs": [ { "timestamp": "2026-07-11T11:32:37Z", "level": "INFO", "message": "Tool store registry initialized." } ], "count": 1, "timestamp": "2026-07-11T11:32:47Z" }
10. Real-time Collaboration & WebSocket Protocol
To provide responsive synchronous cooperation features, the platform uses Spring WebSockets using STOMP.
Connection Architecture
- Client initiates connection handshake using SockJS fallback mechanisms:
ws://localhost:9092/ws - During the standard HTTP Upgrade handshake, a security filter verifies the JWT token sent in headers.
- Message headers use standard STOMP conventions (
CONNECT,SUBSCRIBE,SEND,DISCONNECT).
STOMP Message Routing Specification
1. Collaborative Document Editing (OT)
- Subscription Destination:
/topic/document/{documentId}/operations - Application Publish Destination:
/app/document/{documentId}/operations.apply - Payload format:
{ "authorId": 105, "revision": 12, "operation": { "type": "INSERT", "position": 256, "text": "Furthermore, the evaluation indicates..." } }
2. Project Workspace Chat
- Subscription Destination:
/topic/project/{projectId}/chat - Application Publish Destination:
/app/project/{projectId}/chat.sendMessage - Payload format:
{ "sender": "tahamajs", "content": "I am updating the references in section 3.", "type": "CHAT" }
11. Developer CLI Specification (Node.js & Go)
The platform provides developers with CLI utilities. Both versions are designed to be unified in options, commands, and layouts.
CLI Installation
Node.js
Requires Node.js (v18+) to run.
cd Projects/cli
npm install -g .
ie-cli help
Go (Compiled Binary)
Standalone executable compiled binary. Move to /usr/local/bin for system-wide access.
cd Projects/cli
go build -o ie-cli main.go
./ie-cli help
Parameter Parser Logic
A custom argument parser separates flag types based on a value flag lookup map (--username, -u, --password, -p, --host, --file, -f, --id, --limit).
- Boolean flags like
--public,--private, and--prowill not consume subsequent positional parameters. - If a value flag lacks an argument, it is safely initialized to an empty string.
12. CLI Interactive Command Walkthroughs
The following runs simulate the terminal interactions when using the custom Developer CLI.
1. init - Creating a New Tool Sandbox
This command interactively prompts for metadata and generates local templates.
$ ie-cli init
Initializing new custom tool project
────────────────────────────────────
Tool Name (e.g. Citation Counter): PDF Reader
Short Description: Renders PDF contents dynamically.
Author Name: Taha Majlesi
Category [ai|statistics|data-viz|productivity|utility]: productivity
Version (default 1.0.0): 1.0.0
Publish to tool store? [Y/n]: Y
Require Pro subscription? [y/N]: N
✔ Created tool.json
✔ Created tool.html
Project ready! Next steps:
1. Edit tool.html with your custom UI and JavaScript logic
2. Edit tool.json to update metadata (name, description, category…)
3. Validate before deploying:
ie-cli validate
4. Log in to the platform:
ie-cli login --username <you> --password <pass>
5. Deploy:
ie-cli deploy --file ./tool.html
2. login - Session Authentications
Authenticates and locks credentials securely inside ~/.ie-research-cli.json with 0600 permissions.
$ ie-cli login -u tahamajs -p SecurePassword123! --host http://localhost:9092
Login
─────
⠋ Authenticating as tahamajs...
✔ Logged in as tahamajs (token saved to /Users/taha/.ie-research-cli.json)
3. whoami - Show Session Details
Fetches live account characteristics using the stored JWT token.
$ ie-cli whoami
Account Details
───────────────
⠙ Retrieving account details...
✔ Account details:
Username : tahamajs
Email : tahamajs@ece.ut.ac.ir
Role : RESEARCHER
Plan : PRO
Host : http://localhost:9092
Logged in : 7/11/2026, 11:15:00 AM
4. validate - Verifying Files
Performs local syntax parsing and sizing validation.
$ ie-cli validate -f ./tool.html
Validating tool configuration
─────────────────────────────
✔ tool.html found (2.4 KB)
✔ tool.json parsed successfully
✔ Tool Name: 'PDF Reader' version 1.0.0
All checks passed – tool is valid and ready to deploy!
5. deploy - Publishing a Tool
Deploys a new tool to the store. Supports visibility options: --public, --private, and subscription access: --pro.
$ ie-cli deploy -f ./tool.html --private
Deploying tool to store
───────────────────────
ℹ Tool : PDF Reader v1.0.0
ℹ File : /Users/taha/Projects/tool.html (2 KB)
ℹ Server : http://localhost:9092
ℹ User : tahamajs
⠹ Uploading tool to platform...
✔ Deployment successful! 🚀
Tool ID : 42
URL : http://localhost:9092/tools/42
Tip: run ie-cli status --id 42 to check live status.
6. list - Reviewing Deployed Collections
Retrieves all author-owned tools in an aligned terminal table with download counters.
$ ie-cli list
Your Deployed Tools
───────────────────
⠸ Fetching tool list...
✔ Found 1 tool(s)
ID │ Name │ Category │ Version │ Public │ Downloads
─────────┼────────────────────────────────┼──────────────┼────────────┼──────────┼───────────
42 │ PDF Reader │ productivity │ 1.0.0 │ No │ 0
7. status - Detailed Analytics Inspection
Displays live download rates and reviewer evaluation metrics.
$ ie-cli status --id 42
Tool Status Details
───────────────────
⠴ Fetching status for tool 42...
✔ Status for: PDF Reader
ID : 42
Name : PDF Reader
Version : 1.0.0
Category : productivity
Author : tahamajs
Public : No
Requires Pro : No
Downloads : 0
Rating : —
Created : 7/11/2026, 11:15:05 AM
Updated : 7/11/2026, 11:15:05 AM
URL : http://localhost:9092/tools/42
13. Observability, APM & Observability Configuration
To monitor performance and query traces, the platform integrates a complete observability cluster alongside the application containers.
Observability Architecture
+--------------------+
| Spring Boot JVM |
| (OTel Java Agent) |
+---------+----------+
|
| (OTLP Spans via gRPC)
v
+---------+----------+
| OTel Collector |
+----+----+----+-----+
| | |
| | +--------------------> Prometheus (Metrics on :9090)
| +-------------------------> Grafana Loki (Logs on :3100)
+------------------------------> Tempo (Trace Spans on :3200)
Configuration Files
1. OpenTelemetry Collector (otel-collector-config.yaml)
Receives traces, metrics, and logs from the application and exports them to their respective databases.
receivers:
otlp:
protocols:
grpc:
http:
processors:
batch:
exporters:
prometheus:
endpoint: "0.0.0.0:8889"
namespace: "projects"
otlp/tempo:
endpoint: "tempo:4317"
tls:
insecure: true
loki:
endpoint: "http://loki:3100/loki/api/v1/push"
service:
pipelines:
traces:
receivers: [otlp]
processors: [batch]
exporters: [otlp/tempo]
metrics:
receivers: [otlp]
processors: [batch]
exporters: [prometheus]
logs:
receivers: [otlp]
processors: [batch]
exporters: [loki]
2. Prometheus Configuration (prometheus.yml)
Scrapes metrics exposed by the OTel Collector.
global:
scrape_interval: 15s
scrape_configs:
- job_name: 'otel-collector'
static_configs:
- targets: ['otel-collector:8889']
3. Grafana Loki Logger Configuration (loki-config.yaml)
Stores consolidated system log files.
auth_enabled: false
server:
http_listen_port: 3100
common:
ring:
instance_addr: 127.0.0.1
kvstore:
store: inmemory
replication_factor: 1
path_prefix: /tmp/loki
schema_config:
configs:
- from: 2023-01-01
store: boltdb-shipper
object_store: filesystem
schema: v11
index:
prefix: index_
period: 24h
storage_config:
filesystem:
directory: /tmp/loki/chunks
4. Tempo Distributed Tracing Configuration (tempo.yml)
Manages high-volume trace span contexts.
server:
http_listen_port: 3200
distributor:
receivers:
otlp:
protocols:
grpc:
endpoint: 0.0.0.0:4317
http:
endpoint: 0.0.0.0:4318
ingester:
lifecycler:
ring:
kvstore:
store: inmemory
replication_factor: 1
chunk_idle_period: 3m
max_block_duration: 5m
storage:
trace:
backend: local
local:
path: /tmp/tempo/blocks
14. Testing Infrastructure & Mocking Profiles
The platform maintains a robust verification layer spanning unit and integration tests.
Spring Boot Profiles
dev(Default): Uses a local database. In-memory Mockups are active.prod: Enforces strict database persistence and SSL checks.test: Activated during integration tests. Utilizes an in-memory database to prevent test contamination.
Integration Tests (FullApiIntegrationTest.java)
We utilize a comprehensive integration test suite that spins up the application context using dynamic configuration to bypass physical database setups.
- Strict Validation Toggle: During test executions,
strictValidationis toggled off (application.propertieskey:security.strict-validation=false). This allows integration tests to register dummy user accounts without passing strict password complexity regex tests, speeding up test setup. - Key Coverage Modules:
- Authentication Flow: Registers a user, authenticates credentials, requests refresh tokens, and validates header checks.
- Password Updates: Securely updates passwords and attempts logging in with old (should fail) and new (should pass) credentials.
- Peer Review Pipeline: Steps an article through draft creation, submission, review submission, scoring, and editor finalization.
To run the full test suite locally:
mvn clean test
15. Troubleshooting & DevOps Runbook
Issue: mvn package fails with compilation errors
- Cause: Outdated Java runtime or misconfigured environment paths.
- Check: Run
java -versionandecho $JAVA_HOME. Ensure both reference JDK 17 (Java 17). - Fix: Update your local terminal configurations to export Java 17.
Issue: Database connection refused inside Docker Compose
- Cause: The Spring Boot backend container started and tried connecting to MySQL before MySQL was ready to accept network calls.
- Check: Run
docker logs projects-backend. Look forConnection Refusedexceptions. - Fix: Docker Compose utilizes health checks, but in case of high disk latency, MySQL startup can lag. Execute:
docker-compose restart backend
Issue: yarn build for frontend freezes or runs out of memory
- Cause: Node.js virtual disk lock issues or excessive dependency caching.
- Fix: Remove current cache assets and reinstall cleanly:
cd front rm -rf node_modules yarn.lock yarn install yarn build
Issue: Developer CLI fails to deploy custom tools with 415 error
- Cause: Previously, the backend PUT endpoint exclusively consumed
multipart/form-data. - Fix: Ensure your backend matches our latest refactored
ToolController.javawhich supportsapplication/jsonupdates.
Issue: Cross-compilation task fails on developer machine
- Cause: Target architecture mismatch or missing compilation environments.
- Check: Verify that the Go toolchain supports target environments:
go tool dist list - Fix: Ensure you have proper read/write permissions on the
cli/bin/folder.
Copyright (c) 2026 The Research Platform Development Team. All rights reserved.
- Total size
- 3.75 GB
- Files
- 76,734
- Last updated
- Sep 11
- Pre-warmed CDN
- US EU US EU