A high-performance CDN API service for image optimization, file management, and asset delivery built with Express.js and TypeScript.
Features โข Installation โข API Documentation โข Development
- About
- Features
- Prerequisites
- Installation
- Configuration
- Usage
- API Documentation
- Development
- Project Structure
- Deployment
- Testing
- Contributing
- License
CDN API is a production-ready content delivery network service that provides intelligent image optimization, secure file storage, and efficient asset management. Built with modern web technologies, it offers both a RESTful API and a web-based dashboard for managing your digital assets.
- Backend: Express.js 5.x with TypeScript
- Database: Drizzle ORM with SQLite (Better-SQLite3)
- Authentication: JWT-based with bcrypt password hashing
- Image Processing: Sharp (high-performance image optimization)
- Document Preview: Puppeteer for PDF generation and document previews
- TIFF Support: TIFF.js for TIFF image handling
- File Handling: Multer, fs-extra
- Security: Express Rate Limiting, CORS, Session Management
- Frontend: EJS templating with Tailwind CSS 4.x
- Development: TypeScript, ts-node with hot reload
- Intelligent Optimization: Automatic image compression and format conversion
- Multi-format Support: JPEG, PNG, WebP, AVIF, GIF, TIFF
- Responsive Images: Generate multiple sizes for responsive design
- Caching: Built-in image caching for improved performance
- Metadata Extraction: EXIF data preservation and extraction
- Secure Upload: Validated file uploads with type checking
- Folder Organization: Hierarchical folder structure support
- File Operations: Move, delete, rename, and search files
- Preview Generation: Document preview for supported formats
- Direct Download: Secure file download endpoints
- Upload Tracking: Complete audit trail of all uploads with user association
- Metadata Storage: File metadata and tags in SQLite database
- JWT Authentication: Secure token-based authentication
- Role-Based Access: Admin, user, and viewer roles
- Session Management: Active session tracking with refresh tokens
- Account Security: Failed login attempt tracking and account locking
- Audit Logging: Complete authentication audit trail
- Password Security: Bcrypt hashing with configurable rounds
- Default Admin: Auto-created admin account for initial setup
- SQLite Database: Lightweight, serverless database with Drizzle ORM
- Type-Safe Queries: Full TypeScript support with Drizzle
- Migration System: Timestamp-based schema migration tracking
- Seed Data: Database seeding for demo users and test data
- Database Studio: Built-in Drizzle Studio for visual database management
- Schema Export: Export database schema for documentation
- Rate Limiting: Configurable rate limits for all endpoints
- Image uploads: 30 requests per 15 minutes
- File uploads: 15 requests per 15 minutes
- CORS Protection: Configurable origin and pattern-based access control
- IPv6 Support: Full IPv4/IPv6 compatibility
- Input Validation: Comprehensive request validation
- Storage Statistics: Real-time storage usage analytics
- File Type Analysis: Breakdown by file type and folder
- Largest Files Tracking: Identify storage-heavy assets
- Performance Metrics: Response time and throughput monitoring
- Authentication: Login page with JWT-based authentication
- Dashboard: Overview of storage usage and recent activity
- File Browser: Visual interface for browsing and managing files with breadcrumb navigation
- My Files: Organize and manage files in folders
- Quick Access: Starred files and recent items for fast retrieval
- Upload Interface: User-friendly file upload with progress tracking
- Upload History: Track all upload activities with user information
- Shared Files: Manage and view shared resources
- User Management: Admin interface for managing user accounts
- Search: Powerful filename search capabilities
- Responsive Design: Mobile-friendly interface with modern UI
Before installing, ensure you have the following:
- Node.js: >= 18.0.0 (LTS recommended)
- npm: >= 9.0.0 or yarn: >= 1.22.0
- Operating System: Windows, macOS, or Linux
- Memory: Minimum 512MB RAM (2GB+ recommended for image processing)
- Disk Space: Varies based on storage needs
- Docker: For containerized deployment
- PM2: For production process management
- Nginx: For reverse proxy setup
# Clone the repository
git clone <repository-url>
cd assets.stackdev.cloud
# Install dependencies
npm install
# Configure environment
cp env.json.example env.json
# Edit env.json with your configuration
# Initialize database
npm run migrate:up
# (Optional) Seed demo data
npm run seed
# Run in development mode
npm run devgit clone <repository-url>
cd assets.stackdev.cloud
npm installCreate your configuration file:
cp env.json.example env.jsonEdit env.json with your settings (see Configuration section).
# Run database migrations
npm run migrate:up
# Check migration status
npm run migrate:status
# (Optional) Seed demo users
npm run seed# Build CSS (Tailwind)
npm run build:css
# Full production build
npm run build# Development (with hot reload)
npm run dev
# Production
npm startThe server will be available at http://localhost:3000 (or your configured port).
{
"app": {
"name": "CDN API",
"env": "development" // "development" or "production"
},
"port": 3000, // Server port
"directories": [
"./storage/**/**" // Storage directory pattern
],
"allow": {
"origins": [ // Allowed CORS origins
"http://localhost:3000",
"http://localhost:5173"
],
"patterns": [ // Regex patterns for origins
"^https?://.*\\.stackdev\\.cloud$"
]
},
"database": {
"dbPath": "src/data/app.db", // SQLite database path
"autoRunMigrations": true, // Run migrations on startup
"autoRunSeeds": false // Run seeds on startup
},
"auth": {
"jwtSecret": "your-super-secret-jwt-key-min-32-characters-long",
"jwtExpiresIn": "1h", // Access token expiration
"refreshTokenExpiresIn": "7d", // Refresh token expiration
"bcryptRounds": 12, // Password hashing rounds
"maxLoginAttempts": 5, // Failed login limit
"lockoutDuration": 15, // Account lockout minutes
"maxSessionsPerUser": 5 // Max concurrent sessions
}
}| Option | Type | Description | Default |
|---|---|---|---|
app.name |
string | Application name | "CDN API" |
app.env |
string | Environment mode | "development" |
port |
number | Server port | 3000 |
directories |
array | Storage directory patterns | ["./storage/**/**"] |
allow.origins |
array | Exact CORS origins | [] |
allow.patterns |
array | Regex patterns for CORS | [] |
database.dbPath |
string | SQLite database file path | "src/data/app.db" |
database.autoRunMigrations |
boolean | Auto-run migrations on startup | true |
database.autoRunSeeds |
boolean | Auto-run seeds on startup | false |
auth.jwtSecret |
string | JWT secret key (min 32 chars) | Required |
auth.jwtExpiresIn |
string | Access token TTL | "1h" |
auth.refreshTokenExpiresIn |
string | Refresh token TTL | "7d" |
auth.bcryptRounds |
number | Password hashing strength | 12 |
auth.maxLoginAttempts |
number | Failed login threshold | 5 |
auth.lockoutDuration |
number | Lockout duration (minutes) | 15 |
auth.maxSessionsPerUser |
number | Max concurrent sessions per user | 5 |
The default storage structure:
storage/
โโโ background/ # Background images
โ โโโ cover/ # Cover images
โโโ documents/ # Document uploads
โโโ example/ # Example assets
โ โโโ site.webmanifest
โโโ files/ # General file uploads
You can customize storage locations in env.json.
The application uses SQLite with Drizzle ORM for data persistence. The database file is stored at src/data/app.db.
The system includes the following tables:
- users - User accounts with role-based access
- sessions - JWT session management with refresh tokens
- auth_audit_log - Security audit trail for authentication events
- files - Uploaded files metadata
- uploads - Upload tracking with user association
- migrations - Migration execution history
# Check migration status
npm run migrate:status
# Run all pending migrations
npm run migrate:up
# Rollback last migration
npm run migrate:down
# Create a new migration
npm run migrate:create "migration_name"# Run all seed files
npm run seed
# Create a new seed file
npm run seed:create "seed_name"Launch the visual database browser:
npm run db:studioThen visit http://localhost:4983/ to:
- Browse all tables and data
- Run queries visually
- Edit records directly
- Export/import data
# Generate schema from TypeScript code
npm run db:generate
# Push schema changes directly to database
npm run db:pushdb:push for rapid development, but use migrations (migrate:up) for production environments.
To backup the database:
# Windows
copy src\data\app.db src\data\app.db.backup
# Linux/macOS
cp src/data/app.db src/data/app.db.backupOr use the API endpoint:
curl -X POST http://localhost:3000/api/database/backup# Development mode (with hot reload and detailed logging)
npm run dev
# Production mode
npm start
# Watch CSS changes (separate terminal)
npm run css- Web Dashboard: http://localhost:3000/
- API Base URL: http://localhost:3000/api/
- API Welcome: http://localhost:3000/api/
- API Version: http://localhost:3000/api/version
- Database Studio: Run
npm run db:studioand visit http://localhost:4983/
After running migrations, a default admin account is created:
- Username:
admin - Password:
admin123 - Email:
admin@stackdev.cloud
curl -X POST http://localhost:3000/api/image/upload \
-F "images=@photo.jpg"curl -X POST http://localhost:3000/api/file/upload \
-F "files=@document.pdf" \
-F "path=/documents"curl http://localhost:3000/api/storagehttp://localhost:3000/api
The API supports JWT-based authentication. While many endpoints work without authentication, protected endpoints require a valid JWT token.
curl -X POST http://localhost:3000/api/auth/login \
-H "Content-Type: application/json" \
-d '{
"username": "admin",
"password": "admin123"
}'Include the JWT token in the Authorization header:
curl http://localhost:3000/api/auth/me \
-H "Authorization: Bearer YOUR_JWT_TOKEN"- Access Token: Valid for 1 hour (configurable)
- Refresh Token: Valid for 7 days (configurable)
- Use
/auth/logoutto invalidate current session - Use
/auth/logout-allto invalidate all user sessions
| Category | Endpoint | Method | Description | Auth Required |
|---|---|---|---|---|
| Health | / |
GET | API welcome message | No |
| Health | /version |
GET | Get API version info | No |
| Auth | /auth/login |
POST | User login (rate limited) | No |
| Auth | /auth/logout |
POST | Logout current session | Yes |
| Auth | /auth/logout-all |
POST | Logout all sessions | Yes |
| Auth | /auth/me |
GET | Get current user info | Yes |
| Images | /image/upload |
POST | Upload images (rate limited) | Optional |
| Images | /image/* |
GET | Retrieve optimized images | No |
| Files | /file/upload |
POST | Upload files (rate limited) | Optional |
| Files | /file/search |
GET | Search files by name | No |
| Files | /file/move |
PUT | Move files/folders | Optional |
| Files | /file/delete |
DELETE | Delete files | Optional |
| Files | /file/download/* |
GET | Download files | No |
| Files | /file/preview/* |
GET | Preview documents | No |
| Folders | /folder |
GET | Get folder structure | No |
| Database | /database/files |
GET | Get files database | No |
| Database | /database/stats |
GET | Database statistics | No |
| Database | /database/search |
GET | Search database | No |
| Database | /database/backup |
POST | Backup database | Optional |
| Storage | /storage |
GET | Full storage statistics | No |
| Storage | /storage/summary |
GET | Quick storage summary | No |
For comprehensive API documentation with examples, see:
- Migration Guide - Database migration system
- Image Upload Endpoint
- File Upload Endpoint
- Storage API Endpoint
- Get Image Endpoint
- Get Content Structure
- Move File Endpoint
- Search Filename
- Rate Limiting
Import the Postman collection for testing:
docs/collections/collection.postman_collection.json
The application includes a full-featured web interface accessible via browser:
| Route | Description | Auth Required |
|---|---|---|
/ |
Dashboard overview with storage stats | Yes |
/login |
User authentication page | No |
/files |
File browser and manager | Yes |
/files/* |
Navigate through folder structure | Yes |
/starred |
Quick access to starred files | Yes |
/recent |
Recently accessed files | Yes |
/detail |
Detailed file information | Yes |
/share |
Shared files management | Yes |
/upload |
File upload interface | Yes |
/upload/history |
Upload activity history | Yes |
/users |
User management (Admin only) | Yes |
Note: Web authentication is handled via JWT tokens stored in browser cookies. Users are automatically redirected to /login if not authenticated.
# Development server with hot reload
npm run dev
# Watch CSS changes (Tailwind)
npm run css
# Build CSS for production
npm run build:css
# Build TypeScript
npm run build
# Production server
npm start# Run all pending migrations
npm run migrate:up
# Rollback last migration
npm run migrate:down
# Check migration status
npm run migrate:status
# Create new migration
npm run migrate:create "migration name"
# Run database seeds
npm run seed
# Create new seed file
npm run seed:create "seed name"
# Generate Drizzle schema
npm run db:generate
# Push schema changes
npm run db:push
# Open Drizzle Studio
npm run db:studio- Make Changes: Edit TypeScript files in
src/ - Auto Reload: Server automatically restarts (ts-node watch mode)
- CSS Updates: Run
npm run cssin separate terminal for Tailwind - Testing: Test endpoints using Postman collection
- Build: Run
npm run buildbefore deployment
- TypeScript: Strict mode enabled
- Formatting: Use consistent indentation (2 spaces)
- Imports: ES modules with
.jsextensions - Error Handling: Use try-catch with proper error responses
- Comments: Document complex logic and public APIs
- Create Route: Add route file in
src/server/routes/ - Create Controller: Add controller in
src/server/controllers/ - Add Utilities: Add helper functions in
src/server/utils/ - Register Route: Import and use in
src/server/routes/api.ts - Update Documentation: Add endpoint docs to
docs/how-to-use/ - Update Postman: Add to collection
cdn.api.pphat.stackdev.cloud/
โโโ src/
โ โโโ app.ts # Application entry point
โ โโโ client/ # Frontend application
โ โ โโโ controller/ # Client controllers
โ โ โโโ middlewares/ # Client middlewares
โ โ โ โโโ auth.ts # Client auth middleware
โ โ โโโ routes/ # Client routes
โ โ โ โโโ web.ts # Web routes
โ โ โโโ styles/ # CSS/Tailwind styles
โ โ โโโ utils/ # Client utilities
โ โ โโโ views/ # EJS templates
โ โ โโโ components/ # Reusable components
โ โ โโโ layouts/ # Layout templates
โ โ โโโ pages/ # Page templates
โ โโโ data/ # Data storage
โ โ โโโ app.db # SQLite database
โ โ โโโ database.json # Legacy JSON store
โ โ โโโ migrations/ # Database migrations
โ โ โ โโโ 0000_youthful_ozymandias.sql
โ โ โ โโโ 20260213_000000_create_initial_auth_tables_sqlite.ts
โ โ โ โโโ 20260214_000000_create_files_uploads_tables_sqlite.ts
โ โ โ โโโ meta/ # Drizzle metadata
โ โ โ โโโ README.md
โ โ โโโ schema/ # Database schemas
โ โ โ โโโ schema.ts # Drizzle ORM schema
โ โ โโโ seeds/ # Database seeds
โ โ โโโ 20260213_010000_demo_users_sqlite.ts
โ โโโ server/ # Backend API
โ โโโ controllers/ # API controllers
โ โ โโโ auth.controller.ts # Authentication controller
โ โ โโโ files.controller.ts
โ โ โโโ folder.controller.ts
โ โ โโโ images.controller.ts
โ โ โโโ preview.controller.ts
โ โ โโโ session.controller.ts # Session management
โ โ โโโ storage.controller.ts
โ โ โโโ upload.controller.ts
โ โ โโโ users.controller.ts # User management
โ โโโ middlewares/ # Express middlewares
โ โ โโโ auth.ts # JWT auth middleware
โ โ โโโ cors.ts
โ โ โโโ rate-limit.ts
โ โ โโโ security.ts # Security headers
โ โโโ routes/ # API routes
โ โ โโโ api.ts # Main API router
โ โ โโโ auth.ts # Auth routes
โ โ โโโ database.ts
โ โ โโโ file.ts
โ โ โโโ folder.ts
โ โ โโโ image.ts
โ โ โโโ storage.ts
โ โโโ types/ # TypeScript types
โ โ โโโ user.ts # User & auth types
โ โโโ utils/ # Server utilities
โ โโโ auth.ts # Auth utilities
โ โโโ config.ts # Configuration loader
โ โโโ database.ts # Database operations (legacy)
โ โโโ db.ts # Drizzle DB client
โ โโโ directories.ts # Directory utilities
โ โโโ files.ts # File operations
โ โโโ image-cache.ts # Image caching
โ โโโ migration-runner.ts # Migration system
โ โโโ mine-types.ts # MIME type detection
โ โโโ response.ts # Response helpers
โ โโโ storage.ts # Storage statistics
โโโ storage/ # File storage directory
โ โโโ background/ # Background images
โ โ โโโ cover/ # Cover images
โ โโโ documents/ # Document files
โ โโโ example/ # Example assets
โ โโโ files/ # General file uploads
โโโ docs/ # Documentation
โ โโโ collections/ # Postman collections
โ โ โโโ collection.postman_collection.json
โ โโโ how-to-use/ # Endpoint documentation
โโโ scripts/ # Build and utility scripts
โ โโโ migrate.ts # Migration CLI
โ โโโ register.mjs # TS-Node registration
โโโ dist/ # Compiled output (gitignored)
โโโ drizzle.config.ts # Drizzle ORM config
โโโ env.json # Configuration (gitignored)
โโโ env.json.example # Configuration template
โโโ package.json # Dependencies
โโโ tsconfig.json # TypeScript config
โโโ postcss.config.js # PostCSS config
โโโ Dockerfile # Docker configuration
โโโ README.md # This file
# Install dependencies
npm ci --production=false
# Build application
npm run build
# Start production server
npm start# Build Docker image
docker build -t cdn-api .
# Run container
docker run -d \
-p 3000:3000 \
-v $(pwd)/storage:/app/storage \
-v $(pwd)/env.json:/app/env.json \
--name cdn-api \
cdn-api# Install PM2
npm install -g pm2
# Start with PM2
pm2 start dist/app.js --name cdn-api
# Enable startup script
pm2 startup
pm2 save
# Monitor
pm2 monitserver {
listen 80;
server_name cdn.yourdomain.com;
location / {
proxy_pass http://localhost:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}For production, consider using environment variables instead of env.json:
export NODE_ENV=production
export PORT=3000
export APP_NAME="CDN API"Use the provided Postman collection:
# Import collection
docs/collections/collection.postman_collection.json- User login with valid credentials
- Login rate limiting (5 attempts)
- Account locking after failed attempts
- JWT token validation
- Protected endpoint access
- Logout functionality
- Current user info retrieval
- Image upload with various formats (JPEG, PNG, WebP, TIFF)
- File upload with different file types
- File search by name
- File move operations
- File deletion
- File download
- Document preview generation
- Rate limiting verification (all endpoints)
- CORS headers validation
- Storage statistics accuracy
- Database migrations (up/down)
- Seed data creation
- Error handling scenarios
- Session management
- Migration execution
- Rollback functionality
- Seed data integrity
- Foreign key constraints
- Data validation
# Install Apache Bench
apt-get install apache2-utils # Linux
brew install httpd # macOS
# Test image endpoint
ab -n 1000 -c 10 http://localhost:3000/api/storage/summary
# Test upload rate limiting
ab -n 50 -c 5 -p file.jpg -T multipart/form-data \
http://localhost:3000/api/image/uploadContributions are welcome! Please follow these guidelines:
- Fork the repository
- Clone your fork
- Create a feature branch (
git checkout -b feature/amazing-feature) - Make your changes
- Test thoroughly
- Commit with clear messages (
git commit -m 'Add amazing feature') - Push to your branch (
git push origin feature/amazing-feature) - Open a Pull Request
- Follow existing code style and conventions
- Add comments for complex logic
- Update documentation for new features
- Ensure TypeScript compiles without errors
- Test your changes before submitting
type(scope): subject
body
footer
Types: feat, fix, docs, style, refactor, test, chore
Example:
feat(storage): add file type filtering to storage stats
Added optional query parameter to filter storage statistics by file type.
This allows users to get specific analytics for images, documents, etc.
Closes #123
This project is licensed under the ISC License - see the LICENSE file for details.
Sophat (PPhat)
- GitHub: @pphatdev
- Website: stackdev.cloud
- Sharp - High-performance image processing
- Express.js - Fast, minimalist web framework
- Multer - Multipart/form-data handling
- Tailwind CSS - Utility-first CSS framework
- Drizzle ORM - TypeScript ORM for SQL databases
- Better-SQLite3 - Fast SQLite3 driver for Node.js
If you encounter any issues or have questions:
- Check the documentation
- Review existing issues
- Open a new issue with details
- Authentication & Authorization - JWT-based auth with role-based access
- Database System - SQLite with Drizzle ORM and migrations
- Session Management - Refresh tokens and session tracking
- Security Audit - Complete authentication audit trail
- Image Optimization - Multi-format support with Sharp
- File Management - Upload, organize, and manage files
- Rate Limiting - Endpoint-specific rate limiting
- Storage Analytics - Real-time storage statistics
- Web Dashboard - Visual interface for file management
- User profile management UI
- Two-factor authentication (2FA)
- Image watermarking
- Video processing support
- CDN integration (CloudFlare, AWS CloudFront)
- Automatic backup system
- Advanced analytics dashboard
- Webhook notifications
- API versioning
- API key system with per-key rate limiting
- File compression (ZIP archives)
- Batch operations API
- GraphQL API endpoint
- Email notifications
- Shared folder/file links
- 1.0.0 (February 2026)
- โ JWT authentication system
- โ SQLite database with Drizzle ORM
- โ Database migration system
- โ User management with roles
- โ Session tracking and refresh tokens
- โ Security audit logging
- โ File upload tracking in database
- โ Image optimization engine
- โ File management system
- โ Rate limiting
- โ Storage statistics
- โ Web dashboard
- โ Drizzle Studio integration
Made with โค๏ธ by pphatdev