@shadow-js/ui 1.0.4 → 1.0.5

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 CHANGED
@@ -1,5 +1,12 @@
1
1
  # Changelog
2
2
 
3
+ ## 1.0.5
4
+
5
+ ### Fixed
6
+
7
+ - Calendar month names and the DatePicker round trip follow the Gregorian grid in every locale.
8
+ - The message formatter's per-locale caches are bounded.
9
+
3
10
  ## 1.0.4
4
11
 
5
12
  ### Changed
package/README.md CHANGED
@@ -302,7 +302,7 @@ it("starts from the system, toggles the html class and remembers the choice", ()
302
302
 
303
303
  `ThemeProvider` persists the choice in `localStorage`, follows `prefers-color-scheme` while the theme is
304
304
  `"system"`, syncs between tabs, and is SSR-safe: it touches nothing before it has mounted, so `resolvedTheme()`
305
- is `undefined` on the server and on the first client render (hydration never mismatches). If the browser blocks
305
+ is `undefined` on the server and on the first client render, and the resolved theme is applied after mount. If the browser blocks
306
306
  `localStorage`, the choice still applies for the current page.
307
307
 
308
308
  **No flash**: `themeScript()` returns a dependency-free ES5 script as text; put it in a `<script>` in `<head>` and the
@@ -578,7 +578,7 @@ Everything is documented with TSDoc in the sources.
578
578
  - Runtime `@shadow-js/table` `1.0.4`: imported only as types by the data-table item (`registry/data-table/data-table.tsx`).
579
579
  - Runtime `class-variance-authority` `0.7.1`: `cva` and `VariantProps` (`src/index.ts`).
580
580
  - Runtime `clsx` `2.1.1` and `tailwind-merge` `3.7.0`: class merging behind `cn` (`registry/utils/utils.ts`).
581
- - Peers: `@shadow-js/core`, `@shadow-js/primitives`, and `@shadow-js/web` `^1.0.3`: the behavior and rendering under each component.
581
+ - Peers: `@shadow-js/core`, `@shadow-js/primitives`, and `@shadow-js/web` `^1.0.5`: the behavior and rendering under each component.
582
582
 
583
583
  ## Types
584
584
 
package/dist/cli.mjs CHANGED
@@ -2443,7 +2443,7 @@ function realContext(cwd) {
2443
2443
  cwd: resolve(cwd ?? process.cwd()),
2444
2444
  fs: nodeFs(),
2445
2445
  registry: loadRegistrySource(),
2446
- version: "1.0.4",
2446
+ version: "1.0.5",
2447
2447
  out: (line) => process.stdout.write(`${line}\n`),
2448
2448
  err: (line) => process.stderr.write(`${line}\n`),
2449
2449
  async confirm(question) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@shadow-js/ui",
3
- "version": "1.0.4",
3
+ "version": "1.0.5",
4
4
  "description": "shadcn-style components you add to your project with a CLI, styled with Tailwind v4",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -60,22 +60,22 @@
60
60
  "check": "npm run lint && npm run typecheck && npm run build && npm test && npm run test:perf && npm run test:gc"
61
61
  },
62
62
  "peerDependencies": {
63
- "@shadow-js/core": "^1.0.4",
64
- "@shadow-js/primitives": "^1.0.4",
65
- "@shadow-js/web": "^1.0.4"
63
+ "@shadow-js/core": "^1.0.5",
64
+ "@shadow-js/primitives": "^1.0.5",
65
+ "@shadow-js/web": "^1.0.5"
66
66
  },
67
67
  "devDependencies": {
68
68
  "@biomejs/biome": "2.5.15",
69
- "@shadow-js/compiler": "^1.0.4",
70
- "@shadow-js/core": "^1.0.4",
71
- "@shadow-js/forms": "^1.0.4",
72
- "@shadow-js/primitives": "^1.0.4",
73
- "@shadow-js/testing": "^1.0.4",
74
- "@shadow-js/web": "^1.0.4",
69
+ "@shadow-js/compiler": "^1.0.5",
70
+ "@shadow-js/core": "^1.0.5",
71
+ "@shadow-js/forms": "^1.0.5",
72
+ "@shadow-js/primitives": "^1.0.5",
73
+ "@shadow-js/testing": "^1.0.5",
74
+ "@shadow-js/web": "^1.0.5",
75
75
  "@tailwindcss/node": "4.3.3",
76
76
  "@types/node": "^24.0.0",
77
77
  "fast-check": "^4.10.2",
78
- "happy-dom": "^21.0.3",
78
+ "happy-dom": "21.0.4",
79
79
  "oxc-parser": "0.153.0",
80
80
  "shiki": "4.5.0",
81
81
  "tailwindcss": "4.3.3",
@@ -84,7 +84,7 @@
84
84
  "vitest": "5.0.3"
85
85
  },
86
86
  "dependencies": {
87
- "@shadow-js/table": "1.0.4",
87
+ "@shadow-js/table": "1.0.5",
88
88
  "class-variance-authority": "0.7.1",
89
89
  "clsx": "2.1.1",
90
90
  "tailwind-merge": "3.7.0"
@@ -67,7 +67,12 @@ export interface CalendarLabels {
67
67
 
68
68
  /** The month names of a locale, from `Intl` (January first). @internal */
69
69
  function monthNames(locale: string): string[] {
70
- const format = new Intl.DateTimeFormat(locale, { month: "long", timeZone: "UTC" });
70
+ // Gregorian months: the grid is Gregorian, and a locale such as fa-IR defaults to a calendar whose months differ.
71
+ const format = new Intl.DateTimeFormat(locale, {
72
+ month: "long",
73
+ timeZone: "UTC",
74
+ calendar: "gregory",
75
+ });
71
76
  return Array.from({ length: 12 }, (_, index) =>
72
77
  format.format(new Date(Date.UTC(2000, index, 15))),
73
78
  );
@@ -174,6 +174,12 @@ function parseMessage(message: string): readonly Piece[] {
174
174
  return sequence(false, false);
175
175
  }
176
176
 
177
+ /**
178
+ * Most locales each of the caches below keeps. A locale often comes from a request header or a URL, so the
179
+ * set is not the app's own: a full cache starts over instead of growing with every new tag. @internal
180
+ */
181
+ const MAX_CACHED_LOCALES = 128;
182
+
177
183
  const RTL_LANGUAGES = new Set(["ar", "he", "fa", "ur", "ps", "sd", "ug", "yi", "dv", "ckb", "ks"]);
178
184
  const DIRECTIONS = new Map<string, boolean>();
179
185
 
@@ -192,6 +198,7 @@ function isRightToLeft(locale: string): boolean {
192
198
  if (!(error instanceof RangeError)) throw error;
193
199
  known = false;
194
200
  }
201
+ if (DIRECTIONS.size >= MAX_CACHED_LOCALES) DIRECTIONS.clear();
195
202
  DIRECTIONS.set(locale, known);
196
203
  }
197
204
  return known;
@@ -214,6 +221,7 @@ function numberFormat(locale: string, style: string | undefined): Intl.NumberFor
214
221
  ? { maximumFractionDigits: 0 }
215
222
  : undefined,
216
223
  );
224
+ if (NUMBER_FORMATS.size >= MAX_CACHED_LOCALES) NUMBER_FORMATS.clear();
217
225
  NUMBER_FORMATS.set(key, format);
218
226
  }
219
227
  return format;
@@ -246,6 +254,7 @@ function write(
246
254
  let rules = PLURAL_RULES.get(locale);
247
255
  if (rules === undefined) {
248
256
  rules = new Intl.PluralRules(locale);
257
+ if (PLURAL_RULES.size >= MAX_CACHED_LOCALES) PLURAL_RULES.clear();
249
258
  PLURAL_RULES.set(locale, rules);
250
259
  }
251
260
  const shifted = count - piece.offset;
package/registry.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@shadow-js/ui",
3
- "version": "1.0.4",
3
+ "version": "1.0.5",
4
4
  "frameworkDependencies": [
5
5
  "@shadow-js/core",
6
6
  "@shadow-js/primitives",
@@ -1063,7 +1063,7 @@
1063
1063
  "utils"
1064
1064
  ],
1065
1065
  "dependencies": {
1066
- "@shadow-js/table": "1.0.4"
1066
+ "@shadow-js/table": "1.0.5"
1067
1067
  },
1068
1068
  "exports": [
1069
1069
  "DataTable",