Spaces:
Sleeping
Sleeping
File size: 10,404 Bytes
d0a01ab 6490f91 d0a01ab |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 |
# Document Management System
## Overview
Universal document management system with polymorphic ownership, automatic storage routing, and version control.
## Features
β
**Universal & Polymorphic** - One system for all entities (users, tickets, projects, etc.)
β
**Automatic Storage Routing** - Images/videos β Cloudinary, Documents β Supabase
β
**Version Control** - Track document versions with history
β
**Metadata & Tagging** - Rich metadata, tags, and search capabilities
β
**Access Control** - Public/private documents with uploader tracking
β
**Audit Logging** - Complete audit trail of all document operations
## Architecture
```
User uploads file
β
FastAPI receives file
β
StorageService determines provider based on MIME type
β
βββ Images/Videos β Cloudinary (CDN-optimized)
βββ Documents (PDF, DOCX) β Supabase Storage
β
Receive URL from storage provider
β
Create document record in database
β
Return document metadata to user
```
## Storage Routing Rules
The system automatically routes files based on optimization, not capability:
| File Type | Default Provider | Reason | Alternative |
|-----------|-----------------|--------|-------------|
| `image/*` | **Cloudinary** | CDN delivery, auto-optimization, transformations | Supabase can also store images |
| `video/*` | **Cloudinary** | Streaming, transcoding, adaptive bitrate | Supabase can also store videos |
| `application/pdf` | **Supabase** | Cost-effective, simple storage | N/A |
| `application/*` | **Supabase** | General documents (DOCX, XLSX, etc.) | N/A |
| Other | **Supabase** | Fallback for all other file types | N/A |
**Note**: Both providers can technically store any file type. The routing is based on optimization:
- **Cloudinary**: Best for media that needs CDN delivery and transformations
- **Supabase**: Best for documents and general file storage
## Database Schema
```sql
CREATE TABLE documents (
id UUID PRIMARY KEY,
-- Polymorphic ownership
entity_type TEXT NOT NULL, -- 'user', 'project', 'ticket', etc.
entity_id UUID NOT NULL,
-- File details
file_name TEXT NOT NULL,
file_type TEXT, -- MIME type
file_size BIGINT,
file_url TEXT NOT NULL,
storage_provider TEXT DEFAULT 'supabase', -- 'cloudinary', 'supabase'
-- Classification
document_type TEXT, -- 'profile_photo', 'identity_card', etc.
document_category TEXT, -- 'legal', 'financial', 'operational'
-- Version control
version INTEGER DEFAULT 1,
is_latest_version BOOLEAN DEFAULT TRUE,
previous_version_id UUID REFERENCES documents(id),
-- Metadata
description TEXT,
tags JSONB DEFAULT '[]',
additional_metadata JSONB DEFAULT '{}',
-- Access control
uploaded_by_user_id UUID REFERENCES users(id),
is_public BOOLEAN DEFAULT FALSE,
-- Timestamps
created_at TIMESTAMP WITH TIME ZONE,
updated_at TIMESTAMP WITH TIME ZONE,
deleted_at TIMESTAMP WITH TIME ZONE
);
```
## API Endpoints
### Universal Endpoints
```http
POST /api/v1/documents/upload
GET /api/v1/documents/{entity_type}/{entity_id}
GET /api/v1/documents/id/{document_id}
PUT /api/v1/documents/id/{document_id}
DELETE /api/v1/documents/id/{document_id}
```
### Convenience Endpoints (Shortcuts)
```http
POST /api/v1/documents/users/{user_id}/upload
GET /api/v1/documents/users/{user_id}
```
## Usage Examples
### Upload User Profile Photo
```bash
curl -X POST "https://api.example.com/api/v1/documents/upload" \
-H "Authorization: Bearer {token}" \
-F "file=@profile.jpg" \
-F "entity_type=user" \
-F "entity_id=123e4567-e89b-12d3-a456-426614174000" \
-F "document_type=profile_photo" \
-F "document_category=personal" \
-F "description=User profile photo" \
-F "tags=[\"profile\", \"avatar\"]" \
-F "is_public=true"
```
**Response:**
```json
{
"id": "doc-uuid",
"entity_type": "user",
"entity_id": "user-uuid",
"file_name": "profile.jpg",
"file_type": "image/jpeg",
"file_size": 245678,
"file_url": "https://res.cloudinary.com/...",
"storage_provider": "cloudinary",
"document_type": "profile_photo",
"version": 1,
"uploader": {
"id": "uploader-uuid",
"name": "John Doe",
"email": "john@example.com"
},
"created_at": "2025-11-16T10:30:00Z"
}
```
### Upload Ticket Photo
```bash
curl -X POST "https://api.example.com/api/v1/documents/upload" \
-H "Authorization: Bearer {token}" \
-F "file=@site_photo.jpg" \
-F "entity_type=ticket" \
-F "entity_id=ticket-uuid" \
-F "document_type=ticket_image" \
-F "document_category=evidence" \
-F "description=Before installation photo"
```
### Upload User ID Document (PDF)
```bash
curl -X POST "https://api.example.com/api/v1/documents/users/{user_id}/upload" \
-H "Authorization: Bearer {token}" \
-F "file=@national_id.pdf" \
-F "document_type=identity_card" \
-F "document_category=legal" \
-F "description=National ID card"
```
### Get All User Documents
```bash
curl "https://api.example.com/api/v1/documents/user/{user_id}" \
-H "Authorization: Bearer {token}"
```
### Get Specific Document Type
```bash
curl "https://api.example.com/api/v1/documents/user/{user_id}?document_type=profile_photo" \
-H "Authorization: Bearer {token}"
```
### Update Document Metadata
```bash
curl -X PUT "https://api.example.com/api/v1/documents/id/{document_id}" \
-H "Authorization: Bearer {token}" \
-H "Content-Type: application/json" \
-d '{
"description": "Updated description",
"tags": ["updated", "new-tag"],
"is_public": true
}'
```
### Delete Document
```bash
curl -X DELETE "https://api.example.com/api/v1/documents/id/{document_id}" \
-H "Authorization: Bearer {token}"
```
## Document Types
### User Documents
- `profile_photo` - User avatar/profile picture
- `identity_card` - National ID, passport, etc.
- `driver_license` - Driver's license
- `contract` - Employment contract
- `certification` - Professional certifications
### Ticket Documents
- `ticket_image` - Site photos, equipment photos
- `before_photo` - Before installation/repair
- `after_photo` - After installation/repair
- `work_report` - PDF work reports
### Expense Documents
- `receipt` - Payment receipts
- `invoice` - Invoices
- `expense_proof` - Expense documentation
### Project Documents
- `project_plan` - Project planning documents
- `blueprint` - Technical blueprints
- `contract` - Project contracts
## Document Categories
- `legal` - Legal documents (contracts, IDs, licenses)
- `financial` - Financial documents (receipts, invoices)
- `operational` - Operational documents (reports, plans)
- `evidence` - Evidence documents (photos, proofs)
- `personal` - Personal documents (profile photos)
## Storage Providers
### Cloudinary
- **Used for**: Images and videos
- **Benefits**: CDN delivery, automatic optimization, on-the-fly transformations
- **Folder structure**: `/swiftops/users/`, `/swiftops/tickets/`, `/swiftops/receipts/`
- **Metadata stored**: `public_id`, `format`, `width`, `height`, `bytes`, `resource_type`
### Supabase Storage
- **Used for**: Documents (PDF, DOCX, etc.)
- **Benefits**: Integrated with database, simple API, cost-effective
- **Bucket structure**: `documents-users`, `documents-tickets`, `documents-general`
- **Metadata stored**: `bucket`, `path`, `size`, `content_type`
## Version Control
Documents support versioning:
1. Upload new version of existing document
2. System creates new document record with incremented version
3. Previous version marked as `is_latest_version = false`
4. `previous_version_id` links to old version
5. Both versions remain accessible
## Security
### Authentication
- All endpoints require valid JWT token
- User must be authenticated to upload/view documents
### Authorization
- Users can upload documents for entities they have access to
- Public documents (`is_public=true`) can be viewed by anyone with the link
- Private documents require proper permissions
### File Validation
- File size limits enforced
- File type validation
- Malicious file detection (future enhancement)
## Error Handling
### Upload Failures
- If storage provider fails, no database record is created
- User receives clear error message
- Failed uploads are logged for debugging
### Database Failures
- If database insert fails after successful upload, file is deleted from storage
- Prevents orphaned files
- Transaction-like behavior
## Monitoring
### Metrics to Track
- Upload success/failure rates
- Average upload times
- Storage usage by provider
- Most common document types
- Failed uploads requiring retry
### Logs
- All uploads logged with user, entity, file details
- Audit trail in `audit_logs` table
- Error logs for failed operations
## Future Enhancements
- [ ] Document preview/thumbnail generation
- [ ] OCR for text extraction from images
- [ ] Virus scanning for uploaded files
- [ ] Bulk upload support
- [ ] Document expiry/retention policies
- [ ] Advanced search with full-text search
- [ ] Document sharing with external users
- [ ] E-signature integration
## Testing
Run integration tests:
```bash
node tests/integration/test_document_upload.js
```
## Configuration
Required environment variables:
```env
# Cloudinary (for images/videos)
CLOUDINARY_CLOUD_NAME=your_cloud_name
CLOUDINARY_API_KEY=your_api_key
CLOUDINARY_API_SECRET=your_api_secret
# Supabase (for documents)
SUPABASE_URL=https://your-project.supabase.co
SUPABASE_SERVICE_KEY=your_service_key
```
## Troubleshooting
### "Cloudinary not configured" error
- Check that all Cloudinary environment variables are set
- Verify credentials are correct in Cloudinary dashboard
### "Failed to upload to Supabase Storage" error
- Check Supabase service key is valid
- Verify storage buckets exist in Supabase dashboard
- Check bucket permissions
### Files not appearing in Cloudinary Media Library
- Check `asset_folder` parameter in upload
- Verify account is using dynamic folder mode (post-June 2024)
### Large file uploads failing
- Check file size limits (default 10MB for most endpoints)
- For files >100MB, use chunked upload (future enhancement)
## Support
For issues or questions:
1. Check logs in `docs/hflogs/runtimeerror.txt`
2. Review audit logs in database
3. Check Cloudinary/Supabase dashboards for storage issues
|