# Bloom-Backend A backend API for user authentication, authorization, and management, featuring JWT-based Access and Refresh Tokens, HWID linking, and key-based registration with flexible access durations. ## Table of Contents - [Prerequisites](#prerequisites) - [Installation](#installation) - [Configuration](#configuration) - [Running the Server](#running-the-server) - [API Endpoints](#api-endpoints) - [Authentication and User Management](#authentication-and-user-management) - [Register Key Management (Admin Only)](#register-key-management-admin-only) - [Role Management (Admin Only)](#role-management-admin-only) - [JWT Authentication (Access & Refresh Tokens)](#jwt-authentication-access--refresh-tokens) - [Database Structure](#database-structure) ## Prerequisites Before you begin, ensure you have met the following requirements: * Node.js (v12 or higher recommended) * MongoDB (running instance) * pnpm or npm ## Installation 1. Clone the repository: ```bash git clone <repository_url> cd <repository_directory> ``` 2. Install dependencies using pnpm or npm: ```bash pnpm install # or npm install ``` ## Configuration Create a `.env` file in the root directory of the project with the following environment variables: ```dotenv JWT_SECRET=your_super_strong_and_unique_jwt_secret_key MONGO_URI=mongodb://localhost:27017/your_database_name # Add other environment variables as needed ``` * `JWT_SECRET`: **REQUIRED.** Replace with a strong, unique secret key for signing JWTs. **Do not use 'secret_key' in production.** This is crucial for security. * `MONGO_URI`: **REQUIRED.** Replace with your MongoDB connection string. ## Running the Server Start the server using the following command: ```bash node server.js # or using pnpm/npm script if configured (check package.json): # pnpm start # npm start ``` The server should start and listen on port 3000 (or the port configured in `server.js`). ## API Endpoints You can interact with the API using tools like `curl` or Postman. ### Authentication and User Management * **`POST /api/user/register`** Register a new user using a register key. Requires `username`, `password`, `repeatPassword`, and `registerKey` in the request body. ```bash curl -X POST http://localhost:3000/api/user/register \ -H 'Content-Type: application/json' \ -d '{ "username": "newuser", "password": "securepassword", "repeatPassword": "securepassword", "registerKey": "valid_unused_key" }' ``` * **`POST /api/user/login`** Login a user. Requires `username` and `password` in the request body. Returns `accessToken` and `refreshToken` upon success. ```bash curl -X POST http://localhost:3000/api/user/login \ -H 'Content-Type: application/json' \ -d '{ "username": "your_username", "password": "your_password" }' ``` * **`POST /api/user/refresh-token`** Attempt to refresh tokens. This endpoint is currently routed to a placeholder or incorrect handler in the code as of the last commit. **Note: This endpoint's functionality may be broken or incorrect based on recent code changes.** ```bash curl -X POST http://localhost:3000/api/user/refresh-token \ -H 'Content-Type: application/json' \ -d '{ "refreshToken": "your_existing_refresh_token" }' ``` * **`GET /api/user/me`** Get the authenticated user's information. Requires a valid `accessToken` in the `Authorization: Bearer <token>` header. ```bash curl -X GET http://localhost:3000/api/user/me \ -H 'Authorization: Bearer your_access_token' ``` * **`POST /api/user/me/changepassword`** Change the authenticated user's password. Requires a valid `accessToken` in the `Authorization` header and `currentPassword`, `password`, `repeatPassword` in the request body. Invalidates all refresh tokens for the user upon success. ```bash curl -X POST http://localhost:3000/api/user/me/changepassword \ -H 'Content-Type: application/json' \ -H 'Authorization: Bearer your_access_token' \ -d '{ "currentPassword": "old_password", "password": "new_password", "repeatPassword": "new_password" }' ``` * **`POST /api/user/updateHwid`** Update the authenticated user's HWID. Requires a valid `accessToken` and `hwid` in the request body. Subject to a 30-day cooldown for regular users. ```bash curl -X POST http://localhost:3000/api/user/updateHwid \ -H 'Content-Type: application/json' \ -H 'Authorization: Bearer your_access_token' \ -d '{ "hwid": "new_hardware_id" }' ``` *Admin users can update other users' HWID by including `userId` in the body (requires admin access token).* * **`POST /api/user/check`** Check client access using username and HWID. Likely used by the client application. ```bash curl -X POST http://localhost:3000/api/user/check \ -H 'Content-Type: application/json' \ -d '{ "username": "user_to_check", "hwid": "client_hardware_id" }' ``` * **`GET /api/user/:id`** (Admin Only) Get a user's information by ID. Requires admin `accessToken`. * **`PUT /api/user/:id`** (Admin Only) Update a user's information by ID. Requires admin `accessToken`. Does not handle HWID updates (use `/api/user/updateHwid`). Invalidates refresh tokens if password is changed by admin. * **`DELETE /api/user/:id`** (Admin Only) Delete a user by ID. Requires admin `accessToken`. Deletes associated refresh tokens. * **`GET /api/user/`** (Admin Only) List all users. Requires admin `accessToken`. Excludes passwords and refresh tokens from results. ### Register Key Management (Admin Only) These endpoints require a valid `accessToken` from an **admin** user. * **`POST /api/register-keys/create`** Create a new register key. Optionally accepts `durationDays` (number of days) and `isLifetime` (boolean) in the body to define the access duration provided by the key. ```bash curl -X POST http://localhost:3000/api/register-keys/create \ -H 'Content-Type: application/json' \ -H 'Authorization: Bearer admin_access_token' \ -d '{ "durationDays": 90, "isLifetime": false }' ``` * **`GET /api/register-keys/list`** List all register keys. ```bash curl -X GET http://localhost:3000/api/register-keys/list \ -H 'Authorization: Bearer admin_access_token' ``` * **`DELETE /api/register-keys/delete/:key`** Delete a specific register key by key string. ```bash curl -X DELETE http://localhost:3000/api/register-keys/delete/key_to_delete \ -H 'Authorization: Bearer admin_access_token' ``` ### Role Management (Admin Only) These endpoints require a valid `accessToken` from an **admin** user. * **`POST /api/role/`** Create a new role. Requires `name` in the request body. ```bash curl -X POST http://localhost:3000/api/role/ \ -H 'Content-Type: application/json' \ -H 'Authorization: Bearer admin_access_token' \ -d '{ "name": "moderator" }' ``` * **`PUT /api/role/`** Edit a role. Requires role details to update in the request body. ```bash curl -X PUT http://localhost:3000/api/role/ \ -H 'Content-Type: application/json' \ -H 'Authorization: Bearer admin_access_token' \ -d '{ "name": "moderator", "newFieldName": "newValue" # ... other fields to update }' ``` * **`GET /api/role/:id`** Get information about a specific role by ID. Requires admin `accessToken`. ```bash curl -X GET "http://localhost:3000/api/role/role_id_here" \ -H 'Authorization: Bearer admin_access_token' ``` * **`GET /api/role/`** List all roles. Requires admin `accessToken`. ```bash curl -X GET http://localhost:3000/api/role/ \ -H 'Authorization: Bearer admin_access_token' ``` * **`DELETE /api/role/`** Delete a role. Requires role details in the request body. ```bash curl -X DELETE http://localhost:3000/api/role/ \ -H 'Content-Type: application/json' \ -H 'Authorization: Bearer admin_access_token' \ -d '{ "name": "moderator" }' ``` ## JWT Authentication (Access & Refresh Tokens) This project implements JWT authentication using a pair of tokens: * **Access Token:** Short-lived (15 minutes). Used to access protected API endpoints. * **Refresh Token:** Longer-lived (7 days, managed by database TTL). Used to obtain a new pair of Access and Refresh Tokens when the Access Token expires. Include the Access Token in the `Authorization: Bearer <token>` header for requests to protected endpoints. When an Access Token expires, the server will likely return a 401 Unauthorized response (with a specific message). Based on the current routing, the `/api/user/refresh-token` endpoint is intended to handle token refreshing using a Refresh Token, but its implementation might be incorrect. Clients would typically use their Refresh Token to call this endpoint to get a new pair of tokens. ## Database Structure This project uses MongoDB and interacts with the following collections: * `users`: Stores user accounts (username, password hash, role, HWID, access expiry, etc.). Does **not** store refresh tokens. * `keys`: Stores register keys, their usage status, and the access duration/type (`durationDays`, `isLifetime`) they provide. * `tokens`: Stores refresh tokens for active user sessions. Each document links a `refreshToken` string to a `userId` and has a time-to-live (TTL) index to automatically handle expiry. Make sure your MongoDB instance is running and accessible via the `MONGO_URI` in your `.env` file.