Dates without timezone surprises.
DaySafe is a lightweight, zero-dependency TypeScript library for safe, predictable calendar date operations. Pure civil arithmetic, strict validation, and branded types.
const diff = daysBetween(baseDate, nextDate);
JavaScript dates are not always calendar dates.
The native JavaScript Date object was designed for millisecond timestamps. When applications use timestamps to store dates of birth, invoices, or hotel reservations, timezone boundaries inevitably distort the data.
1Off-By-One Day Timezone Bug
Parsing ISO date strings shifts backward by 1 full day in Western timezones.
// In New York (America/New_York, UTC-5):
const d = new Date("2026-11-02");
console.log(d.getDate()); // 1 (November 1st!)// With DaySafe in any timezone:
const d = parseDate("2026-11-02");
console.log(d); // "2026-11-02"2DST Transition Distortions
Subtracting timestamps and dividing by 86,400,000 yields fractional days on 23h/25h days.
// Spring DST transition (23-hour day):
const diff = (t2 - t1) / (1000 * 60 * 60 * 24);
console.log(diff); // 1.9583 days (breaks billing!)// Exact civil calendar day arithmetic:
const diff = daysBetween("2026-03-07", "2026-03-09");
console.log(diff); // 2 (exact integer days)3Silent Rollover on Invalid Dates
JavaScript Date silently normalizes impossible days like Feb 30 into March 2.
// Invalid calendar day silently accepted:
new Date(2026, 1, 30);
// Becomes March 2nd without warning!// Strict Gregorian calendar validation:
parseDate("2026-02-30");
// Returns null (rejected immediately)4Legacy Two-Digit Year Quirks
Date.UTC(25, 0, 1) silently treats year 25 as 1925 instead of civil year 0025.
// Legacy quirk for years 0-99:
new Date(Date.UTC(25, 0, 1)).getUTCFullYear();
// 1925 (Unexpected century mapping!)// Uniform handling across years 0001 - 9999:
fromDateParts({ year: 25, month: 1, day: 1 });
// "0025-01-01" (pure civil year)Treat dates like dates.
DaySafe eliminates timestamp conversion entirely. By modeling dates strictly as Gregorian calendar values, your application gains 100% predictable arithmetic and airtight type safety.
Strict YYYY-MM-DD Strings
Canonical ISO 8601 calendar date representation without time or timezone offset ambiguity.
Branded DateOnly Type
Compile-time nominal typing prevents arbitrary unvalidated strings from passing into critical calculations.
Integer Civil Calendar Math
Based on Howard Hinnant's proven calendar algorithms for pure integer day-number arithmetic.
Predictable Month Clamping
Adding 1 month to January 31 safely resolves to February 28 (or 29 in leap years), never overflowing into March.
Timezone Independence
Calculations occur on civil calendar units. Running in Tokyo, London, or San Francisco yields identical answers.
UTC-Safe Locale Formatting
Native Intl.DateTimeFormat locked to UTC calendar day so localized strings never shift day boundaries.
Engineered for bulletproof calendar math.
Every feature is verified in the source code, backed by strict unit tests, and guaranteed zero runtime dependencies.
Timezone-Independent
Operations execute on calendar dates without local machine timezone offsets or UTC conversions ever shifting the date.
Strict Date Validation
Validates YYYY-MM-DD for Gregorian years 0001 to 9999. Rejects timestamps, non-strings, year 0000, and impossible days like Feb 30.
Date-Only Branded Types
Nominal DateOnly branded strings prevent unvalidated strings from being passed into calculations without validation.
Accurate Leap-Year Support
Full Gregorian century rules: 2024 is a leap year, 1900 is not, and 2000 is a leap year. Accurate February 29 handling.
Predictable Month Math
Safe month-end clamping prevents dates from silently spilling into the following month (e.g. Jan 31 + 1 mo = Feb 28).
DST-Independent Differences
Guaranteed exact signed integer day differences without timestamp division fractional errors on 23-hour or 25-hour DST days.
Locale-Aware Formatting
Leverages native Intl.DateTimeFormat locked to UTC, ensuring localized format strings never cross day boundaries.
Zero Runtime Dependencies
Exactly zero dependencies in production. Lightweight, audit-friendly, and minimal footprint in your application bundle.
Dual ESM & CommonJS
Pre-bundled with tsup into modern ECMAScript Modules (.mjs) and CommonJS (.js) with comprehensive .d.ts and .d.mts declarations.
Try DaySafe in real-time.
Switch operations and tweak parameters below to see actual in-browser calculations and generated code.
2026-02-30 into parseDate to watch DaySafe strictly reject non-existent calendar days without throwing an unhandled exception.import { addMonths } from "daysafe";
const result = addMonths("2026-01-31", 1);
// "2026-02-28"Designed for TypeScript purists.
No heavy class instances, no monkey-patching prototypes, no global state. Just pure functions, branded types, and instant autocompletion.
Install and import in seconds.
DaySafe distributes dual ESM and CommonJS modules with pre-generated declaration files. Bundlers like Vite, Next.js, Rollup, and esbuild tree-shake everything with zero extra configuration.
Pure Functional Design
All operations accept inputs and return new values without mutating dates.
Zero Runtime Dependencies
No external packages, no risk of supply-chain vulnerabilities.
Complete Autocomplete & TSDoc
Full descriptions, parameters, throws, and code examples visible right in your IDE.
400 font-semibold">import { addDays, isValidDate, parseDate } 400 font-semibold">from 400 font-semibold">class="text-emerald-400">"daysafe";// 1. Strict parsing with narrowing400 font-semibold">const userInput: unknown = 400 font-semibold">class="text-emerald-400">"2026-11-02";400 font-semibold">if (isValidDate(userInput)) {// userInput is automatically typed as DateOnly!400 font-semibold">const nextWeek = addDays(userInput, 7);console.log(nextWeek); 400 font-semibold">class=400 font-semibold">class="text-emerald-400">"text-slate-500 italic">// 400 font-semibold">class="text-emerald-400">"2026-11-09"}// 2. Direct string usage is also allowed:400 font-semibold">const end = addDays(400 font-semibold">class="text-emerald-400">"2026-11-02", 30);console.log(end); 400 font-semibold">class=400 font-semibold">class="text-emerald-400">"text-slate-500 italic">// 400 font-semibold">class="text-emerald-400">"2026-12-02"
Built for real-world software.
From regulated enterprise fintech to consumer booking platforms, calendar dates are mission-critical.
Booking & Hospitality
Calculate exact night counts between check-in and check-out dates without DST transitions causing 1.95 fractional day errors.
Date of Birth & Age Verification
Strictly validate birthdays, verify 18+ legal age thresholds, and safely handle leap-day (Feb 29) birthdays without silent rollover.
Billing & Invoicing
Compute exact Net-30 payment due dates, roll weekend deadlines to Monday, and print timezone-immune invoice dates.
Subscription Scheduling
Add monthly billing cycles with end-of-month clamping (Jan 31 rolls to Feb 28, not March 3).
Examination Platforms
Ensure exam schedules, application windows, and submission deadlines fall on identical calendar dates worldwide.
Database DATE Serialization
Bind directly to PostgreSQL, MySQL, and SQLite DATE columns without the JavaScript Date timestamp timezone offset shifts.
Calendar UI Components
Generate 42-cell month grids with startOfMonth, endOfMonth, and getDayOfWeek in pure civil time.
How DaySafe processes dates.
By bypassing JavaScript timestamp conversions entirely, DaySafe ensures your calendar calculations remain deterministic, auditable, and timezone-free.
DateInput
DateOnly | stringAccepts either branded DateOnly values or standard ISO 8601 calendar strings ('YYYY-MM-DD').
Strict Validation
ECMAScript SpecValidates year range (0001 - 9999), month bounds (1-12), and leap-year rules. Rejects timestamps and non-dates.
Civil Day Calculations
Howard Hinnant AlgorithmsTransforms calendar components into civil day integers for exact math, free of timezone and DST interference.
DateOnly Result
Branded StringReturns immutable, nominal DateOnly string or formatted output with native Intl locked to UTC.
Make calendar dates predictable.
Eliminate timezone offsets, DST clock distortion, and silent invalid date rollovers. Start using DaySafe today with zero runtime dependencies.