feat: Add timezone configuration for Docker to ensure correct time handling in production and development environments

This commit is contained in:
2025-10-04 20:52:39 +02:00
parent 9357c2e0b9
commit 5011f80fc4
6 changed files with 295 additions and 0 deletions

156
DOCKER_TIMEZONE_FIX.md Normal file
View File

@@ -0,0 +1,156 @@
# Docker Timezone Configuration Fix
## Problem
Even after fixing the SQLite `datetime('now', 'localtime')` calls, notes posted at 10:00 still showed as 08:00 when running in Docker.
## Root Cause
**Docker containers run in UTC timezone by default!**
When using `datetime('now', 'localtime')` in SQLite:
- On local Windows machine: Uses Windows timezone (Europe/Warsaw) → ✅ Correct
- In Docker container: Uses container timezone (UTC) → ❌ Wrong by 2 hours
Example:
```
User posts at 10:00 Poland time (UTC+2)
Docker container thinks local time is 08:00 UTC
SQLite datetime('now', 'localtime') stores: 08:00
Display shows: 08:00 (wrong!)
```
## Solution
Set the Docker container timezone to Europe/Warsaw
### 1. Updated Dockerfile (Production)
```dockerfile
# Use Node.js 22.11.0 as the base image
FROM node:22.11.0
# Set timezone to Europe/Warsaw (Polish timezone)
ENV TZ=Europe/Warsaw
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
# ... rest of Dockerfile
```
### 2. Updated Dockerfile.dev (Development)
```dockerfile
# Use Node.js 22.11.0 as the base image
FROM node:22.11.0
# Set timezone to Europe/Warsaw (Polish timezone)
ENV TZ=Europe/Warsaw
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone
# ... rest of Dockerfile
```
### 3. Updated docker-compose.yml (Development)
```yaml
environment:
- NODE_ENV=development
- TZ=Europe/Warsaw
```
### 4. Updated docker-compose.prod.yml (Production)
```yaml
environment:
- NODE_ENV=production
- TZ=Europe/Warsaw
- NEXTAUTH_SECRET=...
- NEXTAUTH_URL=...
```
## How to Apply
### Option 1: Rebuild Docker Images
```bash
# Stop containers
docker-compose down
# Rebuild images
docker-compose build --no-cache
# Start containers
docker-compose up -d
```
### Option 2: For Production Deployment
```bash
# Pull latest code with fixes
git pull
# Rebuild production image
docker-compose -f docker-compose.prod.yml build --no-cache
# Restart
docker-compose -f docker-compose.prod.yml up -d
```
## Verification
After rebuilding and restarting, verify timezone inside container:
```bash
# Check timezone
docker exec -it <container_name> date
# Should show: Sat Oct 4 19:00:00 CEST 2025
# Check Node.js sees correct timezone
docker exec -it <container_name> node -e "console.log(new Date().toLocaleString('pl-PL', {timeZone: 'Europe/Warsaw'}))"
# Should show current Polish time
# Check SQLite sees correct timezone
docker exec -it <container_name> node -e "const db = require('better-sqlite3')('./data/database.sqlite'); console.log(db.prepare(\"SELECT datetime('now', 'localtime')\").get());"
# Should show current Polish time
```
## Why This Works
1. **TZ Environment Variable**: Tells all processes (including Node.js and SQLite) what timezone to use
2. **Symlink /etc/localtime**: Updates system timezone for the entire container
3. **echo TZ > /etc/timezone**: Ensures the timezone persists
Now when SQLite uses `datetime('now', 'localtime')`:
- Container local time is 10:00 Poland time
- SQLite stores: 10:00
- Display shows: 10:00 ✅
## Important Notes
1. **Must rebuild images**: Just restarting containers is not enough - the timezone configuration is baked into the image
2. **All existing data**: Old notes will still show incorrect times (they were stored in UTC)
3. **New notes**: Will now display correctly
4. **DST handling**: Europe/Warsaw automatically handles Daylight Saving Time transitions
## Alternative Approach (Not Recommended)
Instead of changing container timezone, you could:
1. Store everything in UTC (like audit logs do with ISO format)
2. Always convert on display
But this requires more code changes and the current approach is simpler and more maintainable.
## Files Modified
1. `Dockerfile` - Added TZ configuration
2. `Dockerfile.dev` - Added TZ configuration
3. `docker-compose.yml` - Added TZ environment variable
4. `docker-compose.prod.yml` - Added TZ environment variable
## Testing Checklist
After deployment:
- [ ] Container shows correct date/time with `docker exec <container> date`
- [ ] Post a new note at known time (e.g., 10:30)
- [ ] Verify note displays the same time (10:30)
- [ ] Check both project notes and task notes
- [ ] Verify audit logs still work correctly
- [ ] Check task timestamps (date_started, date_completed)