What Number Is My Computer Using Right Now?
Open a browser console and type Date.now(). You get a thirteen-digit integer. That number is the current Unix epoch time in milliseconds: the count of milliseconds since 00:00:00 UTC on 1 January 1970. Divide by a thousand and you have the classic Unix timestamp, the ten-digit count that underpins file systems, databases, TLS certificates, and nearly every API you touch.
The number contains no month, no weekday, no country, no time zone. That absence is the design. A single integer sorts chronologically, parses without ambiguity, and survives a round trip through JSON, a log aggregator, and a database replica without anyone needing to agree on a date format. The formal name is POSIX time, and the standard that defines it treats every day as exactly 86,400 seconds, a simplification that keeps arithmetic fast at the cost of a small drift from astronomical reality.
What the Number Leaves Out
No time zone. No calendar system. No daylight saving flag. The integer is the same in Tokyo, São Paulo, and a server rack in Ashburn, Virginia. Only when you format it for human eyes does a zone enter the picture.
Seconds, Milliseconds, or Something Else?
A ten-digit value is in seconds. Thirteen digits means milliseconds. Sixteen digits means microseconds. Nineteen digits means nanoseconds. Mistaking one for another throws a date off by roughly a factor of a thousand, landing you in 1970 or tens of millennia in the future. If a converted value falls outside a plausible window (before 1990 or after 2100), the unit is almost certainly wrong, not the data.
Why Does Unix Epoch Time Start at 1970?
The origin was a retrofit. Early Unix developers at Bell Labs needed a recent, round starting point their hardware could count from without overflowing within the machine's expected lifetime. The beginning of 1970 was the nearest convenient boundary when the work was done.
Dennis Ritchie later explained that at the time they had a 60Hz clock and the epoch was whenever they last rebooted. It was standardized to 1970-01-01 after the fact. No astronomical event, no calendar reform, no historical milestone. Just a boundary that made the numbers work for the hardware of the era.
What matters is that everybody adopted it. Java, JavaScript, Python, Go, Rust, MySQL, PostgreSQL, and effectively every network protocol that carries a timestamp use the same origin.
The Hardware Constraint
A 60Hz clock increments sixty times per second. Counting from a recent reboot kept the numbers small. Standardizing to a fixed date made the system portable across machines.
Adoption Beyond Unix
The epoch outlived the operating system that gave it its name. HTTP cookies use it. TLS certificates embed it. Cloud storage object metadata carries it. The agreement on a single origin is more valuable than any technical property of the date itself.
What Is the Year 2038 Problem?
The C programming language gave Unix its time type: time_t. Originally a signed 32-bit integer on most platforms, it counts whole seconds. A 32-bit signed integer tops out at 2,147,483,647, which means the maximum representable moment is 03:14:07 UTC on 19 January 2038. After that, the count overflows and wraps to a negative value.
The 64-bit transition began in the 1990s and completed on most modern operating systems by the 2010s. A 64-bit signed time_t handles roughly 292 billion years. But 32-bit environments persist: embedded controllers, older databases, some file systems. Linux kernel 5.6, released in 2020, fixed the remaining 32-bit time_t uses internally. Plenty of hardware still runs older kernels.
Where 32-bit Still Lives
Embedded devices in vehicles, industrial controllers, and consumer appliances often run stripped-down operating systems that never migrated. A thermostat installed in 2015 may still be counting with 32 bits.
The Overflow Moment
19 January 2038 at 03:14:07 UTC. After that moment, a 32-bit signed counter rolls to a negative number. Platforms that rely on the value for ordering, expiry, or comparison will behave unpredictably.
How Does POSIX Handle Leap Seconds?
The POSIX.1 standard mandates that every day is exactly 86,400 seconds. No exceptions. POSIX time ignores leap seconds entirely. When the International Earth Rotation and Reference Systems Service inserts a leap second into UTC, the POSIX count does not adjust. The two diverge slightly.
The rule exists for simplicity. If every time calculation had to consult a leap-second table, arithmetic would require a lookup. The cost is a slow drift from solar time. The standard accepts that trade-off.
The 27-Second Gap
As of 2026, 27 leap seconds have been inserted since the practice began in 1972. None have been added since 31 December 2016, the longest gap on record.
Abolition by 2035
The General Conference on Weights and Measures voted in November 2022 to abolish leap seconds by 2035, replacing them with a larger correction at longer intervals. When that happens, POSIX time's 86,400-second day will align more closely with civil timekeeping.
Milliseconds, Microseconds, and Nanoseconds: Which Unit Is This?
JavaScript uses milliseconds. Date.now() returns a thirteen-digit value, and the Date constructor expects the same. A JavaScript timestamp is roughly a thousand times larger than a Unix timestamp for the identical moment.
Go and many databases store nanosecond precision. Python's time.time() returns a float with microsecond resolution. The pattern is consistent: if you see ten digits, it is seconds. Thirteen digits means milliseconds. Sixteen digits means microseconds. Nineteen digits means nanosecond.
JavaScript's Choice
The language specification defines the Date object as millisecond precision since the epoch. Every browser, every Node.js runtime, every embedded JavaScript engine follows this. There is no configuration flag.
Database Variations
MySQL's UNIX_TIMESTAMP() returns seconds. Its NOW(6) returns a datetime with microsecond precision. PostgreSQL's EXTRACT(epoch FROM now()) returns a double-precision value with microsecond granularity. Check the documentation for the platform you are using; the unit is not consistent across products.
Can Unix Epoch Time Represent Dates Before 1970?
Yes. A negative integer is a moment before the epoch. The value -1 is 23:59:59 UTC on 31 December 1969. The value -86400 is exactly one day before the origin, at midnight starting 31 December 1969.
Negative values are legal and correctly handled by most platforms. They are uncommon because few applications need dates before 1970, but they exist. Birth dates, historical records, and astronomical data all require them.
How Far Back Can It Go?
A 64-bit signed integer reaches billions of years in both directions. A 32-bit signed integer covers roughly 1902 to 2038. For practical historical work, 64-bit is sufficient.
Platforms That Reject Negatives
Some older libraries and file formats treat negative timestamps as errors. If you are ingesting historical data, verify that every layer of the pipeline accepts signed values.
Epoch in Logs, APIs, and Databases
Every JSON API you have used probably carries a Unix timestamp somewhere. Log files use them because they are unambiguous across zones. Databases store them because they sort naturally and require no string parsing.
The core question is whether you need seconds, millisecond, or finer granularity. For an API, millisecond is the safest default because JavaScript and most front-end tooling expect it. For debugging logs, seconds are usually sufficient. For performance tracing, you will want nanosecond.
API Design Default
Return millisecond precision from REST endpoints. Front-end code can consume the value directly with new Date(millis). No parsing, no format negotiation.
Log Correlation
When logs from servers in different zones carry epoch timestamps, sorting them into a single timeline requires no zone conversion. The integer order is the chronological order.
Common Pitfalls With Unix Epoch Time
The most frequent mistake is treating the count as if it had a zone. It does not. Conversion to local time is a display concern. Store the count; format it for display.
The second mistake is assuming every environment uses seconds. JavaScript uses millisecond. Go's time.Time.Unix() returns seconds, but time.Now().UnixNano() returns nanosecond. MySQL's UNIX_TIMESTAMP() returns seconds, but its fractional-second functions differ.
The third is the overflow problem. If you are building software that will still run in 2038, check whether your dependencies use 32-bit or 64-bit integers for time. Most modern stacks are fine. Embedded devices, legacy databases, and some file systems are not.
Zone Confusion in Practice
A timestamp stored as an integer and then formatted in a different zone than intended produces a wrong wall-clock reading. The integer itself is correct. The formatting step introduced the error.
Unit Mismatch Symptoms
A date in 1970 or far in the future is the classic sign. Divide or multiply by 1,000 and the date snaps back to the present.
The 2038 Check
Ask your embedded vendor. Check your database version. If your platform runs a 32-bit kernel, the clock will wrap. Most cloud instances are 64-bit. The device in a car or a building management panel may not be.