The isAfter function checks if the first date is strictly after the second date. It provides flexible date comparison with optional unit-based granularity, allowing you to compare dates at different time scales (year, month, day, hour, minute, second, or millisecond).
function isAfter(
a: DateInput,
b: DateInput,
options?: ComparisonOptions,
): boolean;
| Parameter | Type | Description |
|---|---|---|
a |
DateInput |
The first date as a Date object, numeric timestamp, or ISO 8601 string |
b |
DateInput |
The second date as a Date object, numeric timestamp, or ISO 8601 string |
options |
ComparisonOptions |
Optional configuration object |
options.unit |
TimeUnit |
The unit of comparison: "year", "month", "day", "hour", "minute", "second", or "millisecond". Defaults to "millisecond" |
| Type | Description |
|---|---|
boolean |
Returns true if date a is strictly after date b, false otherwise or if either date is invalid |
The isAfter function determines whether the first date occurs chronologically after the second date. It supports both precise millisecond-level comparison and coarser-grained comparisons by truncating dates to a specified unit before comparing.
true when:a is chronologically after date b at the specified granularityNaN, not Infinity, not -Infinity)a is greater than the truncated value of bfalse when:a is equal to date b (strict comparison - equality is not “after”)a is before date ba or date b is invalid (Invalid Date, NaN, Infinity, -Infinity)a is lessfalse - this function checks if a is strictly after b, not after-or-equalfalse immediately without throwing exceptionsunit is specified, dates are truncated to that unit before comparison
"day" ignores hours, minutes, seconds, and milliseconds"year" ignores months, days, and all time componentsimport { isAfter } from "chronia";
// Check if content has expired
function hasExpired(expirationDate: Date): boolean {
return isAfter(Date.now(), expirationDate);
}
// Check if token is still valid
function isTokenExpired(tokenExpiryTimestamp: number): boolean {
const now = Date.now();
return isAfter(now, tokenExpiryTimestamp);
}
// Example usage
const subscriptionExpiry = new Date(2025, 0, 1); // January 1, 2025
hasExpired(subscriptionExpiry); // Returns: false (if current date is before Jan 1, 2025)
const tokenExpiry = Date.now() - 1000; // 1 second ago
isTokenExpired(tokenExpiry); // Returns: true
import { isAfter } from "chronia";
interface Activity {
user: string;
timestamp: number;
action: string;
}
// Filter activities after a specific date
function getRecentActivities(
activities: Activity[],
sinceDate: Date,
): Activity[] {
return activities.filter((activity) =>
isAfter(activity.timestamp, sinceDate),
);
}
// Get activities from the last 7 days
function getLastWeekActivities(activities: Activity[]): Activity[] {
const sevenDaysAgo = Date.now() - 7 * 24 * 60 * 60 * 1000;
return activities.filter((activity) =>
isAfter(activity.timestamp, sevenDaysAgo),
);
}
// Example usage
const activities: Activity[] = [
{ user: "alice", timestamp: new Date(2025, 0, 5).getTime(), action: "login" },
{ user: "bob", timestamp: new Date(2025, 0, 15).getTime(), action: "update" },
{
user: "charlie",
timestamp: new Date(2025, 0, 20).getTime(),
action: "create",
},
];
const cutoff = new Date(2025, 0, 10); // January 10, 2025
const recent = getRecentActivities(activities, cutoff);
// Returns: activities from bob (Jan 15) and charlie (Jan 20)
import { isAfter } from "chronia";
// Validate that an event is scheduled in the future
function isFutureEvent(
eventDate: Date,
referenceDate: Date = new Date(),
): boolean {
return isAfter(eventDate, referenceDate);
}
// Check if deadline is in the future
function hasTimeRemaining(deadline: number): boolean {
return isAfter(deadline, Date.now());
}
// Validate event scheduling constraints
function canScheduleEvent(eventDate: Date, minimumLeadTime: number): boolean {
const earliestAllowed = Date.now() + minimumLeadTime;
return isAfter(eventDate, earliestAllowed);
}
// Example usage
const futureEvent = new Date(2025, 11, 31); // December 31, 2025
isFutureEvent(futureEvent); // Returns: true (if current date is before Dec 31, 2025)
const deadline = Date.now() + 3 * 24 * 60 * 60 * 1000; // 3 days from now
hasTimeRemaining(deadline); // Returns: true
// Require at least 48 hours lead time
const eventDate = new Date(Date.now() + 72 * 60 * 60 * 1000); // 72 hours from now
const leadTime = 48 * 60 * 60 * 1000; // 48 hours
canScheduleEvent(eventDate, leadTime); // Returns: true
import { isAfter } from "chronia";
interface Event {
name: string;
timestamp: Date;
}
// Sort events in descending chronological order
function sortEventsDescending(events: Event[]): Event[] {
return events.sort((a, b) => {
if (isAfter(a.timestamp, b.timestamp)) return -1;
if (isAfter(b.timestamp, a.timestamp)) return 1;
return 0;
});
}
// Find the most recent event
function getMostRecentEvent(events: Event[]): Event | null {
if (events.length === 0) return null;
return events.reduce((latest, current) => {
return isAfter(current.timestamp, latest.timestamp) ? current : latest;
});
}
// Example usage
const events: Event[] = [
{ name: "Project Start", timestamp: new Date(2025, 0, 1) },
{ name: "Milestone 1", timestamp: new Date(2025, 2, 15) },
{ name: "Milestone 2", timestamp: new Date(2025, 5, 30) },
];
const sorted = sortEventsDescending(events);
// Returns: [Milestone 2 (Jun 30), Milestone 1 (Mar 15), Project Start (Jan 1)]
const latest = getMostRecentEvent(events);
// Returns: { name: 'Milestone 2', timestamp: ... }
import { isAfter } from "chronia";
// Validate date range
function isValidDateRange(start: Date, end: Date): boolean {
return isAfter(end, start);
}
// Validate booking dates
function validateBooking(
checkIn: Date,
checkOut: Date,
): { valid: boolean; error?: string } {
if (!isAfter(checkOut, checkIn)) {
return {
valid: false,
error: "Check-out date must be after check-in date",
};
}
if (!isAfter(checkIn, Date.now())) {
return {
valid: false,
error: "Check-in date must be in the future",
};
}
return { valid: true };
}
// Example usage
const startDate = new Date(2025, 0, 1); // January 1, 2025
const endDate = new Date(2025, 11, 31); // December 31, 2025
isValidDateRange(startDate, endDate); // Returns: true
isValidDateRange(endDate, startDate); // Returns: false
// Equality returns false (strict comparison)
const sameDate = new Date(2025, 0, 1);
isAfter(sameDate, sameDate); // Returns: false
const checkIn = new Date(2025, 6, 1); // July 1, 2025
const checkOut = new Date(2025, 6, 7); // July 7, 2025
validateBooking(checkIn, checkOut); // Returns: { valid: true }
import { isAfter } from "chronia";
// Compare dates at year granularity
const date1 = new Date(2025, 0, 1, 0, 0, 0); // January 1, 2025, 00:00:00
const date2 = new Date(2024, 11, 31, 23, 59, 59); // December 31, 2024, 23:59:59
isAfter(date1, date2, { unit: "year" }); // Returns: true (2025 > 2024)
// Compare dates at month granularity
const feb1 = new Date(2025, 1, 1); // February 1, 2025
const jan15 = new Date(2025, 0, 15); // January 15, 2025
isAfter(feb1, jan15, { unit: "month" }); // Returns: true (Feb > Jan)
// Compare dates at day granularity (ignores time)
const evening = new Date(2025, 0, 15, 18, 0, 0); // January 15, 2025, 18:00
const morning = new Date(2025, 0, 15, 9, 0, 0); // January 15, 2025, 09:00
isAfter(evening, morning, { unit: "day" }); // Returns: false (same day)
isAfter(evening, morning); // Returns: true (different times)
// Compare dates at hour granularity
const time1 = new Date(2025, 0, 15, 9, 45, 0); // 09:45:00
const time2 = new Date(2025, 0, 15, 9, 30, 0); // 09:30:00
isAfter(time1, time2, { unit: "hour" }); // Returns: false (same hour)
isAfter(time1, time2); // Returns: true (different minutes)
// Group events by year
function getEventsAfterYear(events: Event[], year: number): Event[] {
const referenceDate = new Date(year, 11, 31); // End of the reference year
return events.filter((event) =>
isAfter(event.timestamp, referenceDate, { unit: "year" }),
);
}