@@ -15,3 +15,67 @@ export const getNextQuotaReset = (referenceDate: Date | null): Date => {
1515 }
1616 return nextMonth
1717}
18+
19+ export interface FormatTimeUntilOptions {
20+ /**
21+ * What to return when the date is in the past or invalid.
22+ * @default 'now'
23+ */
24+ fallback ?: string
25+ /**
26+ * Whether to include the smaller unit (hours in "Xd Yh", minutes in "Xh Ym").
27+ * @default true
28+ */
29+ includeSubUnit ?: boolean
30+ }
31+
32+ /**
33+ * Format the time until a future date in a human-readable string.
34+ *
35+ * @param date - The target date (Date object or ISO string)
36+ * @param options - Formatting options
37+ * @returns Human-readable string like "4d 7h", "2h 30m", or "45m"
38+ *
39+ * @example
40+ * // Date 2 days and 5 hours in the future
41+ * formatTimeUntil(futureDate) // "2d 5h"
42+ * formatTimeUntil(futureDate, { includeSubUnit: false }) // "2d"
43+ *
44+ * // Date 3 hours and 20 minutes in the future
45+ * formatTimeUntil(futureDate) // "3h 20m"
46+ *
47+ * // Date in the past
48+ * formatTimeUntil(pastDate) // "now"
49+ * formatTimeUntil(pastDate, { fallback: '0h' }) // "0h"
50+ */
51+ export const formatTimeUntil = (
52+ date : Date | string | null ,
53+ options : FormatTimeUntilOptions = { } ,
54+ ) : string => {
55+ const { fallback = 'now' , includeSubUnit = true } = options
56+
57+ if ( ! date ) return fallback
58+
59+ const target = typeof date === 'string' ? new Date ( date ) : date
60+ const diffMs = target . getTime ( ) - Date . now ( )
61+
62+ if ( isNaN ( diffMs ) || diffMs <= 0 ) return fallback
63+
64+ const diffMins = Math . floor ( diffMs / ( 1000 * 60 ) )
65+ const diffHours = Math . floor ( diffMins / 60 )
66+ const diffDays = Math . floor ( diffHours / 24 )
67+ const remainingHours = diffHours % 24
68+ const remainingMins = diffMins % 60
69+
70+ if ( diffDays > 0 ) {
71+ return includeSubUnit && remainingHours > 0
72+ ? `${ diffDays } d ${ remainingHours } h`
73+ : `${ diffDays } d`
74+ }
75+ if ( diffHours > 0 ) {
76+ return includeSubUnit && remainingMins > 0
77+ ? `${ diffHours } h ${ remainingMins } m`
78+ : `${ diffHours } h`
79+ }
80+ return `${ diffMins } m`
81+ }
0 commit comments