@mt-gloss/utils 0.1.151 → 0.1.153
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/index.d.ts +1 -1
- package/index.js +85 -102
- package/lib/toLocalCalendarDate.d.ts +36 -0
- package/package.json +1 -1
- package/lib/featureFlags/index.d.ts +0 -2
- package/lib/featureFlags/v1_1_flags.d.ts +0 -45
package/index.d.ts
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
export { isStatusModeEnabled, v1_1_status_mode, V1_1_STATUS_MODE_ENV, isEdgeHoverResizeEnabled, v1_1_edge_hover_resize, V1_1_EDGE_HOVER_RESIZE_ENV } from './lib/featureFlags';
|
|
2
1
|
export type { PresetDefinition, MarketPreset, DateRange, MarketEvent } from './lib/types';
|
|
3
2
|
export { formatValue, getValueFontSize, pickMetricTier } from './lib/formatValue';
|
|
4
3
|
export type { FormatValueOptions, FormattedValue, MetricTier, PickMetricTierResult } from './lib/formatValue';
|
|
@@ -8,6 +7,7 @@ export { hexToRgba, lerpHex } from './lib/color';
|
|
|
8
7
|
export { getTransitionStyle, interpolate, parseNumericValue } from './lib/cssAnimation';
|
|
9
8
|
export { daysBetween } from './lib/daysBetween';
|
|
10
9
|
export type { DaysBetweenOptions, DaysBetweenRounding } from './lib/daysBetween';
|
|
10
|
+
export { toLocalCalendarDate } from './lib/toLocalCalendarDate';
|
|
11
11
|
export { formatTrend } from './lib/formatTrend';
|
|
12
12
|
export type { TrendDirection, FormattedTrend } from './lib/formatTrend';
|
|
13
13
|
export { formatDateRange, formatMarketDates, isMarketActive, isSameDay, isInRange, generateMarketId } from './lib/dateHelpers';
|
package/index.js
CHANGED
|
@@ -1,35 +1,20 @@
|
|
|
1
|
-
import { D as
|
|
2
|
-
|
|
3
|
-
function $() {
|
|
4
|
-
return typeof globalThis < "u" && globalThis.__GLOSS_FLAGS__?.v1_1_status_mode === !0 ? !0 : typeof process < "u" && process.env ? process.env[m] === "true" : !1;
|
|
5
|
-
}
|
|
6
|
-
const p = {
|
|
7
|
-
env: m,
|
|
8
|
-
check: $
|
|
9
|
-
}, d = "NEXT_PUBLIC_V1_1_EDGE_HOVER_RESIZE";
|
|
10
|
-
function h() {
|
|
11
|
-
return typeof globalThis < "u" && globalThis.__GLOSS_FLAGS__?.v1_1_edge_hover_resize === !0 ? !0 : typeof process < "u" && process.env ? process.env[d] === "true" : !1;
|
|
12
|
-
}
|
|
13
|
-
const M = {
|
|
14
|
-
env: d,
|
|
15
|
-
check: h
|
|
16
|
-
};
|
|
17
|
-
function D(t, { prefix: e = "", suffix: n = "", abbreviated: r = !0, kThreshold: o = 1e3 } = {}) {
|
|
1
|
+
import { D as Y, y as w, P as O, n as v, o as C, R as V, T as z, d as H, t as j, f as k, b as B, k as G, l as K, c as q, h as W, x as Z, g as J, q as Q, j as X, m as tt, u as et, i as nt, v as rt, p as at, a as ot, r as st, s as it, e as ct, w as ut } from "./formatting-dHqp6ksD.js";
|
|
2
|
+
function m(t, { prefix: e = "", suffix: n = "", abbreviated: r = !0, kThreshold: o = 1e3 } = {}) {
|
|
18
3
|
if (t == null) {
|
|
19
4
|
const l = e ? `${e} —${n}` : `—${n}`;
|
|
20
5
|
return { display: l.trim(), full: l.trim(), length: l.trim().length };
|
|
21
6
|
}
|
|
22
7
|
const a = typeof t == "number" ? t : parseFloat(String(t).replace(/,/g, ""));
|
|
23
8
|
if (isNaN(a)) {
|
|
24
|
-
const
|
|
25
|
-
return { display:
|
|
9
|
+
const c = `${e}${t}${n}`;
|
|
10
|
+
return { display: c, full: c, length: c.length };
|
|
26
11
|
}
|
|
27
12
|
let s;
|
|
28
13
|
r !== !1 && Math.abs(a) >= 1e6 ? s = (a / 1e6).toFixed(1).replace(/\.0$/, "") + "M" : r !== !1 && Math.abs(a) >= o ? s = (a / 1e3).toFixed(1).replace(/\.0$/, "") + "K" : s = a.toLocaleString("en-US");
|
|
29
|
-
const i = `${e}${s}${n}`,
|
|
30
|
-
return { display: i, full:
|
|
14
|
+
const i = `${e}${s}${n}`, u = `${e}${a.toLocaleString("en-US")}${n}`;
|
|
15
|
+
return { display: i, full: u, length: i.length };
|
|
31
16
|
}
|
|
32
|
-
function
|
|
17
|
+
function h(t, e) {
|
|
33
18
|
return (e ?? 1) >= 2 ? t <= 4 || t <= 6 ? 30 : t <= 8 ? 24 : 20 : t <= 5 ? 28 : t <= 8 ? 20 : 17;
|
|
34
19
|
}
|
|
35
20
|
const f = {
|
|
@@ -40,21 +25,21 @@ const f = {
|
|
|
40
25
|
3: 12
|
|
41
26
|
// "$1,234,567"
|
|
42
27
|
};
|
|
43
|
-
function
|
|
28
|
+
function $(t) {
|
|
44
29
|
return t <= 1 ? f[1] : t >= 3 ? f[3] : f[t] ?? f[1];
|
|
45
30
|
}
|
|
46
|
-
function
|
|
47
|
-
const r =
|
|
31
|
+
function d(t, e = {}, n = 1) {
|
|
32
|
+
const r = $(n), o = e.prefix ?? "", a = e.suffix ?? "", s = typeof t == "number" ? t : parseFloat(String(t ?? "").replace(/,/g, ""));
|
|
48
33
|
if (t != null && !Number.isNaN(s)) {
|
|
49
|
-
const
|
|
50
|
-
if (
|
|
51
|
-
const
|
|
52
|
-
if (
|
|
34
|
+
const u = `${o}${s.toLocaleString("en-US", { minimumFractionDigits: Number.isInteger(s) ? 0 : 2, maximumFractionDigits: 2 })}${a}`;
|
|
35
|
+
if (u.length <= r) return { formatted: u, tier: "wide", length: u.length };
|
|
36
|
+
const c = `${o}${Math.round(s).toLocaleString("en-US")}${a}`;
|
|
37
|
+
if (c.length <= r) return { formatted: c, tier: "medium", length: c.length };
|
|
53
38
|
}
|
|
54
|
-
const i =
|
|
39
|
+
const i = m(t, { ...e, abbreviated: !0 });
|
|
55
40
|
return i.display.length <= r ? { formatted: i.display, tier: "narrow", length: i.display.length } : { formatted: i.display, tier: "very-narrow", length: i.display.length };
|
|
56
41
|
}
|
|
57
|
-
function
|
|
42
|
+
function p(t, { notation: e = "standard", fractionDigits: n, currency: r = "USD" } = {}) {
|
|
58
43
|
const o = { style: "currency", currency: r };
|
|
59
44
|
if (e === "compact")
|
|
60
45
|
o.notation = "compact", o.compactDisplay = "short", n !== void 0 && (o.minimumFractionDigits = n, o.maximumFractionDigits = n);
|
|
@@ -72,115 +57,113 @@ function g(t) {
|
|
|
72
57
|
parseInt(e.slice(4, 6), 16)
|
|
73
58
|
];
|
|
74
59
|
}
|
|
75
|
-
function
|
|
60
|
+
function M(t, e) {
|
|
76
61
|
const n = t.replace("#", "");
|
|
77
62
|
if (!/^[0-9a-fA-F]{6}$/.test(n))
|
|
78
63
|
return `rgba(0,0,0,${e})`;
|
|
79
64
|
const [r, o, a] = g(t);
|
|
80
65
|
return `rgba(${r},${o},${a},${e})`;
|
|
81
66
|
}
|
|
82
|
-
function
|
|
83
|
-
const r = Math.max(0, Math.min(1, n)), [o, a, s] = g(t), [i,
|
|
84
|
-
return `rgb(${Math.round(o + (i - o) * r)}, ${Math.round(a + (
|
|
85
|
-
s + (
|
|
67
|
+
function S(t, e, n) {
|
|
68
|
+
const r = Math.max(0, Math.min(1, n)), [o, a, s] = g(t), [i, u, c] = g(e);
|
|
69
|
+
return `rgb(${Math.round(o + (i - o) * r)}, ${Math.round(a + (u - a) * r)}, ${Math.round(
|
|
70
|
+
s + (c - s) * r
|
|
86
71
|
)})`;
|
|
87
72
|
}
|
|
88
|
-
function
|
|
73
|
+
function y(t, e = 200, n = "cubic-bezier(0, 0, 0.2, 1)") {
|
|
89
74
|
return t.map((r) => `${r} ${e}ms ${n}`).join(", ");
|
|
90
75
|
}
|
|
91
|
-
function
|
|
76
|
+
function F(t, e, n) {
|
|
92
77
|
return t + (e - t) * n;
|
|
93
78
|
}
|
|
94
|
-
function
|
|
79
|
+
function T(t) {
|
|
95
80
|
const e = t.match(/^([-\d.]+)(.*)$/);
|
|
96
81
|
return e ? { value: parseFloat(e[1]), unit: e[2] || "" } : { value: 0, unit: "" };
|
|
97
82
|
}
|
|
98
|
-
const
|
|
99
|
-
function
|
|
100
|
-
const { rounding: r = "round", inclusive: o = !1, min: a, absolute: s = !0 } = n, i = e.getTime() - t.getTime(),
|
|
101
|
-
let l = r === "ceil" ? Math.ceil(
|
|
83
|
+
const D = 1e3 * 60 * 60 * 24;
|
|
84
|
+
function b(t, e, n = {}) {
|
|
85
|
+
const { rounding: r = "round", inclusive: o = !1, min: a, absolute: s = !0 } = n, i = e.getTime() - t.getTime(), c = (s ? Math.abs(i) : i) / D;
|
|
86
|
+
let l = r === "ceil" ? Math.ceil(c) : r === "floor" ? Math.floor(c) : r === "round" ? Math.round(c) : c;
|
|
102
87
|
return o && (l += 1), a !== void 0 && (l = Math.max(l, a)), l;
|
|
103
88
|
}
|
|
104
|
-
function
|
|
89
|
+
function P(t) {
|
|
90
|
+
return new Date(t.getUTCFullYear(), t.getUTCMonth(), t.getUTCDate());
|
|
91
|
+
}
|
|
92
|
+
function R(t) {
|
|
105
93
|
if (t == null || t === 0)
|
|
106
94
|
return { text: "0%", direction: "flat" };
|
|
107
95
|
const e = t > 0 ? "up" : t < 0 ? "down" : "flat", n = Math.abs(t);
|
|
108
96
|
return { text: n >= 3 ? `${Math.round(n)}%` : `${n.toFixed(1)}%`, direction: e };
|
|
109
97
|
}
|
|
110
|
-
function
|
|
98
|
+
function E(t, e) {
|
|
111
99
|
if (!t || !e) return "";
|
|
112
100
|
const n = t.toLocaleDateString("en-US", { month: "short" }), r = e.toLocaleDateString("en-US", { month: "short" }), o = t.getDate(), a = e.getDate(), s = t.getFullYear(), i = e.getFullYear();
|
|
113
101
|
return t.getTime() === e.getTime() || n === r && o === a && s === i ? `${n} ${o}, ${s}` : n === r && s === i ? `${n} ${o}–${a}` : s === i ? `${n} ${o} – ${r} ${a}` : `${n} ${o}, ${s} – ${r} ${a}, ${i}`;
|
|
114
102
|
}
|
|
115
|
-
function
|
|
103
|
+
function I(t, e) {
|
|
116
104
|
const n = t.toLocaleDateString("en-US", { month: "short" }), r = e.toLocaleDateString("en-US", { month: "short" }), o = t.getDate(), a = e.getDate();
|
|
117
105
|
return n === r ? `${n} ${o}–${a}` : `${n} ${o} – ${r} ${a}`;
|
|
118
106
|
}
|
|
119
|
-
function
|
|
107
|
+
function U(t, e = /* @__PURE__ */ new Date()) {
|
|
120
108
|
return !t?.startDate || !t?.endDate ? !1 : e >= t.startDate && e <= t.endDate;
|
|
121
109
|
}
|
|
122
|
-
function
|
|
110
|
+
function L(t, e) {
|
|
123
111
|
return !t || !e ? !1 : t.getFullYear() === e.getFullYear() && t.getMonth() === e.getMonth() && t.getDate() === e.getDate();
|
|
124
112
|
}
|
|
125
|
-
function
|
|
113
|
+
function _(t, e, n) {
|
|
126
114
|
if (!t || !e || !n) return !1;
|
|
127
115
|
const r = t.getTime(), o = e.getTime(), a = n.getTime();
|
|
128
116
|
return r >= Math.min(o, a) && r <= Math.max(o, a);
|
|
129
117
|
}
|
|
130
|
-
function
|
|
118
|
+
function x() {
|
|
131
119
|
return `custom-${Date.now()}-${Math.random().toString(36).substring(2, 11)}`;
|
|
132
120
|
}
|
|
133
121
|
export {
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
gt as smartDateFormat,
|
|
182
|
-
mt as stripLeadingZeros,
|
|
183
|
-
dt as toUppercasePresetId,
|
|
184
|
-
M as v1_1_edge_hover_resize,
|
|
185
|
-
p as v1_1_status_mode
|
|
122
|
+
Y as DEFAULT_MARKET_PRESETS,
|
|
123
|
+
w as DEFAULT_PINNED,
|
|
124
|
+
O as PERIOD_OPTIONS,
|
|
125
|
+
v as PRESET_ID_MAP,
|
|
126
|
+
C as PRESET_ID_REVERSE_MAP,
|
|
127
|
+
V as ROLLING_OPTIONS,
|
|
128
|
+
z as TODAY_PRESET,
|
|
129
|
+
b as daysBetween,
|
|
130
|
+
H as detectPreset,
|
|
131
|
+
j as findPreset,
|
|
132
|
+
p as formatCurrency,
|
|
133
|
+
E as formatDateRange,
|
|
134
|
+
k as formatDateRangeSmart,
|
|
135
|
+
B as formatDateRangeWithPreset,
|
|
136
|
+
G as formatDuration,
|
|
137
|
+
I as formatMarketDates,
|
|
138
|
+
K as formatPreset,
|
|
139
|
+
q as formatShortYear,
|
|
140
|
+
W as formatSingleDate,
|
|
141
|
+
R as formatTrend,
|
|
142
|
+
m as formatValue,
|
|
143
|
+
x as generateMarketId,
|
|
144
|
+
Z as getAllPresets,
|
|
145
|
+
J as getDateRangeDisplayInfo,
|
|
146
|
+
Q as getDateRangeForPreset,
|
|
147
|
+
X as getDurationDays,
|
|
148
|
+
tt as getPresetDateRange,
|
|
149
|
+
et as getPresetLabel,
|
|
150
|
+
y as getTransitionStyle,
|
|
151
|
+
h as getValueFontSize,
|
|
152
|
+
M as hexToRgba,
|
|
153
|
+
F as interpolate,
|
|
154
|
+
_ as isInRange,
|
|
155
|
+
U as isMarketActive,
|
|
156
|
+
L as isSameDay,
|
|
157
|
+
nt as isValidDateRangeFormat,
|
|
158
|
+
S as lerpHex,
|
|
159
|
+
rt as normalizePresetId,
|
|
160
|
+
at as parseDateRange,
|
|
161
|
+
T as parseNumericValue,
|
|
162
|
+
d as pickMetricTier,
|
|
163
|
+
ot as resolveEvent,
|
|
164
|
+
st as resolvePreset,
|
|
165
|
+
it as smartDateFormat,
|
|
166
|
+
ct as stripLeadingZeros,
|
|
167
|
+
P as toLocalCalendarDate,
|
|
168
|
+
ut as toUppercasePresetId
|
|
186
169
|
};
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Re-project a date onto **local midnight of its UTC calendar date**.
|
|
3
|
+
*
|
|
4
|
+
* Order dates arrive from the BFF as date-only ISO strings (e.g. `"2026-03-09"`).
|
|
5
|
+
* `new Date("2026-03-09")` parses this as **UTC midnight**, which in timezones
|
|
6
|
+
* west of UTC falls on the *previous* local calendar day (e.g. March 8 at
|
|
7
|
+
* 19:00 EST). To bucket an order by its intended calendar day regardless of the
|
|
8
|
+
* viewer's timezone, both the dashboard's table filter and its chart grouping
|
|
9
|
+
* extract the date's **UTC** year/month/day and rebuild a `Date` at **local**
|
|
10
|
+
* midnight of those components. Doing this on both surfaces guarantees the
|
|
11
|
+
* table filter (which uses local-midnight boundaries) and the chart's UTC
|
|
12
|
+
* date-grouping agree on which day an order belongs to.
|
|
13
|
+
*
|
|
14
|
+
* Regress this and table totals silently disagree with chart bars: the only
|
|
15
|
+
* orders affected are those whose date sits on a UTC-vs-local day boundary, so
|
|
16
|
+
* nothing throws — the two surfaces just stop matching.
|
|
17
|
+
*
|
|
18
|
+
* Purity note: the input `Date` only needs to carry the right instant; this
|
|
19
|
+
* helper reads its UTC Y/M/D and nothing else. String parsing and null handling
|
|
20
|
+
* stay with the caller — one consumer coerces with `new Date(str)`, another with
|
|
21
|
+
* date-fns `parseISO` — and both delegate the projection here.
|
|
22
|
+
*
|
|
23
|
+
* @example
|
|
24
|
+
* ```ts
|
|
25
|
+
* import { toLocalCalendarDate } from '@mt-gloss/utils';
|
|
26
|
+
*
|
|
27
|
+
* // A date-only ISO string parses as UTC midnight; the helper re-keys it to
|
|
28
|
+
* // local midnight of the SAME calendar date — timezone-independent.
|
|
29
|
+
* const d = toLocalCalendarDate(new Date('2026-03-09'));
|
|
30
|
+
* d.getFullYear(); // 2026
|
|
31
|
+
* d.getMonth(); // 2 (March, 0-indexed)
|
|
32
|
+
* d.getDate(); // 9 — never the 8th, even west of UTC
|
|
33
|
+
* ```
|
|
34
|
+
*/
|
|
35
|
+
export declare function toLocalCalendarDate(date: Date): Date;
|
|
36
|
+
//# sourceMappingURL=toLocalCalendarDate.d.ts.map
|
package/package.json
CHANGED
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Phase 10: v1.1 feature flags for Status Mode.
|
|
3
|
-
*
|
|
4
|
-
* Flag is OFF by default in production bundles.
|
|
5
|
-
* Enable via env var (server/build-time) or globalThis override (runtime/test).
|
|
6
|
-
*/
|
|
7
|
-
export declare const V1_1_STATUS_MODE_ENV = "NEXT_PUBLIC_V1_1_STATUS_MODE";
|
|
8
|
-
/**
|
|
9
|
-
* Returns true when Status Mode rendering is enabled.
|
|
10
|
-
*
|
|
11
|
-
* Priority order:
|
|
12
|
-
* 1. globalThis.__GLOSS_FLAGS__.v1_1_status_mode === true (runtime override / tests)
|
|
13
|
-
* 2. process.env.NEXT_PUBLIC_V1_1_STATUS_MODE === 'true' (build-time env var)
|
|
14
|
-
* 3. false (default — flag OFF)
|
|
15
|
-
*/
|
|
16
|
-
export declare function isStatusModeEnabled(): boolean;
|
|
17
|
-
export declare const v1_1_status_mode: {
|
|
18
|
-
env: string;
|
|
19
|
-
check: typeof isStatusModeEnabled;
|
|
20
|
-
};
|
|
21
|
-
/**
|
|
22
|
-
* Phase 10.5 WR-01 — edge-hover resize decoupling.
|
|
23
|
-
*
|
|
24
|
-
* Independent feature flag for edge-hover resize. Previously the consumer
|
|
25
|
-
* gated `enableEdgeHover` on `isStatusModeEnabled()`, which coupled two
|
|
26
|
-
* independent features behind a single flag. This helper lets consumers
|
|
27
|
-
* toggle edge-hover-resize on its own.
|
|
28
|
-
*
|
|
29
|
-
* Flag is OFF by default in production bundles.
|
|
30
|
-
*/
|
|
31
|
-
export declare const V1_1_EDGE_HOVER_RESIZE_ENV = "NEXT_PUBLIC_V1_1_EDGE_HOVER_RESIZE";
|
|
32
|
-
/**
|
|
33
|
-
* Returns true when edge-hover resize is enabled.
|
|
34
|
-
*
|
|
35
|
-
* Priority order (mirrors isStatusModeEnabled):
|
|
36
|
-
* 1. globalThis.__GLOSS_FLAGS__.v1_1_edge_hover_resize === true (runtime override / tests)
|
|
37
|
-
* 2. process.env.NEXT_PUBLIC_V1_1_EDGE_HOVER_RESIZE === 'true' (build-time env var)
|
|
38
|
-
* 3. false (default — flag OFF)
|
|
39
|
-
*/
|
|
40
|
-
export declare function isEdgeHoverResizeEnabled(): boolean;
|
|
41
|
-
export declare const v1_1_edge_hover_resize: {
|
|
42
|
-
env: string;
|
|
43
|
-
check: typeof isEdgeHoverResizeEnabled;
|
|
44
|
-
};
|
|
45
|
-
//# sourceMappingURL=v1_1_flags.d.ts.map
|