This commit is contained in:
magdo
2025-11-25 20:53:34 +01:00
parent 5b7e361c21
commit 18e213bc31
357 changed files with 0 additions and 67989 deletions
+71
View File
@@ -0,0 +1,71 @@
# SerpentRace Production Server Environment Variables
# IMPORTANT: Change all placeholder values before deployment!
# Production settings
NODE_ENV=production
# Database Configuration
DB_HOST=postgres
DB_PORT=5432
DB_NAME=serpentrace
DB_USERNAME=postgres
# CHANGE THIS: Use a strong password
POSTGRES_PASSWORD=CHANGE_THIS_STRONG_DATABASE_PASSWORD_123!
# Redis Configuration
REDIS_URL=redis://redis:6379
REDIS_HOST=redis
REDIS_PORT=6379
# CHANGE THIS: Set a Redis password for security
REDIS_PASSWORD=CHANGE_THIS_REDIS_PASSWORD_123!
# JWT Configuration
# CHANGE THIS: Use a strong secret key (minimum 32 characters)
JWT_SECRET=CHANGE_THIS_JWT_SECRET_KEY_MINIMUM_32_CHARACTERS_FOR_PRODUCTION_SECURITY
JWT_EXPIRY=86400
JWT_EXPIRATION=24h
JWT_REFRESH_EXPIRATION=7d
# Email Configuration (SMTP)
# CHANGE THESE: Configure your email provider
EMAIL_HOST=smtp.yourmailprovider.com
EMAIL_PORT=587
EMAIL_SECURE=false
EMAIL_USER=your_email@yourdomain.com
EMAIL_PASS=your_email_password
EMAIL_FROM="SerpentRace <noreply@yourdomain.com>"
# MinIO Object Storage
MINIO_ENDPOINT=minio
MINIO_PORT=9000
MINIO_USE_SSL=false
# CHANGE THESE: Use strong credentials
MINIO_ACCESS_KEY=serpentrace_admin
MINIO_SECRET_KEY=CHANGE_THIS_MINIO_SECRET_KEY_123!
MINIO_BUCKET_NAME=serpentrace-logs
# Application Settings
APP_BASE_URL=http://your-domain.com
PORT=3000
# Chat System Limits
CHAT_INACTIVITY_TIMEOUT_MINUTES=30
CHAT_MAX_MESSAGES_PER_USER=100
CHAT_MESSAGE_CLEANUP_WEEKS=4
# Logging
MAX_LOGS_PER_FILE=10000
# SSL/TLS Configuration (if using HTTPS)
# Uncomment and configure if you have SSL certificates
# SSL_CERT_PATH=/path/to/certificate.crt
# SSL_KEY_PATH=/path/to/private.key
# SSL_CA_PATH=/path/to/ca-bundle.crt
# Security Headers (already configured in nginx)
# These are handled by the nginx configuration
# Backup Configuration (optional)
# BACKUP_ENABLED=true
# BACKUP_SCHEDULE=0 2 * * *
# BACKUP_RETENTION_DAYS=30
+203
View File
@@ -0,0 +1,203 @@
# SerpentRace Production Deployment Guide
## Overview
This package contains everything needed to deploy SerpentRace in a production environment using pre-built Docker images.
## Package Contents
- `serpentRaceDocker.tar` - All Docker images packed for deployment
- `docker-compose.deploy.yml` - Production Docker Compose configuration
- `.env.server` - Environment variables template for production
- `load-images.bat` - Automated deployment script for Windows servers
- `README.md` - This deployment guide
## System Requirements
- Windows Server 2016+ or Windows 10/11
- Docker Desktop or Docker Engine
- Docker Compose
- Minimum 4GB RAM, 20GB free disk space
- Network ports: 80, 443, 3000, 5432, 6379, 9000, 9001
## Pre-Deployment Configuration
### 1. Environment Variables
Edit `.env.server` and update the following **REQUIRED** settings:
```bash
# Database - Use a strong password
POSTGRES_PASSWORD=your_strong_database_password
# JWT Security - Use a random 32+ character string
JWT_SECRET=your_super_secret_jwt_key_32_chars_minimum
# Redis Security
REDIS_PASSWORD=your_redis_password
# MinIO Storage
MINIO_ACCESS_KEY=your_minio_admin_user
MINIO_SECRET_KEY=your_minio_secret_key
# Email Configuration (for notifications)
EMAIL_HOST=smtp.yourmailprovider.com
EMAIL_USER=your_email@yourdomain.com
EMAIL_PASS=your_email_password
EMAIL_FROM="SerpentRace <noreply@yourdomain.com>"
# Application URL
APP_BASE_URL=http://your-domain.com
```
### 2. Security Checklist
- [ ] Changed all default passwords
- [ ] Generated strong JWT secret (32+ characters)
- [ ] Configured email settings
- [ ] Updated domain name in APP_BASE_URL
- [ ] Configured firewall rules
- [ ] Planned SSL certificate setup
## Deployment Steps
### Automatic Deployment (Recommended)
1. Extract all files to your server directory
2. Edit `.env.server` with your configuration
3. Run `load-images.bat`
4. Follow the prompts
### Manual Deployment
1. Load Docker images:
```cmd
docker load -i serpentRaceDocker.tar
```
2. Start services:
```cmd
docker-compose -f docker-compose.deploy.yml --env-file .env.server up -d
```
## Post-Deployment
### Verify Services
Check that all services are running:
```cmd
docker-compose -f docker-compose.deploy.yml ps
```
### Access Points
- **Frontend Application**: http://localhost (or your domain)
- **Backend API**: http://localhost:3000
- **MinIO Console**: http://localhost:9001
- **Database**: localhost:5432 (internal access only)
### Initial Setup
1. Access the frontend and verify it loads
2. Test user registration and login
3. Check backend API health: http://localhost:3000/health
4. Access MinIO console to verify storage
### Security Hardening
#### Firewall Configuration
Open only necessary ports:
- Port 80 (HTTP) - Public
- Port 443 (HTTPS) - Public (when SSL configured)
- Ports 3000, 5432, 6379, 9000, 9001 - Internal/VPN only
#### SSL/TLS Setup
1. Obtain SSL certificates (Let's Encrypt, commercial CA)
2. Configure nginx for HTTPS in the frontend container
3. Update APP_BASE_URL to use https://
#### Regular Maintenance
- Monitor logs: `docker-compose -f docker-compose.deploy.yml logs -f`
- Update images periodically
- Backup database and MinIO data
- Monitor disk space and performance
## Management Commands
### View Logs
```cmd
# All services
docker-compose -f docker-compose.deploy.yml logs -f
# Specific service
docker-compose -f docker-compose.deploy.yml logs -f backend
```
### Restart Services
```cmd
# Restart all
docker-compose -f docker-compose.deploy.yml restart
# Restart specific service
docker-compose -f docker-compose.deploy.yml restart backend
```
### Stop Services
```cmd
docker-compose -f docker-compose.deploy.yml down
```
### Update Deployment
1. Stop current services
2. Load new images
3. Start services with new configuration
## Backup Strategy
### Database Backup
```cmd
docker exec serpentrace-postgres pg_dump -U postgres serpentrace > backup_$(date +%Y%m%d).sql
```
### Complete Backup
```cmd
# Stop services
docker-compose -f docker-compose.deploy.yml down
# Backup volumes
docker run --rm -v postgres_data:/data -v %cd%:/backup ubuntu tar czf /backup/postgres_backup.tar.gz -C /data .
docker run --rm -v minio_data:/data -v %cd%:/backup ubuntu tar czf /backup/minio_backup.tar.gz -C /data .
# Restart services
docker-compose -f docker-compose.deploy.yml up -d
```
## Troubleshooting
### Common Issues
#### Services Not Starting
1. Check Docker is running
2. Verify port availability
3. Check environment variables
4. Review logs for specific errors
#### Database Connection Issues
1. Verify POSTGRES_PASSWORD matches in .env.server
2. Check database container is healthy
3. Ensure network connectivity
#### Frontend Not Loading
1. Check nginx container status
2. Verify backend API is responding
3. Check browser console for errors
#### Performance Issues
1. Monitor resource usage: `docker stats`
2. Check available disk space
3. Review application logs
4. Consider scaling if needed
### Getting Help
- Check application logs for specific error messages
- Verify all environment variables are set correctly
- Ensure all required ports are available
- Contact support with log files and configuration details
## Version Information
- SerpentRace Backend: Latest
- Frontend: Latest
- PostgreSQL: 15-alpine
- Redis: 7-alpine
- MinIO: Latest
- Nginx: Alpine
+149
View File
@@ -0,0 +1,149 @@
version: '3.8'
services:
# Backend service using pre-built image
backend:
image: serpentrace_docker-backend:latest
container_name: serpentrace-backend
restart: unless-stopped
ports:
- "3000:3000"
environment:
- NODE_ENV=production
- PORT=3000
- DB_HOST=postgres
- DB_PORT=5432
- DB_NAME=serpentrace
- DB_USERNAME=postgres
- DB_PASSWORD=${POSTGRES_PASSWORD}
- REDIS_URL=redis://redis:6379
- REDIS_HOST=redis
- REDIS_PORT=6379
- JWT_SECRET=${JWT_SECRET}
- JWT_EXPIRATION=${JWT_EXPIRATION:-24h}
- JWT_REFRESH_EXPIRATION=${JWT_REFRESH_EXPIRATION:-7d}
- MINIO_ENDPOINT=minio
- MINIO_PORT=9000
- MINIO_ACCESS_KEY=${MINIO_ACCESS_KEY}
- MINIO_SECRET_KEY=${MINIO_SECRET_KEY}
- MINIO_USE_SSL=false
- EMAIL_HOST=${EMAIL_HOST}
- EMAIL_PORT=${EMAIL_PORT}
- EMAIL_SECURE=${EMAIL_SECURE}
- EMAIL_USER=${EMAIL_USER}
- EMAIL_PASS=${EMAIL_PASS}
- EMAIL_FROM=${EMAIL_FROM}
volumes:
- backend_logs:/app/logs
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
minio:
condition: service_healthy
networks:
- serpentrace-network
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
interval: 30s
timeout: 10s
retries: 3
start_period: 40s
# Frontend service using pre-built image
frontend:
image: serpentrace_docker-frontend:latest
container_name: serpentrace-frontend
restart: unless-stopped
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx.conf:/etc/nginx/conf.d/default.conf:ro
depends_on:
- backend
networks:
- serpentrace-network
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost/health"]
interval: 30s
timeout: 10s
retries: 3
# PostgreSQL Database
postgres:
image: postgres:15-alpine
container_name: serpentrace-postgres
restart: unless-stopped
ports:
- "5432:5432"
environment:
POSTGRES_DB: serpentrace
POSTGRES_USER: postgres
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
POSTGRES_INITDB_ARGS: "--encoding=UTF-8"
volumes:
- postgres_data:/var/lib/postgresql/data
- ./sql_schema_only.sql:/docker-entrypoint-initdb.d/init.sql
networks:
- serpentrace-network
healthcheck:
test: ["CMD-SHELL", "pg_isready -U postgres"]
interval: 10s
timeout: 5s
retries: 5
# Redis Cache
redis:
image: redis:7-alpine
container_name: serpentrace-redis
restart: unless-stopped
ports:
- "6379:6379"
volumes:
- redis_data:/data
command: redis-server --appendonly yes --requirepass ${REDIS_PASSWORD}
networks:
- serpentrace-network
healthcheck:
test: ["CMD", "redis-cli", "ping"]
interval: 10s
timeout: 5s
retries: 5
# MinIO Object Storage
minio:
image: minio/minio:latest
container_name: serpentrace-minio
restart: unless-stopped
ports:
- "9000:9000"
- "9001:9001"
environment:
MINIO_ROOT_USER: ${MINIO_ACCESS_KEY}
MINIO_ROOT_PASSWORD: ${MINIO_SECRET_KEY}
volumes:
- minio_data:/data
command: server /data --console-address ":9001"
networks:
- serpentrace-network
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:9000/minio/health/live"]
interval: 10s
timeout: 5s
retries: 5
volumes:
postgres_data:
driver: local
redis_data:
driver: local
minio_data:
driver: local
backend_logs:
driver: local
networks:
serpentrace-network:
driver: bridge
+103
View File
@@ -0,0 +1,103 @@
@echo off
REM SerpentRace Production Deployment Script
REM This script loads Docker images and starts the production environment
setlocal EnableDelayedExpansion
echo ===============================================
echo SerpentRace Production Deployment
echo ===============================================
echo.
REM Check if Docker is installed
where docker >nul 2>nul
if %errorlevel% neq 0 (
echo [ERROR] Docker is not installed. Please install Docker first.
pause
exit /b 1
)
where docker-compose >nul 2>nul
if %errorlevel% neq 0 (
echo [ERROR] Docker Compose is not installed. Please install Docker Compose first.
pause
exit /b 1
)
REM Check if serpentRaceDocker.tar exists
if not exist "serpentRaceDocker.tar" (
echo [ERROR] serpentRaceDocker.tar not found!
echo Please ensure the tar file is in the same directory as this script.
pause
exit /b 1
)
REM Check if environment file exists
if not exist ".env.server" (
echo [ERROR] .env.server file not found!
echo Please ensure the environment file is configured.
pause
exit /b 1
)
echo [INFO] Loading Docker images from serpentRaceDocker.tar...
docker load -i serpentRaceDocker.tar
if %errorlevel% neq 0 (
echo [ERROR] Failed to load Docker images!
pause
exit /b 1
)
echo [INFO] Images loaded successfully!
echo.
REM Show loaded images
echo [INFO] Loaded images:
docker images | findstr serpentrace
docker images | findstr postgres
docker images | findstr redis
docker images | findstr minio
echo.
echo [WARNING] Before starting the services, please review and update .env.server:
echo - Change all placeholder passwords
echo - Configure email settings
echo - Update domain names
echo - Set strong JWT secret
echo.
echo Press any key to continue with deployment or Ctrl+C to exit...
pause >nul
echo [INFO] Starting production services...
docker-compose -f docker-compose.deploy.yml --env-file .env.server up -d
if %errorlevel% neq 0 (
echo [ERROR] Failed to start services!
pause
exit /b 1
)
echo.
echo ===============================================
echo Deployment Complete!
echo ===============================================
echo.
echo Services are starting up. Please wait a few moments for all services to be ready.
echo.
echo Available services:
echo - Frontend: http://localhost (or your domain)
echo - Backend API: http://localhost:3000
echo - MinIO Console: http://localhost:9001
echo.
echo To check service status: docker-compose -f docker-compose.deploy.yml ps
echo To view logs: docker-compose -f docker-compose.deploy.yml logs -f [service_name]
echo To stop services: docker-compose -f docker-compose.deploy.yml down
echo.
echo IMPORTANT SECURITY NOTES:
echo 1. Change all default passwords in .env.server
echo 2. Configure firewall rules for your server
echo 3. Set up SSL/TLS certificates for HTTPS
echo 4. Configure regular backups
echo 5. Monitor logs and system resources
echo.
pause
+81
View File
@@ -0,0 +1,81 @@
#!/bin/bash
# SerpentRace Production Deployment Script for Linux
# This script loads Docker images and starts the production environment
set -e
echo "==============================================="
echo "SerpentRace Production Deployment"
echo "==============================================="
echo
# Check if Docker is installed
if ! command -v docker &> /dev/null; then
echo "[ERROR] Docker is not installed. Please install Docker first."
exit 1
fi
if ! command -v docker-compose &> /dev/null; then
echo "[ERROR] Docker Compose is not installed. Please install Docker Compose first."
exit 1
fi
# Check if serpentRaceDocker.tar exists
if [ ! -f "serpentRaceDocker.tar" ]; then
echo "[ERROR] serpentRaceDocker.tar not found!"
echo "Please ensure the tar file is in the same directory as this script."
exit 1
fi
# Check if environment file exists
if [ ! -f ".env.server" ]; then
echo "[ERROR] .env.server file not found!"
echo "Please ensure the environment file is configured."
exit 1
fi
echo "[INFO] Loading Docker images from serpentRaceDocker.tar..."
docker load -i serpentRaceDocker.tar
echo "[INFO] Images loaded successfully!"
echo
# Show loaded images
echo "[INFO] Loaded images:"
docker images | grep -E "(serpentrace|postgres|redis|minio)"
echo
echo "[WARNING] Before starting the services, please review and update .env.server:"
echo " - Change all placeholder passwords"
echo " - Configure email settings"
echo " - Update domain names"
echo " - Set strong JWT secret"
echo
read -p "Press Enter to continue with deployment or Ctrl+C to exit..."
echo "[INFO] Starting production services..."
docker-compose -f docker-compose.deploy.yml --env-file .env.server up -d
echo
echo "==============================================="
echo "Deployment Complete!"
echo "==============================================="
echo
echo "Services are starting up. Please wait a few moments for all services to be ready."
echo
echo "Available services:"
echo " - Frontend: http://localhost (or your domain)"
echo " - Backend API: http://localhost:3000"
echo " - MinIO Console: http://localhost:9001"
echo
echo "To check service status: docker-compose -f docker-compose.deploy.yml ps"
echo "To view logs: docker-compose -f docker-compose.deploy.yml logs -f [service_name]"
echo "To stop services: docker-compose -f docker-compose.deploy.yml down"
echo
echo "IMPORTANT SECURITY NOTES:"
echo "1. Change all default passwords in .env.server"
echo "2. Configure firewall rules for your server"
echo "3. Set up SSL/TLS certificates for HTTPS"
echo "4. Configure regular backups"
echo "5. Monitor logs and system resources"
echo
+60
View File
@@ -0,0 +1,60 @@
server {
listen 80;
server_name localhost;
root /usr/share/nginx/html;
index index.html index.htm;
# Enable gzip compression
gzip on;
gzip_vary on;
gzip_min_length 1024;
gzip_types text/plain text/css text/xml text/javascript application/javascript application/xml+rss application/json;
# Security headers
add_header X-Frame-Options "SAMEORIGIN" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-XSS-Protection "1; mode=block" always;
# Handle client routing
location / {
try_files $uri $uri/ /index.html;
}
# API proxy to backend
location /api/ {
proxy_pass http://backend:3000/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
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;
proxy_cache_bypass $http_upgrade;
}
# WebSocket support
location /socket.io/ {
proxy_pass http://backend:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
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;
}
# Static assets caching
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg)$ {
expires 1y;
add_header Cache-Control "public, immutable";
}
# Health check endpoint
location /health {
access_log off;
return 200 "healthy\n";
add_header Content-Type text/plain;
}
}
@@ -0,0 +1,14 @@
{
"Servers": {
"1": {
"Name": "SerpentRace Production",
"Group": "Servers",
"Host": "postgres",
"Port": 5432,
"MaintenanceDB": "serpentrace",
"Username": "postgres",
"SSLMode": "prefer",
"Comment": "SerpentRace Production Database"
}
}
}
Binary file not shown.
+236
View File
@@ -0,0 +1,236 @@
-- SerpentRace Database Schema
-- Generated from TypeORM Entity Aggregates
-- This file creates the complete database schema without initial data
-- Enable UUID extension
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
-- Create Users table
CREATE TABLE "Users" (
"id" UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
"orgid" UUID NULL,
"username" VARCHAR(100) UNIQUE NOT NULL,
"password" VARCHAR(255) NOT NULL,
"email" VARCHAR(255) UNIQUE NOT NULL,
"fname" VARCHAR(100) NOT NULL,
"lname" VARCHAR(100) NOT NULL,
"token" VARCHAR(255) NULL,
"TokenExpires" TIMESTAMP NULL,
"phone" VARCHAR(20) NULL,
"state" INTEGER NOT NULL DEFAULT 0,
"regdate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"updatedate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"Orglogindate" TIMESTAMP NULL
);
-- Create Organizations table
CREATE TABLE "Organizations" (
"id" UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
"name" VARCHAR(255) NOT NULL,
"contactfname" VARCHAR(100) NOT NULL,
"contactlname" VARCHAR(100) NOT NULL,
"contactphone" VARCHAR(20) NOT NULL,
"contactemail" VARCHAR(255) NOT NULL,
"state" INTEGER NOT NULL DEFAULT 0,
"regdate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"updatedate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"url" VARCHAR(500) NULL,
"userinorg" INTEGER NOT NULL DEFAULT 0,
"maxOrganizationalDecks" INTEGER NULL
);
-- Create Decks table
CREATE TABLE "Decks" (
"id" UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
"name" VARCHAR(255) NOT NULL,
"type" INTEGER NOT NULL,
"user_id" UUID NOT NULL,
"creation_date" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"cards" JSONB NOT NULL DEFAULT '[]',
"played_number" INTEGER NOT NULL DEFAULT 0,
"ctype" INTEGER NOT NULL DEFAULT 0,
"update_date" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"state" INTEGER NOT NULL DEFAULT 0,
"organization_id" UUID NULL
);
-- Create Chats table
CREATE TABLE "Chats" (
"id" UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
"type" VARCHAR(50) NOT NULL DEFAULT 'direct',
"name" VARCHAR(255) NULL,
"gameId" UUID NULL,
"createdBy" UUID NULL,
"users" UUID[] NOT NULL,
"messages" JSONB NOT NULL DEFAULT '[]',
"lastActivity" TIMESTAMP NULL,
"createDate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"updateDate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"state" INTEGER NOT NULL DEFAULT 0,
"archiveDate" TIMESTAMP NULL
);
-- Create Contacts table
CREATE TABLE "Contacts" (
"id" UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
"name" VARCHAR(255) NOT NULL,
"email" VARCHAR(255) NOT NULL,
"userid" UUID NULL,
"type" INTEGER NOT NULL,
"txt" TEXT NOT NULL,
"state" INTEGER NOT NULL DEFAULT 0,
"createDate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"updateDate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"adminResponse" TEXT NULL,
"responseDate" TIMESTAMP NULL,
"respondedBy" UUID NULL
);
-- Create Games table
CREATE TABLE "Games" (
"id" UUID PRIMARY KEY DEFAULT uuid_generate_v4(),
"gamecode" VARCHAR(10) UNIQUE NOT NULL,
"maxplayers" INTEGER NOT NULL,
"logintype" INTEGER NOT NULL DEFAULT 0,
"state" INTEGER NOT NULL DEFAULT 0,
"playerids" UUID[] NOT NULL DEFAULT '{}',
"decks" JSONB NOT NULL DEFAULT '[]',
"boardsize" INTEGER NOT NULL DEFAULT 50,
"createDate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"updateDate" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
"finishDate" TIMESTAMP NULL,
"winnerid" UUID NULL,
"createdBy" UUID NOT NULL,
"organizationid" UUID NULL
);
-- Add Foreign Key Constraints
ALTER TABLE "Users"
ADD CONSTRAINT "FK_Users_Organizations"
FOREIGN KEY ("orgid") REFERENCES "Organizations"("id") ON DELETE SET NULL;
ALTER TABLE "Decks"
ADD CONSTRAINT "FK_Decks_Users"
FOREIGN KEY ("user_id") REFERENCES "Users"("id") ON DELETE CASCADE;
ALTER TABLE "Decks"
ADD CONSTRAINT "FK_Decks_Organizations"
FOREIGN KEY ("organization_id") REFERENCES "Organizations"("id") ON DELETE SET NULL;
ALTER TABLE "Contacts"
ADD CONSTRAINT "FK_Contacts_Users"
FOREIGN KEY ("userid") REFERENCES "Users"("id") ON DELETE SET NULL;
ALTER TABLE "Contacts"
ADD CONSTRAINT "FK_Contacts_RespondedBy"
FOREIGN KEY ("respondedBy") REFERENCES "Users"("id") ON DELETE SET NULL;
ALTER TABLE "Chats"
ADD CONSTRAINT "FK_Chats_CreatedBy"
FOREIGN KEY ("createdBy") REFERENCES "Users"("id") ON DELETE SET NULL;
ALTER TABLE "Chats"
ADD CONSTRAINT "FK_Chats_Games"
FOREIGN KEY ("gameId") REFERENCES "Games"("id") ON DELETE SET NULL;
ALTER TABLE "Games"
ADD CONSTRAINT "FK_Games_CreatedBy"
FOREIGN KEY ("createdBy") REFERENCES "Users"("id") ON DELETE CASCADE;
ALTER TABLE "Games"
ADD CONSTRAINT "FK_Games_Organizations"
FOREIGN KEY ("organizationid") REFERENCES "Organizations"("id") ON DELETE SET NULL;
ALTER TABLE "Games"
ADD CONSTRAINT "FK_Games_Winner"
FOREIGN KEY ("winnerid") REFERENCES "Users"("id") ON DELETE SET NULL;
-- Create Indexes for Performance
CREATE INDEX "IDX_Users_Username" ON "Users" ("username");
CREATE INDEX "IDX_Users_Email" ON "Users" ("email");
CREATE INDEX "IDX_Users_OrgId" ON "Users" ("orgid");
CREATE INDEX "IDX_Users_State" ON "Users" ("state");
CREATE INDEX "IDX_Organizations_Name" ON "Organizations" ("name");
CREATE INDEX "IDX_Organizations_State" ON "Organizations" ("state");
CREATE INDEX "IDX_Decks_UserId" ON "Decks" ("user_id");
CREATE INDEX "IDX_Decks_Type" ON "Decks" ("type");
CREATE INDEX "IDX_Decks_CType" ON "Decks" ("ctype");
CREATE INDEX "IDX_Decks_State" ON "Decks" ("state");
CREATE INDEX "IDX_Decks_OrganizationId" ON "Decks" ("organization_id");
CREATE INDEX "IDX_Chats_Type" ON "Chats" ("type");
CREATE INDEX "IDX_Chats_State" ON "Chats" ("state");
CREATE INDEX "IDX_Chats_GameId" ON "Chats" ("gameId");
CREATE INDEX "IDX_Chats_CreatedBy" ON "Chats" ("createdBy");
CREATE INDEX "IDX_Contacts_Type" ON "Contacts" ("type");
CREATE INDEX "IDX_Contacts_State" ON "Contacts" ("state");
CREATE INDEX "IDX_Contacts_UserId" ON "Contacts" ("userid");
CREATE INDEX "IDX_Games_GameCode" ON "Games" ("gamecode");
CREATE INDEX "IDX_Games_State" ON "Games" ("state");
CREATE INDEX "IDX_Games_CreatedBy" ON "Games" ("createdBy");
CREATE INDEX "IDX_Games_OrganizationId" ON "Games" ("organizationid");
-- Create update trigger for updatedate columns
CREATE OR REPLACE FUNCTION update_updatedate_column()
RETURNS TRIGGER AS $$
BEGIN
NEW.updatedate = CURRENT_TIMESTAMP;
RETURN NEW;
END;
$$ language 'plpgsql';
-- Apply update triggers
CREATE TRIGGER update_users_updatedate
BEFORE UPDATE ON "Users"
FOR EACH ROW EXECUTE FUNCTION update_updatedate_column();
CREATE TRIGGER update_organizations_updatedate
BEFORE UPDATE ON "Organizations"
FOR EACH ROW EXECUTE FUNCTION update_updatedate_column();
CREATE TRIGGER update_decks_updatedate
BEFORE UPDATE ON "Decks"
FOR EACH ROW EXECUTE FUNCTION update_updatedate_column();
CREATE TRIGGER update_chats_updatedate
BEFORE UPDATE ON "Chats"
FOR EACH ROW EXECUTE FUNCTION update_updatedate_column();
CREATE TRIGGER update_contacts_updatedate
BEFORE UPDATE ON "Contacts"
FOR EACH ROW EXECUTE FUNCTION update_updatedate_column();
CREATE TRIGGER update_games_updatedate
BEFORE UPDATE ON "Games"
FOR EACH ROW EXECUTE FUNCTION update_updatedate_column();
-- Comments for documentation
COMMENT ON TABLE "Users" IS 'User accounts with authentication and profile information';
COMMENT ON TABLE "Organizations" IS 'Organizations that can have multiple users and premium features';
COMMENT ON TABLE "Decks" IS 'Card decks for the game, can be public, private, or organizational';
COMMENT ON TABLE "Chats" IS 'Chat system supporting direct messages, groups, and game chats';
COMMENT ON TABLE "Contacts" IS 'Contact form submissions and support tickets';
COMMENT ON TABLE "Games" IS 'Game sessions with players, decks, and game state';
-- Enum value comments
COMMENT ON COLUMN "Users"."state" IS '0=REGISTERED_NOT_VERIFIED, 1=VERIFIED_REGULAR, 2=VERIFIED_PREMIUM, 3=SOFT_DELETE, 4=DEACTIVATED, 5=ADMIN';
COMMENT ON COLUMN "Organizations"."state" IS '0=REGISTERED, 1=ACTIVE, 2=SOFT_DELETE';
COMMENT ON COLUMN "Decks"."type" IS '0=LUCK, 1=JOKER, 2=QUESTION';
COMMENT ON COLUMN "Decks"."ctype" IS '0=PUBLIC, 1=PRIVATE, 2=ORGANIZATION';
COMMENT ON COLUMN "Decks"."state" IS '0=ACTIVE, 1=SOFT_DELETE';
COMMENT ON COLUMN "Chats"."type" IS 'direct, group, game';
COMMENT ON COLUMN "Chats"."state" IS '0=ACTIVE, 1=ARCHIVE, 2=SOFT_DELETE';
COMMENT ON COLUMN "Contacts"."type" IS '0=BUG, 1=PROBLEM, 2=QUESTION, 3=SALES, 4=OTHER';
COMMENT ON COLUMN "Contacts"."state" IS '0=ACTIVE, 1=RESOLVED, 2=SOFT_DELETE';
COMMENT ON COLUMN "Games"."state" IS '0=WAITING, 1=ACTIVE, 2=FINISHED, 3=CANCELLED';
COMMENT ON COLUMN "Games"."logintype" IS '0=PUBLIC, 1=PRIVATE, 2=ORGANIZATION';
-- Grant permissions for application user
-- Note: Replace 'serpentrace_app' with your actual application database user
-- GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA public TO serpentrace_app;
-- GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA public TO serpentrace_app;
-- GRANT EXECUTE ON ALL FUNCTIONS IN SCHEMA public TO serpentrace_app;