{"record":{"id":"d6ac8ea0f231fc90","repo":"vuetifyjs/vuetify","slug":"end-date-is-earlier-than-start-date","errorCode":null,"errorMessage":"End date is earlier than start date.","messagePattern":"End date is earlier than start date\\.","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/vuetify/src/components/VCalendar/util/timestamp.ts","lineNumber":440,"sourceCode":"  return new Date(`${date}T${time}:00+00:00`)\n}\n\nexport function createDayList (\n  start: CalendarTimestamp,\n  end: CalendarTimestamp,\n  now: CalendarTimestamp,\n  weekdaySkips: number[],\n  max = 42,\n  min = 0\n): CalendarTimestamp[] {\n  const stop = getDayIdentifier(end)\n  const days: CalendarTimestamp[] = []\n  let current = copyTimestamp(start)\n  let currentIdentifier = 0\n  let stopped = currentIdentifier === stop\n\n  if (stop < getDayIdentifier(start)) {\n    throw new Error('End date is earlier than start date.')\n  }\n\n  while ((!stopped || days.length < min) && days.length < max) {\n    currentIdentifier = getDayIdentifier(current)\n    stopped = stopped || currentIdentifier === stop\n    if (weekdaySkips[current.weekday] === 0) {\n      current = nextDay(current)\n      continue\n    }\n    const day = copyTimestamp(current)\n    updateFormatted(day)\n    updateRelative(day, now)\n    days.push(day)\n    current = relativeDays(current, nextDay, weekdaySkips[current.weekday])\n  }\n\n  if (!days.length) throw new Error('No dates found using specified start date, end date, and weekdays.')\n","sourceCodeStart":422,"sourceCodeEnd":458,"githubUrl":"https://github.com/vuetifyjs/vuetify/blob/8d153908dffb7592eb389ddbfbab955a0ccc977f/packages/vuetify/src/components/VCalendar/util/timestamp.ts#L422-L458","documentation":"Thrown by createDayList() in VCalendar when getDayIdentifier(end) < getDayIdentifier(start). The day identifier is YYYYMMDD as a number, so this is a pure date-ordering check independent of time. The function builds the visible day range for a calendar view and cannot iterate backwards.","triggerScenarios":"Calling createDayList with a start timestamp whose date is after the end timestamp's date. In components this comes from props where `start` and `end` resolve to inverted dates (e.g. start='2024-01-31', end='2024-01-01'), or when a weekday-skew/interval miscalculation produces an end before start.","commonSituations":"Swapping start/end prop bindings, off-by-one in a custom range picker, timezone shifts that move the end date backwards across the day boundary, or feeding a manually-constructed CalendarTimestamp whose year/month/day are inconsistent.","solutions":["Verify start <= end at the call site before invoking createDayList.","Compare getDayIdentifier(start) and getDayIdentifier(end) and swap or reject when inverted.","Check the component props (start/end) that feed the calendar; correct the binding direction.","Ensure timezone conversion happens before identifier computation so the day boundaries align."],"exampleFix":"// before\nconst days = createDayList(start, end, now, weekdaySkips)\n\n// after\nimport { getDayIdentifier } from 'vuetify/util/timestamp'\nif (getDayIdentifier(end) < getDayIdentifier(start)) {\n  throw new RangeError(`end ${end.date} before start ${start.date}`)\n}\nconst days = createDayList(start, end, now, weekdaySkips)","handlingStrategy":"validation","validationCode":"import { getDayIdentifier, createDayList, type CalendarTimestamp } from 'vuetify/util/timestamp'\n\nfunction safeDayList(start: CalendarTimestamp, end: CalendarTimestamp, now: CalendarTimestamp, skips: number[]) {\n  if (getDayIdentifier(end) < getDayIdentifier(start)) {\n    throw new RangeError(`end ${end.date} is before start ${start.date}`)\n  }\n  return createDayList(start, end, now, skips)\n}","typeGuard":"import { getDayIdentifier, type CalendarTimestamp } from 'vuetify/util/timestamp'\nfunction isOrderedRange(start: CalendarTimestamp, end: CalendarTimestamp): boolean {\n  return getDayIdentifier(start) <= getDayIdentifier(end)\n}","tryCatchPattern":"try {\n  return createDayList(start, end, now, skips)\n} catch (e) {\n  if (e instanceof Error && /earlier than start date/.test(e.message)) {\n    // swap and retry, or return empty\n    return createDayList(end, start, now, skips)\n  }\n  throw e\n}","preventionTips":["Always pair start/end from a single source of truth so ordering is guaranteed.","Validate ranges in your date-picker model before forwarding to the calendar.","Beware timezone offsets shifting the day identifier; normalize to the desired TZ first."],"tags":["vcalendar","date-range","precondition"],"backgroundTag":null,"analyzedSha":"8d153908dffb7592eb389ddbfbab955a0ccc977f","analyzedAt":"2026-08-12T21:54:20.596Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}