← Back to Home
Time Databases APIs

Epoch Timestamps: Complete Developer Guide

Published: May 29, 2026 11 min read Intermediate Level

Unix epoch timestamps are the universal language of time in computing. Understanding how to work with them effectively is essential for building robust applications that handle dates and times correctly across different systems and timezones.

What is an Epoch Timestamp?

A Unix epoch timestamp represents the number of seconds that have elapsed since January 1, 1970, 00:00:00 UTC (Coordinated Universal Time), not counting leap seconds.

Key Characteristics

  • Zero Point: January 1, 1970, 00:00:00 UTC
  • Unit: Seconds (or milliseconds in some systems)
  • Timezone: Always UTC (timezone-independent)
  • Format: Integer or floating-point number
  • Range: 32-bit: 1901-2038, 64-bit: practically infinite

Why Use Epoch Timestamps?

1. Simplicity and Consistency

  • Single number instead of complex date strings
  • Easy to store, transmit, and compare
  • No timezone confusion (always UTC)

2. Mathematical Operations

Timestamps enable easy date calculations:

// Calculate time differences
const start = 1717000000;
const end = 1717003600;
const duration = end - start; // 3600 seconds (1 hour)

// Add time intervals
const now = Math.floor(Date.now() / 1000);
const oneDayLater = now + (24 * 60 * 60); // Add 1 day
const oneWeekLater = now + (7 * 24 * 60 * 60); // Add 1 week

3. Database Efficiency

  • Integer storage uses less space than datetime strings
  • Faster indexing and querying
  • Standardized across database systems

Timestamp Formats

Seconds (Unix Time)

  • Example: 1717000000
  • Precision: 1 second
  • Common in: Unix systems, APIs
  • Year 2038 Problem: 32-bit overflow

Milliseconds (JavaScript)

  • Example: 1717000000000
  • Precision: 1 millisecond
  • Common in: JavaScript, modern APIs
  • No 2038 Problem: 64-bit by default

Working with Timestamps in Different Languages

1. JavaScript/TypeScript

// Current timestamp (milliseconds)
const nowMs = Date.now(); // 1717000000000

// Current timestamp (seconds)
const nowSeconds = Math.floor(Date.now() / 1000); // 1717000000

// Convert timestamp to Date object
const date = new Date(1717000000000);
console.log(date.toISOString()); // "2024-05-30T12:26:40.000Z"

// Convert Date to timestamp
const timestamp = date.getTime(); // 1717000000000

// Format timestamp
const formatted = new Date(1717000000000).toLocaleString('en-US', {
    timeZone: 'America/New_York',
    dateStyle: 'full',
    timeStyle: 'long'
});

2. Python

import time
from datetime import datetime, timezone

# Current timestamp (seconds)
now_seconds = int(time.time())  # 1717000000

# Current timestamp (milliseconds)
now_ms = int(time.time() * 1000)  # 1717000000000

# Convert timestamp to datetime
dt = datetime.fromtimestamp(1717000000, tz=timezone.utc)
print(dt.isoformat())  # "2024-05-30T12:26:40+00:00"

# Convert datetime to timestamp
timestamp = int(dt.timestamp())  # 1717000000

# Format with timezone
formatted = dt.strftime('%Y-%m-%d %H:%M:%S %Z')

3. SQL Databases

-- PostgreSQL
SELECT 
    EXTRACT(EPOCH FROM NOW()),  -- Current timestamp in seconds
    EXTRACT(EPOCH FROM NOW()) * 1000,  -- In milliseconds
    TO_TIMESTAMP(1717000000),  -- Convert to timestamp
    TO_CHAR(TO_TIMESTAMP(1717000000), 'YYYY-MM-DD HH24:MI:SS');  -- Format

-- MySQL
SELECT 
    UNIX_TIMESTAMP(),  -- Current timestamp in seconds
    UNIX_TIMESTAMP(NOW()) * 1000,  -- In milliseconds
    FROM_UNIXTIME(1717000000),  -- Convert to datetime
    DATE_FORMAT(FROM_UNIXTIME(1717000000), '%Y-%m-%d %H:%i:%s');  -- Format

Common Operations and Calculations

1. Time Difference Calculations

function formatDuration(seconds) {
    const units = [
        { name: 'day', seconds: 86400 },
        { name: 'hour', seconds: 3600 },
        { name: 'minute', seconds: 60 },
        { name: 'second', seconds: 1 }
    ];
    
    const parts = [];
    let remaining = seconds;
    
    for (const unit of units) {
        const count = Math.floor(remaining / unit.seconds);
        if (count > 0) {
            parts.push(`${count} ${unit.name}${count !== 1 ? 's' : ''}`);
            remaining %= unit.seconds;
        }
    }
    
    return parts.length > 0 ? parts.join(', ') : '0 seconds';
}

// Example usage
const startTime = 1717000000;
const endTime = 1717007260; // 2 hours, 1 minute later
const duration = endTime - startTime; // 7260 seconds

console.log(formatDuration(duration)); // "2 hours, 1 minute"

2. Date Range Queries

// Get start and end of current day (in UTC)
function getTodayRange() {
    const now = new Date();
    const startOfDay = new Date(Date.UTC(
        now.getUTCFullYear(),
        now.getUTCMonth(),
        now.getUTCDate()
    ));
    const endOfDay = new Date(startOfDay);
    endOfDay.setUTCDate(endOfDay.getUTCDate() + 1);
    
    return {
        start: Math.floor(startOfDay.getTime() / 1000),
        end: Math.floor(endOfDay.getTime() / 1000) - 1
    };
}

// Get last 7 days
function getLast7Days() {
    const now = Math.floor(Date.now() / 1000);
    const sevenDaysAgo = now - (7 * 24 * 60 * 60);
    
    return { start: sevenDaysAgo, end: now };
}

// Database query example
const { start, end } = getTodayRange();
const query = `
    SELECT * FROM events 
    WHERE timestamp >= ${start} 
    AND timestamp <= ${end}
    ORDER BY timestamp DESC
`;

Timezone Handling

⚠️ Timezone Pitfalls

  • Assuming Local Time: Timestamps are always UTC
  • Daylight Saving Time: DST changes can break calculations
  • Server Timezone: Don't rely on server's local time
  • Browser Differences: Different browsers may handle timezones differently

Best Practices for Timezone Handling

// Always store and transmit in UTC
function storeTimestamp() {
    const timestamp = Math.floor(Date.now() / 1000); // UTC seconds
    // Store in database
    db.insert({ event_time: timestamp });
}

// Convert to local time for display
function displayTimestamp(timestamp, timezone = 'UTC') {
    const date = new Date(timestamp * 1000);
    return date.toLocaleString('en-US', {
        timeZone: timezone,
        dateStyle: 'medium',
        timeStyle: 'short'
    });
}

// Handle user timezone
function getUserLocalTime(timestamp) {
    const userTimezone = Intl.DateTimeFormat().resolvedOptions().timeZone;
    return displayTimestamp(timestamp, userTimezone);
}

// Example: Display event time in user's local timezone
const eventTimestamp = 1717000000;
const localTime = getUserLocalTime(eventTimestamp);
console.log(`Event time: ${localTime}`);

The Year 2038 Problem

32-bit systems will overflow on January 19, 2038 when the timestamp exceeds 2,147,483,647 seconds.

2038 Problem Solutions

✅ Use 64-bit Timestamps
  • Milliseconds since epoch
  • No overflow for billions of years
  • Standard in modern systems
⚠️ Legacy Systems
  • Update to 64-bit where possible
  • Use datetime strings as fallback
  • Plan migration before 2038

Best Practices

✅ Epoch Timestamp Best Practices

  • Always use UTC - Store and transmit timestamps in UTC
  • Use milliseconds for precision - JavaScript-style timestamps
  • Validate timestamps - Check for reasonable ranges
  • Handle timezones at display layer - Convert UTC to local time only for UI
  • Use ISO 8601 for APIs - Consider 2024-05-30T12:26:40Z format
  • Test across timezones - Ensure consistent behavior worldwide

Testing with Our Epoch Tool

Use our Epoch Converter Tool to:

  • Convert between timestamps and human-readable dates
  • Test different timestamp formats (seconds vs milliseconds)
  • Compare timezone conversions
  • Calculate date differences
  • Learn through practical examples

Real-World Examples

1. API Rate Limiting

class RateLimiter {
    constructor(limit, windowSeconds) {
        this.limit = limit;
        this.window = windowSeconds;
        this.requests = new Map(); // user_id -> timestamp[]
    }
    
    isAllowed(userId) {
        const now = Math.floor(Date.now() / 1000);
        const windowStart = now - this.window;
        
        // Get user's recent requests
        let userRequests = this.requests.get(userId) || [];
        
        // Filter out old requests
        userRequests = userRequests.filter(time => time > windowStart);
        
        // Check if under limit
        if (userRequests.length >= this.limit) {
            return false;
        }
        
        // Add current request
        userRequests.push(now);
        this.requests.set(userId, userRequests);
        
        return true;
    }
}

// Usage: 100 requests per hour
const limiter = new RateLimiter(100, 3600);
const canProceed = limiter.isAllowed('user123');

2. Cache Expiration

class Cache {
    constructor() {
        this.store = new Map(); // key -> { value, expires }
    }
    
    set(key, value, ttlSeconds) {
        const expires = Math.floor(Date.now() / 1000) + ttlSeconds;
        this.store.set(key, { value, expires });
    }
    
    get(key) {
        const entry = this.store.get(key);
        if (!entry) return null;
        
        const now = Math.floor(Date.now() / 1000);
        if (now > entry.expires) {
            this.store.delete(key);
            return null;
        }
        
        return entry.value;
    }
    
    cleanup() {
        const now = Math.floor(Date.now() / 1000);
        for (const [key, entry] of this.store.entries()) {
            if (now > entry.expires) {
                this.store.delete(key);
            }
        }
    }
}

// Usage: Cache with 5-minute TTL
const cache = new Cache();
cache.set('user:123', { name: 'John' }, 300); // 5 minutes
const user = cache.get('user:123');

Conclusion

Epoch timestamps provide a simple, efficient, and standardized way to work with time in software applications. By following best practices—storing in UTC, using appropriate precision, and handling timezones correctly—you can avoid common pitfalls and build robust time-handling functionality.

Remember that while timestamps are great for storage and calculations, consider using ISO 8601 strings for API responses to improve readability and interoperability.