mirror of
https://github.com/AgentSeal/codeburn.git
synced 2026-05-18 06:04:36 +00:00
fix(date-range): avoid all-period month overflow
This commit is contained in:
parent
3dc3e32715
commit
9a258a8a99
4 changed files with 20 additions and 17 deletions
|
|
@ -26,7 +26,7 @@ const PERIODS = [
|
|||
{ id: 'week', label: '7 Days' },
|
||||
{ id: '30days', label: '30 Days' },
|
||||
{ id: 'month', label: 'Month' },
|
||||
{ id: 'all', label: 'All Time' },
|
||||
{ id: 'all', label: '6 Months' },
|
||||
];
|
||||
|
||||
export default class CodeBurnPreferences extends ExtensionPreferences {
|
||||
|
|
|
|||
|
|
@ -113,7 +113,7 @@ export function getDateRange(period: string): { range: DateRange; label: string
|
|||
return { range: { start, end }, label: 'Last 30 Days' }
|
||||
}
|
||||
case 'all': {
|
||||
const start = new Date(now.getFullYear(), now.getMonth() - ALL_TIME_MONTHS, now.getDate())
|
||||
const start = new Date(now.getFullYear(), now.getMonth() - ALL_TIME_MONTHS, 1)
|
||||
return { range: { start, end }, label: 'Last 6 months' }
|
||||
}
|
||||
default: {
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ import { dateKey } from './day-aggregator.js'
|
|||
import { CompareView } from './compare.js'
|
||||
import { getPlanUsageOrNull, type PlanUsage } from './plan-usage.js'
|
||||
import { planDisplayName } from './plans.js'
|
||||
import { getDateRange as getDateRangeShared, PERIODS, PERIOD_LABELS, type Period } from './cli-date.js'
|
||||
import { getDateRange, PERIODS, PERIOD_LABELS, type Period } from './cli-date.js'
|
||||
import { join } from 'path'
|
||||
import { patchStdoutForWindows } from './ink-win.js'
|
||||
|
||||
|
|
@ -96,7 +96,7 @@ function gradientColor(pct: number): string {
|
|||
}
|
||||
|
||||
function getPeriodRange(period: Period): { start: Date; end: Date } {
|
||||
return getDateRangeShared(period).range
|
||||
return getDateRange(period).range
|
||||
}
|
||||
|
||||
type Layout = { dashWidth: number; wide: boolean; halfWidth: number; barWidth: number }
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { describe, it, expect } from 'vitest'
|
||||
import { afterEach, describe, it, expect, vi } from 'vitest'
|
||||
import {
|
||||
getDateRange,
|
||||
PERIODS,
|
||||
|
|
@ -7,6 +7,10 @@ import {
|
|||
type Period,
|
||||
} from '../src/cli-date.js'
|
||||
|
||||
afterEach(() => {
|
||||
vi.useRealTimers()
|
||||
})
|
||||
|
||||
describe('getDateRange', () => {
|
||||
it('"all" is bounded to the last 6 months, not epoch', () => {
|
||||
const { range, label } = getDateRange('all')
|
||||
|
|
@ -18,27 +22,26 @@ describe('getDateRange', () => {
|
|||
// dashboard bug) or any pre-2000 date.
|
||||
expect(range.start.getFullYear()).toBeGreaterThan(2000)
|
||||
|
||||
// Roughly 6 months back. Accept 5-7 months to absorb end-of-month
|
||||
// clamping (e.g. on May 31, JS rolls Nov 31 -> Dec 1, shifting the
|
||||
// computed month forward by one).
|
||||
const monthsDiff =
|
||||
(now.getFullYear() - range.start.getFullYear()) * 12 +
|
||||
(now.getMonth() - range.start.getMonth())
|
||||
expect(monthsDiff).toBeGreaterThanOrEqual(5)
|
||||
expect(monthsDiff).toBeLessThanOrEqual(7)
|
||||
expect(monthsDiff).toBe(6)
|
||||
expect(range.start.getDate()).toBe(1)
|
||||
|
||||
// End is today, end of day.
|
||||
expect(range.end.getHours()).toBe(23)
|
||||
expect(range.end.getMinutes()).toBe(59)
|
||||
})
|
||||
|
||||
it('CLI and dashboard agree on "all" semantics (no Date(0) drift)', () => {
|
||||
const a = getDateRange('all')
|
||||
const b = getDateRange('all')
|
||||
expect(a.range.start.getTime()).toBe(b.range.start.getTime())
|
||||
expect(a.label).toBe(b.label)
|
||||
// Regression guard: must never silently fall back to epoch.
|
||||
expect(a.range.start.getFullYear()).toBeGreaterThan(2000)
|
||||
it('"all" does not overflow past the target month at end-of-month', () => {
|
||||
vi.useFakeTimers()
|
||||
vi.setSystemTime(new Date(2026, 7, 31, 12, 0, 0))
|
||||
|
||||
const { range } = getDateRange('all')
|
||||
|
||||
expect(range.start.getFullYear()).toBe(2026)
|
||||
expect(range.start.getMonth()).toBe(1)
|
||||
expect(range.start.getDate()).toBe(1)
|
||||
})
|
||||
|
||||
it('"week" returns the last 7 days', () => {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue