qstd 0.1.0
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/CHANGELOG.md +23 -0
- package/README.md +127 -0
- package/dist/client/index.cjs +587 -0
- package/dist/client/index.d.cts +75 -0
- package/dist/client/index.d.ts +75 -0
- package/dist/client/index.js +577 -0
- package/dist/preset/index.cjs +475 -0
- package/dist/preset/index.d.cts +39 -0
- package/dist/preset/index.d.ts +39 -0
- package/dist/preset/index.js +473 -0
- package/dist/random-DMErOOdk.d.cts +447 -0
- package/dist/random-DMErOOdk.d.ts +447 -0
- package/dist/react/index.cjs +3155 -0
- package/dist/react/index.css +1566 -0
- package/dist/react/index.d.cts +21092 -0
- package/dist/react/index.d.ts +21092 -0
- package/dist/react/index.js +3128 -0
- package/dist/server/index.cjs +541 -0
- package/dist/server/index.d.cts +17 -0
- package/dist/server/index.d.ts +17 -0
- package/dist/server/index.js +527 -0
- package/package.json +111 -0
- package/panda.config.ts +68 -0
|
@@ -0,0 +1,527 @@
|
|
|
1
|
+
import { format, formatDistanceToNow, formatISO, isSameYear, isSameMonth, isSameDay, addSeconds, addMinutes, addHours, addDays, addWeeks, addBusinessDays, addMonths, addYears } from 'date-fns';
|
|
2
|
+
import fs from 'fs';
|
|
3
|
+
|
|
4
|
+
var __defProp = Object.defineProperty;
|
|
5
|
+
var __export = (target, all) => {
|
|
6
|
+
for (var name in all)
|
|
7
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
// src/shared/list.ts
|
|
11
|
+
var list_exports = {};
|
|
12
|
+
__export(list_exports, {
|
|
13
|
+
chunk: () => chunk,
|
|
14
|
+
create: () => create,
|
|
15
|
+
partition: () => partition,
|
|
16
|
+
zipWith: () => zipWith
|
|
17
|
+
});
|
|
18
|
+
function zipWith(fn, ...arrays) {
|
|
19
|
+
if (arrays.length === 0) return [];
|
|
20
|
+
const minLength = Math.min(...arrays.map((arr) => arr.length));
|
|
21
|
+
const result = [];
|
|
22
|
+
for (let i = 0; i < minLength; i++) {
|
|
23
|
+
const args = arrays.map((arr) => arr[i]);
|
|
24
|
+
result.push(fn(...args));
|
|
25
|
+
}
|
|
26
|
+
return result;
|
|
27
|
+
}
|
|
28
|
+
var create = (size, fn) => fn ? Array(size).fill(null).map(fn) : Array(size).fill(null);
|
|
29
|
+
var partition = (xs, predicate) => xs.reduce(
|
|
30
|
+
([truthList, falseList], x) => {
|
|
31
|
+
const passes = predicate(x);
|
|
32
|
+
if (passes) truthList.push(x);
|
|
33
|
+
else falseList.push(x);
|
|
34
|
+
return [truthList, falseList];
|
|
35
|
+
},
|
|
36
|
+
[[], []]
|
|
37
|
+
);
|
|
38
|
+
var chunk = (list, chunkSize) => {
|
|
39
|
+
const totalChunks = Math.ceil(list.length / chunkSize);
|
|
40
|
+
return Array.from({ length: totalChunks }, (_, i) => {
|
|
41
|
+
const start = i * chunkSize;
|
|
42
|
+
const end = i * chunkSize + chunkSize;
|
|
43
|
+
return list.slice(start, end);
|
|
44
|
+
});
|
|
45
|
+
};
|
|
46
|
+
|
|
47
|
+
// src/shared/dict.ts
|
|
48
|
+
var dict_exports = {};
|
|
49
|
+
__export(dict_exports, {
|
|
50
|
+
byteSizeOfObj: () => byteSizeOfObj,
|
|
51
|
+
exists: () => exists,
|
|
52
|
+
filter: () => filter,
|
|
53
|
+
isEmpty: () => isEmpty,
|
|
54
|
+
omit: () => omit,
|
|
55
|
+
partition: () => partition2,
|
|
56
|
+
pick: () => pick,
|
|
57
|
+
transform: () => transform
|
|
58
|
+
});
|
|
59
|
+
function byteSizeOfObj(o) {
|
|
60
|
+
const objectList = [];
|
|
61
|
+
const stack = [o];
|
|
62
|
+
const bytes = [0];
|
|
63
|
+
while (stack.length) {
|
|
64
|
+
const value = stack.pop();
|
|
65
|
+
if (value == null) bytes[0] += 4;
|
|
66
|
+
else if (typeof value === "boolean") bytes[0] += 4;
|
|
67
|
+
else if (typeof value === "string") bytes[0] += value.length * 2;
|
|
68
|
+
else if (typeof value === "number") bytes[0] += 8;
|
|
69
|
+
else if (typeof value === "object" && objectList.indexOf(value) === -1) {
|
|
70
|
+
objectList.push(value);
|
|
71
|
+
if (typeof value.byteLength === "number") bytes[0] += value.byteLength;
|
|
72
|
+
else if (value[Symbol.iterator]) {
|
|
73
|
+
for (const v of value) stack.push(v);
|
|
74
|
+
} else {
|
|
75
|
+
Object.keys(value).forEach((k) => {
|
|
76
|
+
bytes[0] += k.length * 2;
|
|
77
|
+
stack.push(value[k]);
|
|
78
|
+
});
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
return bytes[0];
|
|
83
|
+
}
|
|
84
|
+
var filter = (r, predicate) => Object.entries(r).reduce(
|
|
85
|
+
(store, [key, value]) => predicate(value) ? { ...store, [key]: value } : store,
|
|
86
|
+
{}
|
|
87
|
+
);
|
|
88
|
+
var transform = (r, transformFn) => Object.entries(r).reduce(
|
|
89
|
+
(store, [key, value]) => ({
|
|
90
|
+
...store,
|
|
91
|
+
...transformFn(key, value)
|
|
92
|
+
}),
|
|
93
|
+
{}
|
|
94
|
+
);
|
|
95
|
+
var partition2 = (r, predicate) => {
|
|
96
|
+
const passed = {};
|
|
97
|
+
const failed = {};
|
|
98
|
+
for (const key in r) {
|
|
99
|
+
if (predicate(key)) passed[key] = r[key];
|
|
100
|
+
else failed[key] = r[key];
|
|
101
|
+
}
|
|
102
|
+
return [passed, failed];
|
|
103
|
+
};
|
|
104
|
+
var exists = (obj) => {
|
|
105
|
+
return obj && typeof obj === "object" && Object.keys(obj).length > 0;
|
|
106
|
+
};
|
|
107
|
+
var isEmpty = (obj) => {
|
|
108
|
+
return !obj || Object.keys(obj).length === 0 && obj.constructor === Object;
|
|
109
|
+
};
|
|
110
|
+
var pick = (r, paths) => Object.entries(r).reduce(
|
|
111
|
+
(store, [key, value]) => paths.includes(key) ? { ...store, [key]: value } : store,
|
|
112
|
+
{}
|
|
113
|
+
);
|
|
114
|
+
var omit = (r, paths) => {
|
|
115
|
+
if (!r) {
|
|
116
|
+
throw new Error("[omit] item was not an object");
|
|
117
|
+
}
|
|
118
|
+
return Object.entries(r).reduce((store, [key, value]) => {
|
|
119
|
+
if (paths.includes(key)) {
|
|
120
|
+
return store;
|
|
121
|
+
} else {
|
|
122
|
+
store[key] = value;
|
|
123
|
+
return store;
|
|
124
|
+
}
|
|
125
|
+
}, {});
|
|
126
|
+
};
|
|
127
|
+
|
|
128
|
+
// src/shared/str.ts
|
|
129
|
+
var str_exports = {};
|
|
130
|
+
__export(str_exports, {
|
|
131
|
+
concat: () => concat,
|
|
132
|
+
countChar: () => countChar,
|
|
133
|
+
countWords: () => countWords,
|
|
134
|
+
createSentences: () => createSentences,
|
|
135
|
+
toCase: () => toCase
|
|
136
|
+
});
|
|
137
|
+
var createSentences = (text) => {
|
|
138
|
+
if (!text) return [];
|
|
139
|
+
return text?.replace(/([.?!])\s*(?=[A-Z])/g, "$1|").split("|");
|
|
140
|
+
};
|
|
141
|
+
var countWords = (text) => {
|
|
142
|
+
text = text.trim();
|
|
143
|
+
if (text.length === 0) {
|
|
144
|
+
return 0;
|
|
145
|
+
}
|
|
146
|
+
const wordPattern = /\w+/g;
|
|
147
|
+
const matches = text.match(wordPattern);
|
|
148
|
+
return matches ? matches.length : 0;
|
|
149
|
+
};
|
|
150
|
+
var concat = (xs, delimiter) => {
|
|
151
|
+
return xs.filter((x) => !!x).join(delimiter);
|
|
152
|
+
};
|
|
153
|
+
var countChar = (str, ch) => {
|
|
154
|
+
return str.split("").reduce((x, y) => y === ch ? x + 1 : x, 0);
|
|
155
|
+
};
|
|
156
|
+
var toCase = (text, opts) => {
|
|
157
|
+
switch (opts.to) {
|
|
158
|
+
case "title":
|
|
159
|
+
return text.charAt(0).toUpperCase() + text.slice(1);
|
|
160
|
+
case "snake":
|
|
161
|
+
return text.replace(
|
|
162
|
+
/[A-Z]/g,
|
|
163
|
+
(l, idx) => idx === 0 ? l.toLowerCase() : "_" + l.toLowerCase()
|
|
164
|
+
);
|
|
165
|
+
case "kebab": {
|
|
166
|
+
const lowered = text.toLowerCase().trim();
|
|
167
|
+
const cleaned = opts.clean ? lowered.replaceAll(/[:,]/g, "") : lowered;
|
|
168
|
+
return cleaned.replaceAll(/\s+/g, "-");
|
|
169
|
+
}
|
|
170
|
+
default:
|
|
171
|
+
return text;
|
|
172
|
+
}
|
|
173
|
+
};
|
|
174
|
+
|
|
175
|
+
// src/shared/int.ts
|
|
176
|
+
var int_exports = {};
|
|
177
|
+
__export(int_exports, {
|
|
178
|
+
clamp: () => clamp,
|
|
179
|
+
commaSeparateThousandths: () => commaSeparateThousandths,
|
|
180
|
+
formatBytes: () => formatBytes
|
|
181
|
+
});
|
|
182
|
+
var clamp = (num2, range) => Math.min(Math.max(num2, range.min), range.max);
|
|
183
|
+
var isNumeric = (x) => {
|
|
184
|
+
return /^[0-9]+$/.test(x);
|
|
185
|
+
};
|
|
186
|
+
var commaSeparateThousandths = (n) => {
|
|
187
|
+
if (typeof n === "string" && !isNumeric(n)) {
|
|
188
|
+
throw new Error(`[comma separate thousandths] Value ${n} must be a number`);
|
|
189
|
+
}
|
|
190
|
+
return Number(n).toLocaleString("en-US");
|
|
191
|
+
};
|
|
192
|
+
var formatBytes = (bytes, decimals = 1, binaryUnits = false) => {
|
|
193
|
+
if (!bytes) return {};
|
|
194
|
+
if (bytes === 0) return { value: 0, unit: "Bytes" };
|
|
195
|
+
const unitMultiple = binaryUnits ? 1024 : 1e3;
|
|
196
|
+
const unitNames = unitMultiple === 1024 ? ["Bytes", "KiB", "MiB", "GiB", "TiB", "PiB", "EiB", "ZiB", "YiB"] : ["Bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"];
|
|
197
|
+
const unitChanges = Math.floor(Math.log(bytes) / Math.log(unitMultiple));
|
|
198
|
+
const value = parseFloat(
|
|
199
|
+
(bytes / Math.pow(unitMultiple, unitChanges)).toFixed(decimals || 0)
|
|
200
|
+
);
|
|
201
|
+
const unit = unitNames[unitChanges];
|
|
202
|
+
return { value, unit, display: `${value}${unit}` };
|
|
203
|
+
};
|
|
204
|
+
|
|
205
|
+
// src/shared/money.ts
|
|
206
|
+
var money_exports = {};
|
|
207
|
+
__export(money_exports, {
|
|
208
|
+
convertToCents: () => convertToCents,
|
|
209
|
+
convertToUsd: () => convertToUsd
|
|
210
|
+
});
|
|
211
|
+
var convertToUsd = (cents, opts = {}) => {
|
|
212
|
+
if (!cents) return;
|
|
213
|
+
const dollars = (Number(cents) / 100).toLocaleString("en-US", {
|
|
214
|
+
style: "currency",
|
|
215
|
+
currency: "USD"
|
|
216
|
+
});
|
|
217
|
+
const showSymbol = opts.symbol ?? true;
|
|
218
|
+
return showSymbol ? dollars : dollars.slice(1);
|
|
219
|
+
};
|
|
220
|
+
var convertToCents = (dollars) => {
|
|
221
|
+
const str = dollars.toString().replaceAll(/[\$,]+/g, "");
|
|
222
|
+
return Number(str) * 100;
|
|
223
|
+
};
|
|
224
|
+
|
|
225
|
+
// src/shared/time.ts
|
|
226
|
+
var time_exports = {};
|
|
227
|
+
__export(time_exports, {
|
|
228
|
+
adjustDate: () => adjustDate,
|
|
229
|
+
formatDate: () => formatDate,
|
|
230
|
+
formatDateRange: () => formatDateRange,
|
|
231
|
+
formatDuration: () => formatDuration,
|
|
232
|
+
formatThreadDateRange: () => formatThreadDateRange,
|
|
233
|
+
now: () => now,
|
|
234
|
+
sleep: () => sleep,
|
|
235
|
+
toMs: () => toMs
|
|
236
|
+
});
|
|
237
|
+
var formatDuration = (ms, options = {}) => {
|
|
238
|
+
if (ms === null || ms === void 0) return "--:--";
|
|
239
|
+
const { format: fmt = "clock", showZero = false } = options;
|
|
240
|
+
const totalSeconds = Math.floor(Math.abs(ms) / 1e3);
|
|
241
|
+
const hours = Math.floor(totalSeconds / 3600);
|
|
242
|
+
const minutes = Math.floor(totalSeconds % 3600 / 60);
|
|
243
|
+
const seconds = totalSeconds % 60;
|
|
244
|
+
if (fmt === "clock") {
|
|
245
|
+
if (hours > 0) {
|
|
246
|
+
return `${hours}:${minutes.toString().padStart(2, "0")}:${seconds.toString().padStart(2, "0")}`;
|
|
247
|
+
}
|
|
248
|
+
return `${minutes}:${seconds.toString().padStart(2, "0")}`;
|
|
249
|
+
}
|
|
250
|
+
if (fmt === "full") {
|
|
251
|
+
const parts2 = [];
|
|
252
|
+
if (showZero) {
|
|
253
|
+
const hasHours = hours > 0;
|
|
254
|
+
const hasMinutes = minutes > 0;
|
|
255
|
+
const hasSeconds = seconds > 0;
|
|
256
|
+
if (hasHours || hasMinutes || hasSeconds) {
|
|
257
|
+
if (hasHours) parts2.push(`${hours} ${hours === 1 ? "hour" : "hours"}`);
|
|
258
|
+
if (hasHours || hasMinutes)
|
|
259
|
+
parts2.push(`${minutes} ${minutes === 1 ? "minute" : "minutes"}`);
|
|
260
|
+
parts2.push(`${seconds} ${seconds === 1 ? "second" : "seconds"}`);
|
|
261
|
+
} else {
|
|
262
|
+
parts2.push("0 seconds");
|
|
263
|
+
}
|
|
264
|
+
} else {
|
|
265
|
+
if (hours > 0) parts2.push(`${hours} ${hours === 1 ? "hour" : "hours"}`);
|
|
266
|
+
if (minutes > 0)
|
|
267
|
+
parts2.push(`${minutes} ${minutes === 1 ? "minute" : "minutes"}`);
|
|
268
|
+
if (seconds > 0)
|
|
269
|
+
parts2.push(`${seconds} ${seconds === 1 ? "second" : "seconds"}`);
|
|
270
|
+
}
|
|
271
|
+
return parts2.join(" ") || "0 seconds";
|
|
272
|
+
}
|
|
273
|
+
if (fmt === "fractional") {
|
|
274
|
+
const totalSecondsWithFraction = Math.abs(ms) / 1e3;
|
|
275
|
+
const totalMinutes = Math.floor(totalSecondsWithFraction / 60);
|
|
276
|
+
if (totalMinutes === 0) {
|
|
277
|
+
const fractionalSeconds = totalSecondsWithFraction.toFixed(1);
|
|
278
|
+
return `${fractionalSeconds}s`;
|
|
279
|
+
} else {
|
|
280
|
+
const remainingSeconds = totalSecondsWithFraction % 60;
|
|
281
|
+
const fractionalSeconds = remainingSeconds.toFixed(1);
|
|
282
|
+
return `${totalMinutes}m ${fractionalSeconds}s`;
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
const parts = [];
|
|
286
|
+
if (showZero) {
|
|
287
|
+
const hasHours = hours > 0;
|
|
288
|
+
const hasMinutes = minutes > 0;
|
|
289
|
+
const hasSeconds = seconds > 0;
|
|
290
|
+
if (hasHours || hasMinutes || hasSeconds) {
|
|
291
|
+
if (hasHours) parts.push(`${hours}h`);
|
|
292
|
+
if (hasHours || hasMinutes) parts.push(`${minutes}m`);
|
|
293
|
+
parts.push(`${seconds}s`);
|
|
294
|
+
} else {
|
|
295
|
+
parts.push("0s");
|
|
296
|
+
}
|
|
297
|
+
} else {
|
|
298
|
+
if (hours > 0) parts.push(`${hours}h`);
|
|
299
|
+
if (minutes > 0) parts.push(`${minutes}m`);
|
|
300
|
+
if (seconds > 0) parts.push(`${seconds}s`);
|
|
301
|
+
}
|
|
302
|
+
return parts.join(" ") || "0s";
|
|
303
|
+
};
|
|
304
|
+
var formatDate = (input, options = {}) => {
|
|
305
|
+
const { style = "medium", pattern, includeTime = false } = options;
|
|
306
|
+
let date2;
|
|
307
|
+
if (typeof input === "string") {
|
|
308
|
+
date2 = new Date(input);
|
|
309
|
+
} else if (typeof input === "number") {
|
|
310
|
+
date2 = new Date(input);
|
|
311
|
+
} else {
|
|
312
|
+
date2 = input;
|
|
313
|
+
}
|
|
314
|
+
if (isNaN(date2.getTime())) {
|
|
315
|
+
return "Invalid Date";
|
|
316
|
+
}
|
|
317
|
+
if (pattern) {
|
|
318
|
+
return format(date2, pattern);
|
|
319
|
+
}
|
|
320
|
+
switch (style) {
|
|
321
|
+
case "iso":
|
|
322
|
+
return formatISO(date2);
|
|
323
|
+
case "short":
|
|
324
|
+
return includeTime ? format(date2, "M/d/yy h:mm a") : format(date2, "M/d/yy");
|
|
325
|
+
case "medium":
|
|
326
|
+
return includeTime ? format(date2, "MMM d, yyyy h:mm a") : format(date2, "MMM d, yyyy");
|
|
327
|
+
case "long":
|
|
328
|
+
return includeTime ? format(date2, "MMMM d, yyyy 'at' h:mm a") : format(date2, "MMMM d, yyyy");
|
|
329
|
+
case "relative":
|
|
330
|
+
return formatDistanceToNow(date2, { addSuffix: true });
|
|
331
|
+
case "year":
|
|
332
|
+
return format(date2, "yyyy");
|
|
333
|
+
default:
|
|
334
|
+
return includeTime ? format(date2, "MMM d, yyyy h:mm a") : format(date2, "MMM d, yyyy");
|
|
335
|
+
}
|
|
336
|
+
};
|
|
337
|
+
var toDate = (input) => typeof input === "string" || typeof input === "number" ? new Date(input) : input;
|
|
338
|
+
var formatDateRange = (startInput, endInput, options = {}) => {
|
|
339
|
+
const now2 = options.now ?? /* @__PURE__ */ new Date();
|
|
340
|
+
const showTimeWhenSameDay = options.showTimeWhenSameDay ?? true;
|
|
341
|
+
const markToday = options.markToday ?? true;
|
|
342
|
+
const todayLabel = options.todayLabel ?? "today";
|
|
343
|
+
const separator = options.separator ?? " - ";
|
|
344
|
+
const monthPattern = options.monthFormat === "long" ? "MMMM" : "MMM";
|
|
345
|
+
const lowercaseAmPm = options.lowercaseAmPm ?? true;
|
|
346
|
+
const { locale } = options;
|
|
347
|
+
let start = toDate(startInput);
|
|
348
|
+
let end = toDate(endInput);
|
|
349
|
+
if (start.getTime() > end.getTime()) {
|
|
350
|
+
const tmp = start;
|
|
351
|
+
start = end;
|
|
352
|
+
end = tmp;
|
|
353
|
+
}
|
|
354
|
+
if (isNaN(start.getTime()) || isNaN(end.getTime())) return "";
|
|
355
|
+
const sameYear = isSameYear(start, end);
|
|
356
|
+
const sameMonth = sameYear && isSameMonth(start, end);
|
|
357
|
+
const sameDay = sameMonth && isSameDay(start, end);
|
|
358
|
+
const isStartToday = isSameDay(start, now2);
|
|
359
|
+
const isEndToday = isSameDay(end, now2);
|
|
360
|
+
const appendToday = (base, isTodayFlag) => markToday && isTodayFlag ? `${base} (${todayLabel})` : base;
|
|
361
|
+
const fmt = (d, pattern) => locale ? format(d, pattern, { locale }) : format(d, pattern);
|
|
362
|
+
if (sameDay) {
|
|
363
|
+
const dayPart = appendToday(
|
|
364
|
+
fmt(start, `${monthPattern} d`),
|
|
365
|
+
isStartToday || isEndToday
|
|
366
|
+
);
|
|
367
|
+
if (!showTimeWhenSameDay) return dayPart;
|
|
368
|
+
const timePattern = "h:mma";
|
|
369
|
+
const formatTime = (d) => lowercaseAmPm ? fmt(d, timePattern).toLowerCase() : fmt(d, timePattern);
|
|
370
|
+
const startTime = formatTime(start);
|
|
371
|
+
const endTime = formatTime(end);
|
|
372
|
+
return `${dayPart}, ${startTime}${separator}${endTime}`;
|
|
373
|
+
}
|
|
374
|
+
if (sameMonth) {
|
|
375
|
+
const monthPart = fmt(start, monthPattern);
|
|
376
|
+
const startDay = fmt(start, "d");
|
|
377
|
+
const endDay = fmt(end, "d");
|
|
378
|
+
const startSegment = appendToday(startDay, isStartToday);
|
|
379
|
+
const endSegment = appendToday(endDay, isEndToday);
|
|
380
|
+
const yearPart = fmt(start, "yyyy");
|
|
381
|
+
return `${monthPart} ${startSegment}${separator}${endSegment}, ${yearPart}`;
|
|
382
|
+
}
|
|
383
|
+
if (sameYear) {
|
|
384
|
+
const startPart2 = appendToday(
|
|
385
|
+
fmt(start, `${monthPattern} d`),
|
|
386
|
+
isStartToday
|
|
387
|
+
);
|
|
388
|
+
const endPart2 = appendToday(fmt(end, `${monthPattern} d`), isEndToday);
|
|
389
|
+
const yearPart = fmt(start, "yyyy");
|
|
390
|
+
return `${startPart2}${separator}${endPart2}, ${yearPart}`;
|
|
391
|
+
}
|
|
392
|
+
const startPart = appendToday(
|
|
393
|
+
fmt(start, `${monthPattern} d, yyyy`),
|
|
394
|
+
isStartToday
|
|
395
|
+
);
|
|
396
|
+
const endPart = appendToday(fmt(end, `${monthPattern} d, yyyy`), isEndToday);
|
|
397
|
+
return `${startPart}${separator}${endPart}`;
|
|
398
|
+
};
|
|
399
|
+
var formatThreadDateRange = (startInput, endInput, options = {}) => formatDateRange(startInput, endInput, options);
|
|
400
|
+
var adjustDate = (adjustment, baseDate = /* @__PURE__ */ new Date()) => {
|
|
401
|
+
let result = new Date(baseDate);
|
|
402
|
+
if (adjustment.seconds) result = addSeconds(result, adjustment.seconds);
|
|
403
|
+
if (adjustment.minutes) result = addMinutes(result, adjustment.minutes);
|
|
404
|
+
if (adjustment.hours) result = addHours(result, adjustment.hours);
|
|
405
|
+
if (adjustment.days) result = addDays(result, adjustment.days);
|
|
406
|
+
if (adjustment.weeks) result = addWeeks(result, adjustment.weeks);
|
|
407
|
+
if (adjustment.businessDays)
|
|
408
|
+
result = addBusinessDays(result, adjustment.businessDays);
|
|
409
|
+
if (adjustment.months) result = addMonths(result, adjustment.months);
|
|
410
|
+
if (adjustment.years) result = addYears(result, adjustment.years);
|
|
411
|
+
return result;
|
|
412
|
+
};
|
|
413
|
+
var sleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
|
|
414
|
+
var now = () => Date.now();
|
|
415
|
+
var toMs = (value, unit = "seconds") => {
|
|
416
|
+
const multipliers = {
|
|
417
|
+
seconds: 1e3,
|
|
418
|
+
minutes: 60 * 1e3,
|
|
419
|
+
hours: 60 * 60 * 1e3,
|
|
420
|
+
days: 24 * 60 * 60 * 1e3,
|
|
421
|
+
weeks: 7 * 24 * 60 * 60 * 1e3,
|
|
422
|
+
months: 30 * 24 * 60 * 60 * 1e3,
|
|
423
|
+
// approximate
|
|
424
|
+
years: 365 * 24 * 60 * 60 * 1e3
|
|
425
|
+
// approximate
|
|
426
|
+
};
|
|
427
|
+
return value * multipliers[unit];
|
|
428
|
+
};
|
|
429
|
+
|
|
430
|
+
// src/shared/flow.ts
|
|
431
|
+
var flow_exports = {};
|
|
432
|
+
__export(flow_exports, {
|
|
433
|
+
asyncPool: () => asyncPool,
|
|
434
|
+
debounce: () => debounce,
|
|
435
|
+
sleep: () => sleep2,
|
|
436
|
+
throttle: () => throttle
|
|
437
|
+
});
|
|
438
|
+
var throttle = (fn, ms) => {
|
|
439
|
+
let time = Date.now();
|
|
440
|
+
return (...args) => {
|
|
441
|
+
if (time + ms - Date.now() < 0) {
|
|
442
|
+
fn(...args);
|
|
443
|
+
time = Date.now();
|
|
444
|
+
}
|
|
445
|
+
};
|
|
446
|
+
};
|
|
447
|
+
var debounce = (fn, timeout) => {
|
|
448
|
+
let timer;
|
|
449
|
+
return (...args) => {
|
|
450
|
+
clearTimeout(timer);
|
|
451
|
+
timer = setTimeout(() => {
|
|
452
|
+
fn(...args);
|
|
453
|
+
}, timeout);
|
|
454
|
+
};
|
|
455
|
+
};
|
|
456
|
+
var sleep2 = (ms) => new Promise((res) => setTimeout(res, ms));
|
|
457
|
+
async function* asyncPool(concurrency, iterable, iterator_fn) {
|
|
458
|
+
const executing = /* @__PURE__ */ new Set();
|
|
459
|
+
const consume = async () => {
|
|
460
|
+
const [promise, value] = await Promise.race(executing);
|
|
461
|
+
executing.delete(promise);
|
|
462
|
+
return value;
|
|
463
|
+
};
|
|
464
|
+
for (const item2 of iterable) {
|
|
465
|
+
const promise = (async () => await iterator_fn(item2, iterable))().then(
|
|
466
|
+
(value) => [promise, value]
|
|
467
|
+
);
|
|
468
|
+
executing.add(promise);
|
|
469
|
+
if (executing.size >= concurrency) {
|
|
470
|
+
yield await consume();
|
|
471
|
+
}
|
|
472
|
+
}
|
|
473
|
+
while (executing.size) {
|
|
474
|
+
yield await consume();
|
|
475
|
+
}
|
|
476
|
+
}
|
|
477
|
+
|
|
478
|
+
// src/shared/random.ts
|
|
479
|
+
var random_exports = {};
|
|
480
|
+
__export(random_exports, {
|
|
481
|
+
coinFlip: () => coinFlip,
|
|
482
|
+
date: () => date,
|
|
483
|
+
hexColor: () => hexColor,
|
|
484
|
+
item: () => item,
|
|
485
|
+
num: () => num,
|
|
486
|
+
shuffle: () => shuffle
|
|
487
|
+
});
|
|
488
|
+
var item = (xs) => {
|
|
489
|
+
const rand = Math.random() * xs.length;
|
|
490
|
+
const flooredRand = Math.floor(rand);
|
|
491
|
+
return xs[flooredRand];
|
|
492
|
+
};
|
|
493
|
+
var num = (props = {}) => {
|
|
494
|
+
const { min = 0, max = Number.MAX_SAFE_INTEGER } = props;
|
|
495
|
+
return Math.floor(Math.pow(10, 14) * Math.random() * Math.random()) % (max - min + 1) + min;
|
|
496
|
+
};
|
|
497
|
+
var shuffle = (xs) => {
|
|
498
|
+
return xs.reduceRight((r, _, __, s) => {
|
|
499
|
+
const randomItem = s.splice(0 | Math.random() * s.length, 1)[0];
|
|
500
|
+
return r.push(randomItem), r;
|
|
501
|
+
}, []);
|
|
502
|
+
};
|
|
503
|
+
var coinFlip = () => {
|
|
504
|
+
return Math.random() < 0.5;
|
|
505
|
+
};
|
|
506
|
+
var date = () => {
|
|
507
|
+
return new Date(+/* @__PURE__ */ new Date() - Math.floor(Math.random() * 1e13));
|
|
508
|
+
};
|
|
509
|
+
var hexColor = () => {
|
|
510
|
+
const hex = Math.floor(Math.random() * 16777215).toString(16);
|
|
511
|
+
if (hex.length !== 6) {
|
|
512
|
+
console.warn(`${hex} was not 6 characters. Regenerating.`);
|
|
513
|
+
return hexColor();
|
|
514
|
+
}
|
|
515
|
+
return hex;
|
|
516
|
+
};
|
|
517
|
+
|
|
518
|
+
// src/server/file.ts
|
|
519
|
+
var file_exports = {};
|
|
520
|
+
__export(file_exports, {
|
|
521
|
+
readFile: () => readFile
|
|
522
|
+
});
|
|
523
|
+
var readFile = (filePath, encoding = "utf-8") => {
|
|
524
|
+
return fs.readFileSync(filePath, encoding);
|
|
525
|
+
};
|
|
526
|
+
|
|
527
|
+
export { dict_exports as Dict, file_exports as File, flow_exports as Flow, int_exports as Int, list_exports as List, money_exports as Money, random_exports as Random, str_exports as Str, time_exports as Time };
|
package/package.json
ADDED
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "qstd",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Standard Block component and utilities library with Panda CSS",
|
|
5
|
+
"author": "Eric Morrison",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"type": "module",
|
|
8
|
+
"main": "./dist/block/index.js",
|
|
9
|
+
"module": "./dist/block/index.mjs",
|
|
10
|
+
"types": "./dist/block/index.d.ts",
|
|
11
|
+
"exports": {
|
|
12
|
+
"./react": {
|
|
13
|
+
"types": "./dist/react/index.d.ts",
|
|
14
|
+
"import": "./dist/react/index.js",
|
|
15
|
+
"require": "./dist/react/index.cjs"
|
|
16
|
+
},
|
|
17
|
+
"./client": {
|
|
18
|
+
"types": "./dist/client/index.d.ts",
|
|
19
|
+
"import": "./dist/client/index.js"
|
|
20
|
+
},
|
|
21
|
+
"./server": {
|
|
22
|
+
"types": "./dist/server/index.d.ts",
|
|
23
|
+
"node": {
|
|
24
|
+
"import": "./dist/server/index.js",
|
|
25
|
+
"require": "./dist/server/index.cjs"
|
|
26
|
+
}
|
|
27
|
+
},
|
|
28
|
+
"./preset": {
|
|
29
|
+
"types": "./dist/preset/index.d.ts",
|
|
30
|
+
"import": "./dist/preset/index.js",
|
|
31
|
+
"require": "./dist/preset/index.cjs"
|
|
32
|
+
},
|
|
33
|
+
"./react/styles.css": "./dist/react/index.css"
|
|
34
|
+
},
|
|
35
|
+
"files": [
|
|
36
|
+
"dist",
|
|
37
|
+
"panda.config.ts",
|
|
38
|
+
"README.md",
|
|
39
|
+
"CHANGELOG.md"
|
|
40
|
+
],
|
|
41
|
+
"sideEffects": [
|
|
42
|
+
"dist/react/index.css"
|
|
43
|
+
],
|
|
44
|
+
"peerDependencies": {
|
|
45
|
+
"react": "^18.0.0 || ^19.0.0",
|
|
46
|
+
"react-dom": "^18.0.0 || ^19.0.0"
|
|
47
|
+
},
|
|
48
|
+
"dependencies": {
|
|
49
|
+
"@floating-ui/react": "^0.27.12",
|
|
50
|
+
"@fortawesome/fontawesome-svg-core": "^7.0.0",
|
|
51
|
+
"@fortawesome/free-brands-svg-icons": "^7.0.0",
|
|
52
|
+
"@fortawesome/free-regular-svg-icons": "^7.0.0",
|
|
53
|
+
"@fortawesome/free-solid-svg-icons": "^7.0.0",
|
|
54
|
+
"@fortawesome/react-fontawesome": "^3.0.1",
|
|
55
|
+
"date-fns": "^4.1.0",
|
|
56
|
+
"framer-motion": "^12.15.0",
|
|
57
|
+
"motion-dom": "^12.23.21",
|
|
58
|
+
"music-metadata-browser": "^2.5.11",
|
|
59
|
+
"nanoid": "^5.1.5",
|
|
60
|
+
"react-icons": "^5.5.0",
|
|
61
|
+
"react-loader-spinner": "^6.1.6",
|
|
62
|
+
"react-spinners": "^0.17.0",
|
|
63
|
+
"use-immer": "^0.11.0"
|
|
64
|
+
},
|
|
65
|
+
"devDependencies": {
|
|
66
|
+
"@pandacss/dev": "^1.2.0",
|
|
67
|
+
"@types/node": "^22.10.5",
|
|
68
|
+
"@types/react": "^19.1.12",
|
|
69
|
+
"@types/react-dom": "^19.1.8",
|
|
70
|
+
"@typescript-eslint/eslint-plugin": "^8.41.0",
|
|
71
|
+
"@typescript-eslint/parser": "^8.41.0",
|
|
72
|
+
"eslint": "^9.28.0",
|
|
73
|
+
"eslint-plugin-react-hooks": "^5.2.0",
|
|
74
|
+
"react": "^19.2.0",
|
|
75
|
+
"react-dom": "^19.2.0",
|
|
76
|
+
"tsup": "^8.0.0",
|
|
77
|
+
"typescript": "^5.9.2",
|
|
78
|
+
"vitest": "^3.1.4"
|
|
79
|
+
},
|
|
80
|
+
"keywords": [
|
|
81
|
+
"react",
|
|
82
|
+
"component",
|
|
83
|
+
"ui",
|
|
84
|
+
"panda-css",
|
|
85
|
+
"utilities",
|
|
86
|
+
"typescript",
|
|
87
|
+
"hooks"
|
|
88
|
+
],
|
|
89
|
+
"repository": {
|
|
90
|
+
"type": "git",
|
|
91
|
+
"url": "https://github.com/ericmorr/qstd"
|
|
92
|
+
},
|
|
93
|
+
"bugs": {
|
|
94
|
+
"url": "https://github.com/ericmorr/qstd/issues"
|
|
95
|
+
},
|
|
96
|
+
"homepage": "https://github.com/ericmorr/qstd#readme",
|
|
97
|
+
"scripts": {
|
|
98
|
+
"build": "panda codegen && panda cssgen && tsup && node scripts/inject-css-import.js",
|
|
99
|
+
"dev": "tsup --watch",
|
|
100
|
+
"test": "vitest run",
|
|
101
|
+
"test:watch": "vitest",
|
|
102
|
+
"test:all": "pnpx tsx tests/test-all.ts",
|
|
103
|
+
"test:block": "node tests/test-block.tsx",
|
|
104
|
+
"test:playground": "node tests/playground-e2e.mjs",
|
|
105
|
+
"typecheck": "tsc --noEmit",
|
|
106
|
+
"typecheck:perf": "tsc --noEmit --extendedDiagnostics",
|
|
107
|
+
"typecheck:trace": "tsc --noEmit --generateTrace ./performance/ts-trace",
|
|
108
|
+
"analyze:tsserver": "bash performance/analyze-tsserver.sh",
|
|
109
|
+
"lint": "eslint src --ext ts,tsx"
|
|
110
|
+
}
|
|
111
|
+
}
|
package/panda.config.ts
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { defineConfig } from "@pandacss/dev";
|
|
2
|
+
import qstdPreset from "./src/preset/index.js";
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* QSTD Panda Config
|
|
6
|
+
*
|
|
7
|
+
* This config uses the exported preset from src/preset/index.ts to avoid duplicating
|
|
8
|
+
* style definitions. The preset contains all the shared configuration that consumers
|
|
9
|
+
* will also use (globalCss, theme, conditions, utilities).
|
|
10
|
+
*
|
|
11
|
+
* ARCHITECTURE:
|
|
12
|
+
* - src/preset/index.ts: Single source of truth for all styles (exported to consumers)
|
|
13
|
+
* - panda.config.ts: Uses the preset + adds build-specific config (include, outdir, etc.)
|
|
14
|
+
*
|
|
15
|
+
* DEPENDENCIES:
|
|
16
|
+
* - The preset MUST be in the presets array alongside Panda's base preset
|
|
17
|
+
* - Order matters: ["@pandacss/dev/presets", qstdPreset] ensures base colors/tokens load first
|
|
18
|
+
* - Any config defined here will extend/override preset values if needed
|
|
19
|
+
*/
|
|
20
|
+
export default defineConfig({
|
|
21
|
+
// Include Panda's base preset for default tokens (colors, spacing, etc.)
|
|
22
|
+
// Then include our qstd preset for custom utilities and semantic tokens
|
|
23
|
+
presets: ["@pandacss/dev/presets", qstdPreset],
|
|
24
|
+
|
|
25
|
+
// Whether to use css reset
|
|
26
|
+
preflight: true,
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* SOURCE FILES TO SCAN
|
|
30
|
+
*
|
|
31
|
+
* Panda scans these files to extract utility usage and generate CSS.
|
|
32
|
+
* For qstd development, we scan the source files (not dist) to enable:
|
|
33
|
+
* - Static extraction of utilities used in Block components
|
|
34
|
+
* - Type generation for TypeScript
|
|
35
|
+
* - CSS generation for the development environment
|
|
36
|
+
*
|
|
37
|
+
* NOTE: The commented line below would enable the css() function to work
|
|
38
|
+
* inside the qstd package itself (for runtime CSS generation).
|
|
39
|
+
* Uncomment if you need to use: import { css } from 'panda/css'
|
|
40
|
+
*/
|
|
41
|
+
include: [
|
|
42
|
+
"./src/**/*.{ts,tsx,js,jsx}",
|
|
43
|
+
// "./dist/**/*.{js,mjs}", // Uncomment to enable css() function within qstd package
|
|
44
|
+
],
|
|
45
|
+
|
|
46
|
+
exclude: [],
|
|
47
|
+
|
|
48
|
+
/**
|
|
49
|
+
* ALL STYLE DEFINITIONS COME FROM THE PRESET
|
|
50
|
+
*
|
|
51
|
+
* The preset (src/preset/index.ts) contains:
|
|
52
|
+
* - globalCss: Root styles and html defaults
|
|
53
|
+
* - theme: Semantic tokens, breakpoints, keyframes
|
|
54
|
+
* - conditions: Custom selectors (dark mode, hover, focus, etc.)
|
|
55
|
+
* - utilities: All custom utilities (flex, grid, rounded, etc.)
|
|
56
|
+
*
|
|
57
|
+
* By importing the preset in the presets array above, all these definitions
|
|
58
|
+
* are automatically included. No need to duplicate them here.
|
|
59
|
+
*
|
|
60
|
+
* If you need to add development-only utilities (like test utilities),
|
|
61
|
+
* you can extend them below in the utilities.extend section.
|
|
62
|
+
*/
|
|
63
|
+
|
|
64
|
+
// The output directory for your css system
|
|
65
|
+
outdir: "styled-system",
|
|
66
|
+
|
|
67
|
+
jsxFramework: "react",
|
|
68
|
+
});
|