Date & Time Get Certified
Working with dates and times is one of the more error-prone parts of everyday JavaScript. The built-in Date object gives you the tools to create, read, compare, and format dates — once you know its quirks.
Creating Dates
new Date() with no arguments gives you the current moment. You can also create a specific date by passing year, month, day (and optionally time), or by parsing a date string.
What this code does: This code shows several ways to create JavaScript Date objects: the current date and time, a specific date, a date with a specific time, and a date parsed from an ISO-style string.
const now = new Date();
console.log("Right now:", now);
// Year, month (0-indexed!), day
const specificDate = new Date(2024, 2, 15);
console.log("March 15, 2024:", specificDate);
// Year, month, day, hours, minutes, seconds
const withTime = new Date(2024, 2, 15, 14, 30, 0);
console.log("With a specific time:", withTime);
// Parsing an ISO date string
const parsed = new Date("2024-03-15T14:30:00");
console.log("Parsed from string:", parsed);
Watch out: the month argument is zero-indexed — 2 means March, not February. This trips up almost everyone at least once.
Reading Parts of a Date
A Date object has getter methods for every component — year, month, day, hours, and so on — all based on the browser’s local timezone by default.
What this code does: This code reads individual parts of a Date object, such as the year, month, day, weekday, hours, minutes, and the timestamp in milliseconds.
const date = new Date(2024, 2, 15, 9, 5, 0);
console.log("Full year:", date.getFullYear());
console.log("Month (0-indexed):", date.getMonth());
console.log("Day of month:", date.getDate());
console.log("Day of week (0 = Sunday):", date.getDay());
console.log("Hours:", date.getHours());
console.log("Minutes:", date.getMinutes());
console.log("Milliseconds since Jan 1, 1970:", date.getTime());
getDay() gives the day of the week (0 for Sunday through 6 for Saturday), while getDate() gives the day of the month — these two are easy to confuse.
Date Arithmetic
Date objects don’t have built-in “add days” methods. Instead, you read a part, add to it, and set it back. JavaScript automatically rolls the date over into the next month or year as needed.
What this code does: This code performs date arithmetic by adding days, adding months, and subtracting a year. JavaScript automatically adjusts the date when values roll into another month or year.
const today = new Date(2024, 2, 15);
console.log("Starting date:", today.toDateString());
// Add 10 days — JS rolls over into April automatically
const tenDaysLater = new Date(today);
tenDaysLater.setDate(tenDaysLater.getDate() + 10);
console.log("10 days later:", tenDaysLater.toDateString());
// Add 2 months
const twoMonthsLater = new Date(today);
twoMonthsLater.setMonth(twoMonthsLater.getMonth() + 2);
console.log("2 months later:", twoMonthsLater.toDateString());
// Subtract 1 year
const oneYearEarlier = new Date(today);
oneYearEarlier.setFullYear(oneYearEarlier.getFullYear() - 1);
console.log("1 year earlier:", oneYearEarlier.toDateString());
Notice new Date(today) is used to clone the original date before modifying it — calling .setDate() directly on today would mutate the original object in place.
Comparing Dates and Finding the Difference
Dates can be compared directly with < and >. Subtracting one date from another gives the difference in milliseconds, which you can convert into days, hours, or any other unit.
What this code does: This code compares two dates, calculates the number of days between them, and uses a reusable helper function to find the absolute difference between any two dates.
const deadline = new Date(2024, 5, 1);
const today = new Date(2024, 2, 15);
console.log("Is today before the deadline?", today < deadline);
const diffInMs = deadline - today;
const diffInDays = Math.round(diffInMs / (1000 * 60 * 60 * 24));
console.log("Days until deadline:", diffInDays);
function daysBetween(dateA, dateB) {
const msPerDay = 1000 * 60 * 60 * 24;
return Math.round(Math.abs(dateB - dateA) / msPerDay);
}
console.log("Days between (helper function):", daysBetween(today, deadline));
Formatting Dates for Display
Raw Date objects aren’t very readable. The built-in toLocaleDateString() and related methods give you locale-aware, human-friendly formatting without a library.
What this code does: This code demonstrates common date and time formatting methods, including the default string, ISO format, locale-specific date, detailed date, and locale-specific time.
const date = new Date(2024, 2, 15, 14, 30);
console.log("Default toString():", date.toString());
console.log("ISO format:", date.toISOString());
console.log("Locale date:", date.toLocaleDateString("en-US"));
console.log("Locale date, verbose:", date.toLocaleDateString("en-US", {
weekday: "long",
year: "numeric",
month: "long",
day: "numeric"
}));
console.log("Locale time:", date.toLocaleTimeString("en-US", {
hour: "2-digit",
minute: "2-digit"
}));
Quick Reference: Common Date Methods
| Method | Returns | Notes |
|---|---|---|
getFullYear() |
Four-digit year | Prefer this over the deprecated getYear() |
getMonth() |
0–11 | Zero-indexed — January is 0 |
getDate() |
1–31 | Day of the month |
getDay() |
0–6 | Day of the week (0 = Sunday) |
getTime() |
Milliseconds since Jan 1, 1970 | Useful for comparisons and arithmetic |
toISOString() |
ISO 8601 string (UTC) | Great for storing / transmitting dates |
toLocaleDateString() |
Locale-formatted string | Best for displaying dates to users |
Common Mistakes
- Forgetting that months are zero-indexed
- Mutating a shared Date object instead of cloning it first
- Mixing up local time and UTC
- Comparing dates with
===instead of</>or.getTime() - Manually building date strings instead of using locale-aware formatters
Best Practices
- Store and transmit dates as ISO 8601 strings or timestamps
- Use
toLocaleDateString()/toLocaleTimeString()for anything shown to users - Clone a Date before mutating it if the original is still needed
- Compare dates using
.getTime()or relational operators, never=== - Consider a well-maintained library for complex timezone or recurring-event needs
Quick Summary
new Date()creates the current moment; remember that months are zero-indexed- Getter methods read individual parts of a date in local time
- Date arithmetic works by reading a part, adding to it, and setting it back
- Subtracting two dates gives a difference in milliseconds
toLocaleDateString()andtoISOString()are the two main formatting methods
Try It Yourself
What this code does: This code combines reusable date functions to calculate days until a target date and to add business days while skipping Saturdays and Sundays.
function daysUntil(targetDate) {
const now = new Date();
const msPerDay = 1000 * 60 * 60 * 24;
const diff = targetDate - now;
return Math.ceil(diff / msPerDay);
}
function addBusinessDays(startDate, days) {
const result = new Date(startDate);
let added = 0;
while (added < days) {
result.setDate(result.getDate() + 1);
const dayOfWeek = result.getDay();
if (dayOfWeek !== 0 && dayOfWeek !== 6) {
added++;
}
}
return result;
}
const launchDate = new Date(2025, 0, 1);
console.log("Days until launch:", daysUntil(launchDate));
const start = new Date(2024, 2, 15);
const afterFiveBusinessDays = addBusinessDays(start, 5);
console.log("Start date:", start.toDateString());
console.log("5 business days later:", afterFiveBusinessDays.toDateString());
Tip: When a date bug shows up, check the month indexing and the local-vs-UTC distinction first — together they explain the vast majority of date-related bugs in JavaScript.
🧪 Test Your JavaScript Code
Edit the code on the left and click "Run Code" to see the console output on the right.
Click "Run Code" to see the output here.
Code Explanation
The complete example stays visible. Use Previous and Next to move through its logical blocks.
Select Next to begin exploring the code.