Files
auth-service/BACKEND_API.md

529 lines
11 KiB
Markdown
Raw Permalink Normal View History

2026-01-26 16:21:23 +04:00
# Backend API Documentation - Auth Service
Complete API documentation for implementing the backend for the DX Authentication Service.
## 📋 Overview
This authentication service provides QR code-based authentication with comprehensive device tracking for all DX projects (Dexar, Novo Markets, FastCheck, BackOffice).
**Base URL:**
- Development: `http://localhost:3000/api`
- Production: `https://api.dx-projects.com/api`
---
## 🔐 Endpoints
### 1. Generate QR Code
Generate a new QR code session for authentication.
**Endpoint:** `POST /auth/qr/generate`
**Request Body:**
```json
{
"project": "dexar",
"deviceInfo": {
"deviceType": "desktop",
"deviceOS": "windows",
"context": "browser",
"project": "dexar",
"userAgent": "Mozilla/5.0...",
"screenResolution": "1920x1080",
"browserName": "Chrome",
"browserVersion": "120.0.0"
}
}
```
**Request Schema:**
| Field | Type | Required | Description |
|-------|------|----------|-------------|
| `project` | string | Yes | Project ID: dexar, novo, fastcheck, backoffice |
| `deviceInfo.deviceType` | string\|null | No | mobile, desktop, tablet |
| `deviceInfo.deviceOS` | string\|null | No | android, ios, windows, macos, linux |
| `deviceInfo.context` | string\|null | No | browser, application, telegram |
| `deviceInfo.project` | string | Yes | Same as root project |
| `deviceInfo.userAgent` | string | No | Browser user agent |
| `deviceInfo.screenResolution` | string | No | e.g. "1920x1080" |
| `deviceInfo.browserName` | string | No | Browser name |
| `deviceInfo.browserVersion` | string | No | Browser version |
**Response:** `200 OK`
```json
{
"sessionId": "550e8400-e29b-41d4-a716-446655440000",
"qrCode": "data:image/png;base64,iVBORw0KGgo...",
"expiresAt": "2026-01-26T15:30:00.000Z",
"expiresIn": 60
}
```
**QR Code Content Should Be:**
```json
{
"sessionId": "550e8400-e29b-41d4-a716-446655440000",
"apiUrl": "https://api.dx-projects.com/api"
}
```
---
### 2. Scan QR Code (Mobile Auth)
Scan and authenticate using a QR code session.
**Endpoint:** `POST /auth/qr/scan`
**Request Body:**
```json
{
"sessionId": "550e8400-e29b-41d4-a716-446655440000",
"deviceInfo": {
"deviceType": "mobile",
"deviceOS": "android",
"context": "application",
"project": "dexar",
"userAgent": "Mozilla/5.0...",
"screenResolution": "1080x2400",
"browserName": "Chrome Mobile",
"browserVersion": "120.0.0"
}
}
```
**Response:** `200 OK`
```json
{
"success": true,
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"userId": "user-123",
"expiresAt": "2026-01-27T14:30:00.000Z",
"message": "Authentication successful",
"userInfo": {
"username": "john_doe",
"email": "john@example.com",
"role": "admin"
}
}
```
---
### 3. Check Auth Status (Polling)
Check if a QR session has been authenticated. Used for polling every 2 seconds.
**Endpoint:** `GET /auth/qr/status/:sessionId`
**Response (Not Authenticated):** `200 OK`
```json
{
"authenticated": false
}
```
**Response (Authenticated):** `200 OK`
```json
{
"authenticated": true,
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"userId": "user-123",
"expiresAt": "2026-01-27T14:30:00.000Z",
"userInfo": {
"username": "john_doe",
"email": "john@example.com",
"role": "admin"
}
}
```
---
### 4. Traditional Login
Username/password authentication (alternative to QR).
**Endpoint:** `POST /auth/login`
**Request Body:**
```json
{
"username": "john_doe",
"password": "secure_password_123",
"deviceInfo": {
"deviceType": "desktop",
"deviceOS": "windows",
"context": "browser",
"project": "backoffice"
}
}
```
**Response:** `200 OK`
```json
{
"success": true,
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"userId": "user-123",
"expiresAt": "2026-01-27T14:30:00.000Z",
"message": "Login successful",
"userInfo": {
"username": "john_doe",
"email": "john@example.com",
"role": "admin"
}
}
```
---
### 5. Validate Session
Validate an existing JWT token.
**Endpoint:** `POST /auth/validate`
**Headers:**
```
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
```
**Request Body:**
```json
{
"deviceInfo": {
"deviceType": "desktop",
"deviceOS": "windows",
"context": "browser",
"project": "dexar"
}
}
```
**Response:** `200 OK`
```json
{
"valid": true,
"userId": "user-123",
"expiresAt": "2026-01-27T14:30:00.000Z",
"userInfo": {
"username": "john_doe",
"email": "john@example.com",
"role": "admin"
}
}
```
---
### 6. Logout
Invalidate current session.
**Endpoint:** `POST /auth/logout`
**Headers:**
```
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
```
**Request Body:**
```json
{
"deviceInfo": {
"deviceType": "desktop",
"deviceOS": "windows",
"context": "browser",
"project": "dexar"
}
}
```
**Response:** `200 OK`
```json
{
"success": true,
"message": "Logged out successfully"
}
```
---
## 💾 Database Schema
### Sessions Table
```sql
CREATE TABLE auth_sessions (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
session_id VARCHAR(255) UNIQUE NOT NULL,
project VARCHAR(50) NOT NULL,
device_type VARCHAR(20),
device_os VARCHAR(20),
context VARCHAR(20),
user_agent TEXT,
screen_resolution VARCHAR(20),
browser_name VARCHAR(50),
browser_version VARCHAR(20),
authenticated BOOLEAN DEFAULT FALSE,
user_id UUID,
ip_address VARCHAR(45),
created_at TIMESTAMP DEFAULT NOW(),
expires_at TIMESTAMP NOT NULL,
authenticated_at TIMESTAMP,
INDEX idx_session_id (session_id),
INDEX idx_expires_at (expires_at),
INDEX idx_user_id (user_id)
);
```
### Auth Logs Table
```sql
CREATE TABLE auth_logs (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
user_id UUID,
project VARCHAR(50) NOT NULL,
action VARCHAR(50) NOT NULL, -- login, logout, qr_scan, validate, qr_generate
device_type VARCHAR(20),
device_os VARCHAR(20),
context VARCHAR(20),
user_agent TEXT,
ip_address VARCHAR(45),
success BOOLEAN,
error_message TEXT,
created_at TIMESTAMP DEFAULT NOW(),
INDEX idx_user_id (user_id),
INDEX idx_created_at (created_at),
INDEX idx_project (project)
);
```
---
## 🔒 Security Implementation
### Password Hashing
```javascript
const bcrypt = require('bcrypt');
const saltRounds = 12;
// Hash password
const hashedPassword = await bcrypt.hash(password, saltRounds);
// Verify password
const isValid = await bcrypt.compare(password, hashedPassword);
```
### JWT Token Generation
```javascript
const jwt = require('jsonwebtoken');
const token = jwt.sign(
{
userId: user.id,
project: deviceInfo.project,
deviceType: deviceInfo.deviceType
},
process.env.JWT_SECRET,
{ expiresIn: '24h' }
);
```
### QR Code Generation
```javascript
const QRCode = require('qrcode');
const qrData = {
sessionId: sessionId,
apiUrl: process.env.API_URL
};
const qrCodeImage = await QRCode.toDataURL(JSON.stringify(qrData));
```
---
## 🚀 Implementation Flow
### QR Authentication Flow
1. **Desktop Browser Requests QR Code**
- POST `/auth/qr/generate` with desktop device info
- Backend creates session in database
- Returns QR code image
2. **Frontend Starts Polling**
- Every 2 seconds: GET `/auth/qr/status/:sessionId`
- Backend returns `{ authenticated: false }`
3. **Mobile App Scans QR**
- Parse QR code to get sessionId
- POST `/auth/qr/scan` with mobile device info
- Backend authenticates user
- Backend updates session as authenticated
- Returns JWT token
4. **Desktop Polling Detects Auth**
- Next poll returns `{ authenticated: true, token: "..." }`
- Frontend stores token
- Redirects to application
---
## 📊 Device Info Tracking
### When to Send Device Info
**Send device info on:**
- ✅ QR code generation (desktop)
- ✅ QR code scanning (mobile)
- ✅ Traditional login
- ✅ Session validation
- ✅ Logout
**Device Info Rules:**
- All fields except `project` are optional
- Send `null` for unknown values
- Never fail request if device info is incomplete
- Log all device info for analytics
---
## ⚠️ Error Handling
### Error Response Format
```json
{
"error": true,
"message": "Invalid credentials",
"code": "INVALID_CREDENTIALS"
}
```
### Error Codes
| Code | HTTP Status | Description |
|------|-------------|-------------|
| `INVALID_PROJECT` | 400 | Unknown project identifier |
| `INVALID_SESSION` | 401 | Session not found or expired |
| `INVALID_CREDENTIALS` | 401 | Wrong username/password |
| `INVALID_TOKEN` | 401 | JWT token invalid or expired |
| `SESSION_EXPIRED` | 401 | QR code session expired |
| `RATE_LIMIT_EXCEEDED` | 429 | Too many requests |
| `SERVER_ERROR` | 500 | Internal server error |
---
## 🧪 Testing
### Test Data
**Test User:**
```json
{
"username": "test_user",
"password": "Test123!",
"email": "test@dx-projects.com",
"role": "user"
}
```
### Example cURL Commands
**Generate QR Code:**
```bash
curl -X POST http://localhost:3000/api/auth/qr/generate \
-H "Content-Type: application/json" \
-d '{
"project": "dexar",
"deviceInfo": {
"deviceType": "desktop",
"deviceOS": "windows",
"context": "browser",
"project": "dexar"
}
}'
```
**Check Status:**
```bash
curl http://localhost:3000/api/auth/qr/status/{sessionId}
```
**Login:**
```bash
curl -X POST http://localhost:3000/api/auth/login \
-H "Content-Type: application/json" \
-d '{
"username": "test_user",
"password": "Test123!",
"deviceInfo": {
"deviceType": "desktop",
"deviceOS": "windows",
"context": "browser",
"project": "dexar"
}
}'
```
---
## 📌 Important Notes
1. **QR Code Expiration:** 60 seconds (configurable)
2. **JWT Token Expiration:** 24 hours (configurable)
3. **Polling Interval:** 2 seconds
4. **Rate Limiting:** 60 requests/minute per IP
5. **CORS:** Allow all project domains
6. **Session Cleanup:** Delete expired sessions every hour
---
## 🔧 Environment Variables
```env
# API Configuration
PORT=3000
API_URL=http://localhost:3000/api
NODE_ENV=development
# JWT
JWT_SECRET=your-super-secret-jwt-key-change-this
JWT_EXPIRATION=24h
# Database
DB_HOST=localhost
DB_PORT=5432
DB_NAME=dx_auth
DB_USER=postgres
DB_PASSWORD=your-password
# QR Code
QR_EXPIRATION=60
QR_SIZE=240
# CORS
CORS_ORIGINS=http://localhost:4200,http://localhost:4300,http://localhost:4400
# Rate Limiting
RATE_LIMIT_WINDOW=60000
RATE_LIMIT_MAX_REQUESTS=60
```
---
## 📚 Additional Resources
- **Frontend Integration:** See `HOW_TO_USE.md`
- **Project Setup:** See `README.md`
- **FastCheck APIs:** Reference similar implementation in FastCheck project
---
## 🆘 Support
For backend implementation questions:
- Email: backend@dx-projects.com
- Slack: #backend-auth
- Documentation: https://docs.dx-projects.com/auth