ChronoGo

A comprehensive Go datetime library with advanced parsing, business logic, holiday support, and enterprise-grade security

🚀 See ChronoGo's Power in Action:

ChronoGo.Today().AddDays(7)
"Sep 2, 2025"
🔥 v0.6.0 ⚡ 91.7% Coverage 🛡️ Security Hardened 🎄 Holiday Support 💼 Enterprise Ready

🎮 Code Examples

See ChronoGo's power in action with these example code demonstrations

🕐 Human Readable Times

Transform timestamps into natural language expressions

❌ Standard Go

// Complex manual calculation
now := time.Now()
diff := future.Sub(now)
days := int(diff.Hours() / 24)
fmt.Sprintf("in %d days", days)

✅ ChronoGo Magic

// One line of beauty
future.DiffForHumans()
// → "in 2 weeks"
// → "3 hours ago"
// → "next month"

🌍 Timezone Wizardry

Seamless timezone conversions and management

meeting := ChronoGo.Parse("2025-01-15 14:00")
  .InTimezone("America/New_York")

// Show in multiple timezones
fmt.Println("NYC:", meeting.Format("15:04"))
fmt.Println("Tokyo:", meeting.InTimezone("Asia/Tokyo").Format("15:04"))
fmt.Println("London:", meeting.InTimezone("Europe/London").Format("15:04"))


NYC: 14:00
Tokyo: 04:00 (next day)
London: 19:00

💼 Business Date Magic

Skip weekends and holidays automatically

// Project deadline in 10 business days
deadline := ChronoGo.Today().AddBusinessDays(10)

// Check if it's a holiday
isHoliday := deadline.IsHoliday()

// Get next business day if needed
nextWorkday := deadline.NextBusinessDay()


✅ Automatically skips weekends
✅ Handles US holidays 
✅ Custom holiday support

⛓️ Fluent API Power

Chain operations naturally

// Complex date manipulation in one line
result := ChronoGo.Now()
  .StartOfMonth()
  .AddDays(15)
  .SetHour(14)
  .SetMinute(30)
  .InTimezone("Europe/Paris")
  .Format("2006-01-02 15:04 MST")


2025-01-16 14:30 CET

🔄 Smart Iteration

Loop through time periods effortlessly

// Generate a week's schedule
start := ChronoGo.Date(2025, 1, 13) // Monday
end := start.AddDays(7)
period := ChronoGo.NewPeriod(start, end)

// Every 6 hours for a week
for _, time := range period.RangeByUnitSlice(ChronoGo.Hour, 6) {
    fmt.Println(time.Format("Mon 15:04"))
}


Mon 00:00, Mon 06:00, Mon 12:00, Mon 18:00
Tue 00:00, Tue 06:00, Tue 12:00, Tue 18:00
... (automatic iteration)

🚀 Advanced Parsing Features

New ISO 8601 extensions, token-based formats, and flexible parsing options

// ISO 8601 Ordinal dates (day of year)
ordinal1, _ := ChronoGo.Parse("2023-359")     // 2023-12-25
ordinal2, _ := ChronoGo.Parse("2024366")      // 2024-12-31 (compact)

// ISO 8601 Week dates  
week1, _ := ChronoGo.Parse("2023-W52-1")      // Monday of week 52
week2, _ := ChronoGo.Parse("2023W521")        // Compact format
week3, _ := ChronoGo.Parse("2023-W52")        // Defaults to Monday

// Token-based custom formats
date1, _ := ChronoGo.FromFormatTokens("25/12/2023 14:30", "DD/MM/YYYY HH:mm")
date2, _ := ChronoGo.FromFormatTokens("December 25, 2023", "MMMM D, YYYY")

// ISO 8601 Intervals
interval1, _ := ChronoGo.Parse("2023-01-01T00:00:00Z/2023-12-31T23:59:59Z")
interval2, _ := ChronoGo.Parse("2023-01-01T00:00:00Z/P1Y2M3DT4H5M6S")

// Fallback parsing with multiple format attempts
result, _ := ChronoGo.ParseWithFallback("Mon, 25 Dec 2023 10:30:45 UTC")


✅ Ordinal: 359th day = Dec 25, 2023
✅ Week: W52-1 = Monday Dec 25, 2023  
✅ Tokens: DD/MM/YYYY → 25/12/2023
✅ Intervals: Date ranges with durations
✅ Fallback: Tries multiple formats automatically

⚙️ Parsing with Options

Strict vs lenient parsing modes for different use cases

// Strict parsing - only allows exact formats
strictOptions := ChronoGo.ParseOptions{Strict: true}
result1, err := ChronoGo.Parse("2023-12-25T10:30:45Z", strictOptions)
// ✅ Succeeds - valid RFC3339

result2, err := ChronoGo.Parse("2023/12/25 10:30:45", strictOptions)  
// ❌ Fails - not RFC3339

// Lenient parsing - tries multiple formats
lenientOptions := ChronoGo.ParseOptions{Strict: false}
result3, _ := ChronoGo.Parse("2023/12/25 10:30:45", lenientOptions)
// ✅ Succeeds - automatically converts

// Multiple format parsing
formats := []string{"YYYY-MM-DD", "DD/MM/YYYY", "MMMM D, YYYY"}
result4, _ := ChronoGo.ParseMultiple("25/12/2023", formats)


🔒 Strict: Enforces exact format compliance
🔓 Lenient: Flexible format detection  
🎯 Multiple: Tries specific formats in order
⚡ Smart: Best of both worlds

🧠 Intelligent Parsing

Parse any format automatically

// All of these work automatically:
dates := []string{
    "2025-01-15T14:30:00Z",
    "Jan 15, 2025 2:30 PM",
    "15/01/2025 14:30",
    "1737470400", // Unix timestamp
    "tomorrow at 3pm",
}

for _, dateStr := range dates {
    dt, _ := ChronoGo.Parse(dateStr)
    fmt.Println(dt.Format("2006-01-02 15:04"))
}


✅ ISO 8601
✅ Natural language  
✅ Regional formats
✅ Unix timestamps
✅ Smart detection

🎂 Age & Duration Magic

Calculate ages, anniversaries, and precise durations

// Calculate someone's exact age
birthday := ChronoGo.Date(1990, 5, 15)
age := birthday.Age()
fmt.Printf("Age: %d years, %d months, %d days\n", 
    age.Years, age.Months, age.Days)

// Days until next birthday
nextBirthday := birthday.NextAnniversary()
daysUntil := ChronoGo.Now().DiffInDays(nextBirthday)

// Work anniversary
startDate := ChronoGo.Date(2020, 3, 1)
tenure := startDate.DiffForHumans()


Age: 35 years, 3 months, 8 days
Next birthday: in 264 days
Work tenure: 5 years ago

⚖️ Smart Time Comparisons

Intuitive date comparisons and validations

// Event planning made easy
eventDate := ChronoGo.Parse("2025-12-25")
now := ChronoGo.Now()

// Multiple comparison methods
isUpcoming := eventDate.IsFuture()
isPast := eventDate.IsPast()
isToday := eventDate.IsToday()
isWeekend := eventDate.IsWeekend()
isThisYear := eventDate.IsCurrentYear()

// Relative comparisons
isInDecember := eventDate.IsInMonth(12)
isSoon := eventDate.IsBetween(now, now.AddDays(30))


✅ Future event: true
✅ This year: true  
✅ Weekend: false
✅ Coming soon: false
✅ In December: true

📅 Calendar Intelligence

Navigate months, quarters, and calendar periods

// Financial quarters and reporting
today := ChronoGo.Today()
quarter := today.Quarter()
quarterStart := today.StartOfQuarter()
quarterEnd := today.EndOfQuarter()

// Get all Mondays in current month
firstMonday := today.StartOfMonth().NextWeekday(time.Monday)
var mondays []ChronoGo.DateTime
for monday := firstMonday; monday.Month() == today.Month(); monday = monday.AddDays(7) {
    mondays = append(mondays, monday)
}

// Fiscal year calculations
fiscalYearStart := today.StartOfFiscalYear(4) // April start


Current Quarter: Q3
Q3 Start: 2025-07-01
Q3 End: 2025-09-30
Mondays in Aug: [Aug 4, Aug 11, Aug 18, Aug 25]
Fiscal Year: 2025-04-01

🎄 Holiday & Business Logic

Enterprise-grade holiday support with GoHoliday integration

// Smart business day calculations
today := ChronoGo.Today()

// Check if today is a holiday (US by default)
if today.IsHoliday() {
    fmt.Println("It's a holiday!")
}

// Add 5 business days (skipping holidays)
workDeadline := today.AddBusinessDays(5)

// Get next business day
nextWorkDay := today.NextBusinessDay()

// Multi-country holiday support
ukChecker := ChronoGo.NewHolidayChecker("GB")
christmas := ChronoGo.Date(2025, 12, 25)
isUKHoliday := ukChecker.IsHoliday(christmas)

// Business days in current month
businessDays := today.BusinessDaysInMonth()


✅ Holiday check: false
✅ Work deadline: Aug 31, 2025  
✅ Next work day: Aug 27, 2025
✅ UK Christmas: true
✅ Business days this month: 22

⚡ Enhanced Business Calculator

High-performance business day operations with custom weekend support

// Create optimized business day calculator
calc := ChronoGo.NewEnhancedBusinessDayCalculator("US")

// Set custom weekends (e.g., Friday-Saturday for Middle East)
calc.SetCustomWeekends([]time.Weekday{time.Friday, time.Saturday})

// High-performance business day operations
today := ChronoGo.Today()
nextBiz := calc.NextBusinessDay(today)
bizDays := calc.BusinessDaysBetween(today, nextBiz.AddDays(30))

// Check if end of business month
isEOM := calc.IsEndOfMonth(today)


✅ Next business day: Aug 27, 2025
✅ Business days ahead: 22
✅ End of month: false
✅ Custom weekends: Fri-Sat

📅 Holiday-Aware Scheduler

Intelligent scheduling that respects holidays and business days

// Create holiday-aware scheduler for meetings
scheduler := ChronoGo.NewHolidayAwareScheduler("US")

// Schedule recurring weekly meetings (avoids holidays)
startDate := ChronoGo.Date(2025, 9, 1)
weeklyMeetings := scheduler.ScheduleRecurring(
    startDate, 7*24*time.Hour, 8) // 8 weeks

// Schedule monthly end-of-month reports
monthlyReports := scheduler.ScheduleMonthlyEndOfMonth(
    startDate, 6) // 6 months

// Schedule only on business days
businessMeetings := scheduler.ScheduleBusinessDays(startDate, 10)


✅ Weekly meetings: 8 scheduled
✅ Monthly reports: 6 scheduled  
✅ Business meetings: 10 scheduled
✅ All dates avoid holidays

🗓️ Holiday Calendar Integration

Calendar views with holiday information and upcoming tracking

// Create holiday calendar for any country
calendar := ChronoGo.NewHolidayCalendar("US")

// Get all holidays in current month
thisMonth := calendar.GetMonthlyHolidays(2025, time.August)

// Find upcoming holidays
upcoming := calendar.GetUpcomingHolidays(ChronoGo.Now(), 3)

// Generate full month calendar with holiday info
monthEntries := calendar.GenerateMonth(2025, time.December)

// Print formatted calendar
calendar.PrintMonth(2025, time.December)

// Access individual calendar entries
for _, entry := range monthEntries {
    if entry.IsHoliday {
        fmt.Printf("Holiday: %s\n", entry.String())
    }
}


✅ Aug holidays: Labor Day (Sep 2)
✅ Next 3 holidays found
✅ Full December calendar
✅ Holiday: 2025-12-25 (Thu) [HOLIDAY: Christmas Day]

🚀 Get Started in Seconds

Add ChronoGo to your project and start building amazing datetime experiences

1

Install

go get github.com/coredds/ChronoGo
2

Import

import "github.com/coredds/ChronoGo"
3

Use

dt := ChronoGo.Now().AddDays(30)
fmt.Println(dt.DiffForHumans()) // "in 4 weeks"

⚡ Quick Examples

Parse & Format

ChronoGo.Parse("2025-01-15").Format("Jan 2, 2006") → "Jan 15, 2025"

ISO 8601 Ordinal

ChronoGo.Parse("2023-359") → Dec 25, 2023 (359th day)

ISO 8601 Week Date

ChronoGo.Parse("2023-W52-1") → Monday of week 52

Token Formats

ChronoGo.FromFormatTokens("25/12/2023", "DD/MM/YYYY") → Dec 25, 2023

Business Days

ChronoGo.Today().AddBusinessDays(5) → Next Friday (skips weekends)

Human Time

someTime.DiffForHumans() → "2 hours ago"