M9 S3 (frontend): consolidate local-date helpers into notes/datetime.ts
The created-date range facets built local-day bounds by hand in two places (FilterBar's onTo/toInput, TimelineView's buildQuery) — parse a "YYYY-MM-DD", shift a day for the half-open upper bound, format back. - datetime.ts: parseLocalDate() / addLocalDays() (non-mutating) / formatLocalDay(). - TimelineView: drops its inline localDate() + the +1-day Date math. - FilterBar: drops its inline isoDay() + the setDate(±1) mutations. Behavior-preserving and deliberately NOT unifying output: Timeline still emits UTC (.toISOString()) bounds, FilterBar still emits naive-local "…T00:00:00" strings — only the shared primitives are extracted. (The naive-vs-UTC divergence is a separate backend-datetime-semantics question, flagged for later, not silently changed.) Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FRgehjoz7Yv8LkUfADxACm
This commit is contained in:
@@ -6,6 +6,7 @@ import { useSavedFiltersStore } from "../stores/savedFilters";
|
||||
import { useUiStore } from "../stores/ui";
|
||||
import type { NoteFacets } from "../stores/notes";
|
||||
import { facetCount, facetsFromQuery, facetsToQuery } from "../notes/facets";
|
||||
import { addLocalDays, formatLocalDay, parseLocalDate } from "../notes/datetime";
|
||||
import { NOTE_COLOR_KEYS, NOTE_COLOR_LABELS, NOTE_SWATCH_CLASSES, type NoteColor } from "../notes/colors";
|
||||
import Icon from "./Icon.vue";
|
||||
|
||||
@@ -56,30 +57,25 @@ function onQ(e: Event) {
|
||||
qTimer = setTimeout(() => patch({ q: v.trim() || undefined }), 300);
|
||||
}
|
||||
|
||||
function isoDay(d: Date): string {
|
||||
return `${d.getFullYear()}-${String(d.getMonth() + 1).padStart(2, "0")}-${String(d.getDate()).padStart(2, "0")}`;
|
||||
}
|
||||
function onFrom(e: Event) {
|
||||
const v = (e.target as HTMLInputElement).value;
|
||||
patch({ created_after: v ? `${v}T00:00:00` : undefined });
|
||||
}
|
||||
function onTo(e: Event) {
|
||||
const v = (e.target as HTMLInputElement).value;
|
||||
if (!v) {
|
||||
const d = v ? parseLocalDate(v) : null;
|
||||
if (!d) {
|
||||
patch({ created_before: undefined });
|
||||
return;
|
||||
}
|
||||
// Half-open upper bound: the start of the day AFTER the chosen date (so it's inclusive).
|
||||
const d = new Date(`${v}T00:00:00`);
|
||||
d.setDate(d.getDate() + 1);
|
||||
patch({ created_before: `${isoDay(d)}T00:00:00` });
|
||||
patch({ created_before: `${formatLocalDay(addLocalDays(d, 1))}T00:00:00` });
|
||||
}
|
||||
const fromInput = computed(() => (facets.value.created_after ?? "").slice(0, 10));
|
||||
const toInput = computed(() => {
|
||||
if (!facets.value.created_before) return "";
|
||||
const d = new Date(facets.value.created_before);
|
||||
d.setDate(d.getDate() - 1);
|
||||
return isoDay(d);
|
||||
// Reverse the half-open bound (day-after) back to the chosen end day for the input.
|
||||
const d = facets.value.created_before ? parseLocalDate(facets.value.created_before.slice(0, 10)) : null;
|
||||
return d ? formatLocalDay(addLocalDays(d, -1)) : "";
|
||||
});
|
||||
|
||||
async function saveView() {
|
||||
|
||||
Reference in New Issue
Block a user