This is a Node.js application built with Express.js, Sequelize (ORM for PostgreSQL), and other libraries to provide user authentication, PDF generation, file upload, video streaming, and WebSocket functionalities.
- User Registration and Authentication (JWT)
- User Profile Management
- PDF Generation from user data, raw data, or HTML content
- Image Uploads for user profiles
- Email notifications (welcome email)
- Video Streaming with byte-range support
- WebSocket API for real-time communication
- External API integrations (Fake Store API, Random User API)
GET /: Fetches a list of products from a fake product API.GET /error: Triggers a test error for demonstration of global error handling.
POST /auth/register: Register a new user.- Request Body:
name,email,password,image(multipart/form-data)
- Request Body:
POST /auth/login: Log in a user.- Request Body:
email,password
- Request Body:
PUT /auth/update: Update user profile (requires authentication).- Request Body:
name,image(multipart/form-data)
- Request Body:
GET /pdf/generate: Generate a PDF of the authenticated user's profile.POST /pdf/generate-from-data: Generate a PDF from provided title and content.- Request Body:
title,content
- Request Body:
POST /pdf/generate-from-html: Generate a PDF from HTML content (uses worker threads for performance).- Request Body:
htmlContent
- Request Body:
GET /outside/product-list: Fetches a list of products from Fake Store API.GET /outside/random-user: Fetches a random user from Random User API.
GET /ws: Endpoint for WebSocket connections. Connect using a WebSocket client (e.g.,ws://localhost:PORT/ws). Sends random text every 3 seconds.
GET /stream/video/:filename: Streams a video file from theassetsfolder. Supports byte-range requests for seeking.- Example:
http://localhost:PORT/stream/video/sample.mp4
- Example:
- Node.js (v18 or higher recommended)
- PostgreSQL
- Git
-
Clone the repository:
git clone <repository_url> cd new_project
-
Install dependencies:
npm install
Create a .env file in the root directory of the project with the following variables:
PORT=3000
JWT_SECRET=your_jwt_secret_key
DB_NAME=your_database_name
DB_USER=your_database_user
DB_PASSWORD=your_database_password
DB_HOST=localhost
DB_DIALECT=postgres
EMAIL=your_email@gmail.com
PASSWORD=your_email_app_password # For Gmail, use an App PasswordNote on EMAIL and PASSWORD: If you are using Gmail, you will need to generate an App Password. Go to your Google Account -> Security -> App passwords.
-
Start the application in development mode (with nodemon):
npm run dev
-
Start the application in production mode:
npm start
The server will typically run on http://localhost:3000 (or the PORT you specified in .env).
-
Install Homebrew (if you don't have it):
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)" -
Install PostgreSQL:
brew install postgresql
-
Start PostgreSQL:
brew services start postgresql
-
Stop PostgreSQL:
brew services stop postgresql
-
Restart PostgreSQL:
brew services restart postgresql
-
Access the PostgreSQL prompt:
psql postgres
-
Create a new user (replace
your_database_userandyour_database_password):CREATE USER your_database_user WITH PASSWORD 'your_database_password';
-
Create a new database (replace
your_database_name):CREATE DATABASE your_database_name;
-
Grant all privileges on the database to the user:
GRANT ALL PRIVILEGES ON DATABASE your_database_name TO your_database_user;
-
Exit the PostgreSQL prompt:
\q
-
Download and install PG Admin: Visit pgAdmin website and download the installer for macOS.
-
Open pgAdmin and right-click on "Servers" in the left sidebar. Select "Register" -> "Server...".
-
In the "General" tab:
- Name:
My Local PostgreSQL(or any descriptive name)
- Name:
-
In the "Connection" tab:
- Host name/address:
localhost - Port:
5432(default) - Maintenance database:
postgres(or your database name) - Username:
your_database_user(the one you created) - Password:
your_database_password(the one you created) - Save password: (Optional, but recommended for convenience)
- Host name/address:
-
Click "Save". You should now be connected to your PostgreSQL server.
After setting up your database and .env file, run the migrations to create the necessary tables:
npx sequelize-cli db:migrate- Authentication Controller (
authController.js):- Removed inefficient
allUsersqueries during registration and login. - Corrected password comparison logic in login.
- Switched to asynchronous file reading for welcome email template.
- Removed duplicate
verifyTokenfunction (now handled by middleware). - Added HTML escaping for user data in welcome email to prevent XSS.
- Removed inefficient
- PDF Controller (
pdfController.js):- Ensured
puppeteer.launch()usesheadless: 'new'for better performance. - Implemented
try...finallyblock to guaranteebrowser.close()is called. - Implemented
worker_threadsfor PDF generation from HTML to offload CPU-intensive tasks from the main thread. - Added basic URL validation for
user.imageto mitigate SSRF vulnerabilities.
- Ensured
- Upload Middleware (
uploadMiddleware.js):- Added file type validation (JPEG, PNG, GIF only) and a 5MB size limit for uploads.
- Mail Client Utility (
mailClient.js):- Refactored to create a single, reusable Nodemailer transporter instance, avoiding redundant creation on each email send.
- Removed
nodemailer.createTestAccount()anddotenv.config()from this file.
- Error Handling:
- Implemented a custom
AppErrorclass for better distinction between operational and programming errors. - Enhanced global error handler to correctly return specific status codes for operational errors (e.g., 404 Not Found).
- Implemented a custom
- Security Hardening:
- HTTP Header Hardening: Integrated
helmetmiddleware to set various security-related HTTP headers (e.g.,X-Content-Type-Options,X-Frame-Options,X-XSS-Protection,Strict-Transport-Security,Referrer-Policy). - Content Security Policy (CSP): Configured a basic CSP using
helmetto control resource loading and mitigate XSS.
- HTTP Header Hardening: Integrated
- Video Streaming:
- Implemented byte-range requests for efficient streaming of large video files.
- Enabled dynamic video selection by filename from the
assetsfolder. - Added improved error handling for file not found scenarios.
- Included HTTP caching headers for better performance on repeated requests.
- WebSocket API:
- Created a dedicated WebSocket API route (
/ws) that sends random text every 3 seconds. - Refactored WebSocket logic into a separate controller for better modularity.
- Created a dedicated WebSocket API route (