@asafarim/shared-i18n 0.8.0 → 0.9.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.
Files changed (94) hide show
  1. package/README.md +266 -280
  2. package/demo/README.md +119 -0
  3. package/demo/index.html +12 -1
  4. package/demo/node_modules/.bin/kill-port +17 -0
  5. package/demo/node_modules/.bin/tsc +5 -9
  6. package/demo/node_modules/.bin/tsserver +5 -9
  7. package/demo/node_modules/.bin/vite +5 -9
  8. package/demo/package.json +7 -4
  9. package/demo/public/404.html +24 -0
  10. package/demo/public/favicon.svg +4 -4
  11. package/demo/public/logo.svg +24 -24
  12. package/demo/src/App.tsx +178 -129
  13. package/demo/src/components/CountryLanguageSelectorsPage.tsx +240 -0
  14. package/demo/src/components/GetStartedSection.tsx +56 -56
  15. package/demo/src/components/KeyTable.tsx +29 -29
  16. package/demo/src/components/LanguageBar.tsx +145 -103
  17. package/demo/src/components/LanguageSwitcherDemo.module.css +114 -114
  18. package/demo/src/components/LanguageSwitchersPage.tsx +245 -0
  19. package/demo/src/components/Logo.tsx +6 -6
  20. package/demo/src/components/OverviewSection.tsx +58 -43
  21. package/demo/src/components/Panel.tsx +15 -15
  22. package/demo/src/components/RoutingLabPage.tsx +147 -0
  23. package/demo/src/components/StatusCard.tsx +109 -109
  24. package/demo/src/data/countries.ts +48 -0
  25. package/demo/src/i18n/localeAdapter.ts +91 -0
  26. package/demo/src/i18n/localeRouting.ts +77 -0
  27. package/demo/src/index.css +1075 -644
  28. package/demo/src/locales/de/demo.json +202 -84
  29. package/demo/src/locales/en/demo.json +201 -85
  30. package/demo/src/locales/fr/demo.json +203 -85
  31. package/demo/src/locales/it/demo.json +202 -84
  32. package/demo/src/locales/lb/demo.json +201 -0
  33. package/demo/src/locales/nl/demo.json +203 -85
  34. package/demo/src/main.tsx +32 -29
  35. package/demo/tsconfig.json +18 -18
  36. package/demo/tsconfig.node.json +10 -10
  37. package/demo/tsconfig.tsbuildinfo +1 -1
  38. package/demo/vite-env.d.ts +7 -7
  39. package/demo/vite.config.d.ts +2 -2
  40. package/demo/vite.config.js +10 -10
  41. package/dist/components/LanguageSwitcher.module.css +303 -303
  42. package/dist/country-language-selector.css +431 -0
  43. package/dist/index.d.ts +2 -0
  44. package/dist/index.d.ts.map +1 -1
  45. package/dist/index.js +2 -0
  46. package/dist/tsconfig.tsbuildinfo +1 -1
  47. package/package.json +87 -85
  48. package/demo/dist/Icon Dropdown_Limited Languages.png +0 -0
  49. package/demo/dist/Select Dropdown_Text Only.png +0 -0
  50. package/demo/dist/assets/favicon-BZYZvBLo.svg +0 -4
  51. package/demo/dist/assets/index-BdjqKw_N.css +0 -1
  52. package/demo/dist/assets/index-C1Tq1uEr.js +0 -191
  53. package/demo/dist/favicon.svg +0 -4
  54. package/demo/dist/index.html +0 -27
  55. package/demo/dist/logo.svg +0 -24
  56. package/demo/node_modules/.bin/browserslist +0 -21
  57. package/demo/node_modules/.bin/browserslist.CMD +0 -12
  58. package/demo/node_modules/.bin/browserslist.ps1 +0 -41
  59. package/demo/node_modules/.bin/tsc.CMD +0 -12
  60. package/demo/node_modules/.bin/tsc.ps1 +0 -41
  61. package/demo/node_modules/.bin/tsserver.CMD +0 -12
  62. package/demo/node_modules/.bin/tsserver.ps1 +0 -41
  63. package/demo/node_modules/.bin/vite.CMD +0 -12
  64. package/demo/node_modules/.bin/vite.ps1 +0 -41
  65. package/demo/node_modules/.vite/deps/@asafarim_country-language-selector.js +0 -848
  66. package/demo/node_modules/.vite/deps/@asafarim_country-language-selector.js.map +0 -7
  67. package/demo/node_modules/.vite/deps/_metadata.json +0 -76
  68. package/demo/node_modules/.vite/deps/chunk-5WRI5ZAA.js +0 -30
  69. package/demo/node_modules/.vite/deps/chunk-5WRI5ZAA.js.map +0 -7
  70. package/demo/node_modules/.vite/deps/chunk-B3AHR5EX.js +0 -1004
  71. package/demo/node_modules/.vite/deps/chunk-B3AHR5EX.js.map +0 -7
  72. package/demo/node_modules/.vite/deps/chunk-E6BG6WAU.js +0 -292
  73. package/demo/node_modules/.vite/deps/chunk-E6BG6WAU.js.map +0 -7
  74. package/demo/node_modules/.vite/deps/chunk-MVARZQEG.js +0 -280
  75. package/demo/node_modules/.vite/deps/chunk-MVARZQEG.js.map +0 -7
  76. package/demo/node_modules/.vite/deps/i18next-browser-languagedetector.js +0 -400
  77. package/demo/node_modules/.vite/deps/i18next-browser-languagedetector.js.map +0 -7
  78. package/demo/node_modules/.vite/deps/i18next.js +0 -2392
  79. package/demo/node_modules/.vite/deps/i18next.js.map +0 -7
  80. package/demo/node_modules/.vite/deps/package.json +0 -3
  81. package/demo/node_modules/.vite/deps/react-dom.js +0 -6
  82. package/demo/node_modules/.vite/deps/react-dom.js.map +0 -7
  83. package/demo/node_modules/.vite/deps/react-dom_client.js +0 -20217
  84. package/demo/node_modules/.vite/deps/react-dom_client.js.map +0 -7
  85. package/demo/node_modules/.vite/deps/react-i18next.js +0 -869
  86. package/demo/node_modules/.vite/deps/react-i18next.js.map +0 -7
  87. package/demo/node_modules/.vite/deps/react.js +0 -5
  88. package/demo/node_modules/.vite/deps/react.js.map +0 -7
  89. package/demo/node_modules/.vite/deps/react_jsx-dev-runtime.js +0 -278
  90. package/demo/node_modules/.vite/deps/react_jsx-dev-runtime.js.map +0 -7
  91. package/demo/node_modules/.vite/deps/react_jsx-runtime.js +0 -6
  92. package/demo/node_modules/.vite/deps/react_jsx-runtime.js.map +0 -7
  93. package/demo/src/components/CountryLanguageDemo.tsx +0 -140
  94. package/demo/src/components/LanguageSwitcherDemo.tsx +0 -256
package/demo/README.md ADDED
@@ -0,0 +1,119 @@
1
+ # @asafarim/shared-i18n Demo
2
+
3
+ Interactive demo for [@asafarim/shared-i18n](../README.md). Showcases **both** `LanguageSwitcher` and `CountryLanguageSelector` imported from a single package, with Benelux + UK locale-aware URL routing.
4
+
5
+ Live: [https://alisafari-it.github.io/shared-i18n/](https://alisafari-it.github.io/shared-i18n/)
6
+
7
+ ## Local Development
8
+
9
+ ```bash
10
+ # From workspace root — build the package first
11
+ pnpm install
12
+ pnpm run build # builds @asafarim/shared-i18n (including CSS copy)
13
+
14
+ # Start the demo dev server
15
+ cd demo
16
+ pnpm run dev # http://localhost:5173/shared-i18n/
17
+ ```
18
+
19
+ ## Demo Pages
20
+
21
+ ### Overview (`/be-en/overview`)
22
+ - Hero with live locale / URL preview
23
+ - Two-column feature comparison between `LanguageSwitcher` and `CountryLanguageSelector`
24
+ - Routing contract explanation
25
+
26
+ ### Get Started (`/be-en/get-started`)
27
+ - Step-by-step guide: install → CSS import → `initI18n` → add both selectors
28
+ - Code snippets for `resolveLocaleFromLanguage` adapter pattern
29
+ - Pro tips
30
+
31
+ ### Language Switchers (`/be-en/language-switchers`)
32
+ All six `LanguageSwitcher` variants with live `resolveLocaleFromLanguage` wiring:
33
+ - Buttons, select, icon-dropdown (all / limited languages)
34
+ - Icon-dropdown with labels
35
+ - Toggle button (2 languages)
36
+ - **Comparison table** and country-awareness explanation
37
+ - Inline notice when language falls back to a different country
38
+
39
+ ### Country Language Selectors (`/be-en/country-language-selectors`)
40
+ All `CountryLanguageSelector` variants controlled by the same locale:
41
+ - Image flags / emoji flags × compact / full / flag-only triggers
42
+ - Custom `renderTrigger` render prop example
43
+ - Popover `align="start"` variant
44
+ - Live status bar (country, language, slug, URL)
45
+
46
+ ### Routing Lab (`/be-en/routing-lab`)
47
+ Side-by-side demo:
48
+ - Left: `LanguageSwitcher` + `resolveLocaleFromLanguage` adapter with fallback notices
49
+ - Right: `CountryLanguageSelector` direct full-locale output
50
+ - Scripted scenario cards that apply predefined transitions
51
+
52
+ ## Countries Covered
53
+
54
+ | Code | Country | Languages |
55
+ |------|---------|-----------|
56
+ | BE | Belgium | en, nl, fr, de |
57
+ | NL | Netherlands | nl, en |
58
+ | LU | Luxembourg | lb, fr, de, en |
59
+ | GB | United Kingdom | en |
60
+
61
+ ## URL Structure
62
+
63
+ ```
64
+ /shared-i18n/<country-lower>-<language-lower>/<page>
65
+
66
+ Examples:
67
+ /shared-i18n/be-en/overview
68
+ /shared-i18n/nl-nl/language-switchers
69
+ /shared-i18n/lu-fr/country-language-selectors
70
+ /shared-i18n/gb-en/routing-lab
71
+ ```
72
+
73
+ Changing locale preserves the active page; changing page preserves the active locale. Invalid slugs fall back to `be-en/overview`.
74
+
75
+ ## Architecture
76
+
77
+ ```
78
+ demo/src/
79
+ ├── App.tsx # URL-driven router, locale ↔ i18n sync
80
+ ├── main.tsx # initI18n + CSS import
81
+ ├── index.css # Premium app-shell design
82
+ ├── data/
83
+ │ └── countries.ts # Benelux + UK country list (Country[])
84
+ ├── i18n/
85
+ │ ├── localeRouting.ts # DemoPage type, slug helpers, parsePathname
86
+ │ └── localeAdapter.ts # resolveLocaleFromLanguage helper
87
+ ├── components/
88
+ │ ├── LanguageBar.tsx # Navbar: two CLS controls, theme toggle
89
+ │ ├── OverviewSection.tsx # Overview feature cards
90
+ │ ├── GetStartedSection.tsx # Accordion steps
91
+ │ ├── LanguageSwitchersPage.tsx # All LanguageSwitcher variants + comparison table
92
+ │ ├── CountryLanguageSelectorsPage.tsx # All CLS variants
93
+ │ ├── RoutingLabPage.tsx # Side-by-side LS vs CLS routing demo
94
+ │ ├── KeyTable.tsx # Translation key inspector
95
+ │ ├── StatusCard.tsx # i18n live status
96
+ │ └── Logo.tsx # Brand logo
97
+ └── locales/
98
+ ├── en/demo.json
99
+ ├── nl/demo.json
100
+ ├── fr/demo.json
101
+ ├── de/demo.json
102
+ └── it/demo.json
103
+ ```
104
+
105
+ ## Key Technologies
106
+
107
+ - **React 19** + **TypeScript**
108
+ - **Vite 6** — build tool and dev server
109
+ - **i18next** + **react-i18next** — translation engine
110
+ - **@asafarim/shared-i18n** — LanguageSwitcher, CountryLanguageSelector, all hooks
111
+ - **@asafarim/design-tokens** — Design system
112
+
113
+ ## GitHub Pages Deployment
114
+
115
+ The demo uses a `public/404.html` + `index.html` script pattern to handle SPA deep links on GitHub Pages. See those files for the implementation.
116
+
117
+ ## License
118
+
119
+ MIT
package/demo/index.html CHANGED
@@ -2,9 +2,20 @@
2
2
  <html lang="en">
3
3
  <head>
4
4
  <meta charset="UTF-8" />
5
- <link rel="icon" type="image/svg+xml" href="./public/favicon.svg" />
5
+ <link rel="icon" type="image/svg+xml" href="./favicon.svg" />
6
6
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
7
7
  <title>Shared i18n demo</title>
8
+ <script>
9
+ // SPA GitHub Pages fallback decoder. Pairs with public/404.html.
10
+ (function (l) {
11
+ if (l.search[1] === '/') {
12
+ var decoded = l.search.slice(1).split('&').map(function (s) {
13
+ return s.replace(/~and~/g, '&');
14
+ }).join('?');
15
+ window.history.replaceState(null, '', l.pathname.slice(0, -1) + decoded + l.hash);
16
+ }
17
+ }(window.location));
18
+ </script>
8
19
  </head>
9
20
  <body>
10
21
  <div id="root"></div>
@@ -0,0 +1,17 @@
1
+ #!/bin/sh
2
+ basedir=$(dirname "$(echo "$0" | sed -e 's,\\,/,g')")
3
+
4
+ case `uname` in
5
+ *CYGWIN*) basedir=`cygpath -w "$basedir"`;;
6
+ esac
7
+
8
+ if [ -z "$NODE_PATH" ]; then
9
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/kill-port@2.0.1/node_modules/kill-port/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/kill-port@2.0.1/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules"
10
+ else
11
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/kill-port@2.0.1/node_modules/kill-port/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/kill-port@2.0.1/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
12
+ fi
13
+ if [ -x "$basedir/node" ]; then
14
+ exec "$basedir/node" "$basedir/../kill-port/cli.js" "$@"
15
+ else
16
+ exec node "$basedir/../kill-port/cli.js" "$@"
17
+ fi
@@ -2,20 +2,16 @@
2
2
  basedir=$(dirname "$(echo "$0" | sed -e 's,\\,/,g')")
3
3
 
4
4
  case `uname` in
5
- *CYGWIN*|*MINGW*|*MSYS*)
6
- if command -v cygpath > /dev/null 2>&1; then
7
- basedir=`cygpath -w "$basedir"`
8
- fi
9
- ;;
5
+ *CYGWIN*) basedir=`cygpath -w "$basedir"`;;
10
6
  esac
11
7
 
12
8
  if [ -z "$NODE_PATH" ]; then
13
- export NODE_PATH="/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/node_modules"
9
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules"
14
10
  else
15
- export NODE_PATH="/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
11
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
16
12
  fi
17
13
  if [ -x "$basedir/node" ]; then
18
- exec "$basedir/node" "$basedir/../../../node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/tsc" "$@"
14
+ exec "$basedir/node" "$basedir/../typescript/bin/tsc" "$@"
19
15
  else
20
- exec node "$basedir/../../../node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/tsc" "$@"
16
+ exec node "$basedir/../typescript/bin/tsc" "$@"
21
17
  fi
@@ -2,20 +2,16 @@
2
2
  basedir=$(dirname "$(echo "$0" | sed -e 's,\\,/,g')")
3
3
 
4
4
  case `uname` in
5
- *CYGWIN*|*MINGW*|*MSYS*)
6
- if command -v cygpath > /dev/null 2>&1; then
7
- basedir=`cygpath -w "$basedir"`
8
- fi
9
- ;;
5
+ *CYGWIN*) basedir=`cygpath -w "$basedir"`;;
10
6
  esac
11
7
 
12
8
  if [ -z "$NODE_PATH" ]; then
13
- export NODE_PATH="/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/node_modules"
9
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules"
14
10
  else
15
- export NODE_PATH="/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
11
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/typescript@5.8.3/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
16
12
  fi
17
13
  if [ -x "$basedir/node" ]; then
18
- exec "$basedir/node" "$basedir/../../../node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/tsserver" "$@"
14
+ exec "$basedir/node" "$basedir/../typescript/bin/tsserver" "$@"
19
15
  else
20
- exec node "$basedir/../../../node_modules/.pnpm/typescript@5.8.3/node_modules/typescript/bin/tsserver" "$@"
16
+ exec node "$basedir/../typescript/bin/tsserver" "$@"
21
17
  fi
@@ -2,20 +2,16 @@
2
2
  basedir=$(dirname "$(echo "$0" | sed -e 's,\\,/,g')")
3
3
 
4
4
  case `uname` in
5
- *CYGWIN*|*MINGW*|*MSYS*)
6
- if command -v cygpath > /dev/null 2>&1; then
7
- basedir=`cygpath -w "$basedir"`
8
- fi
9
- ;;
5
+ *CYGWIN*) basedir=`cygpath -w "$basedir"`;;
10
6
  esac
11
7
 
12
8
  if [ -z "$NODE_PATH" ]; then
13
- export NODE_PATH="/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/bin/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/node_modules"
9
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/bin/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules"
14
10
  else
15
- export NODE_PATH="/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/bin/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules:/mnt/c/repos/my-tools/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
11
+ export NODE_PATH="/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/bin/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules:/home/runner/work/shared-i18n/shared-i18n/node_modules/.pnpm/node_modules:$NODE_PATH"
16
12
  fi
17
13
  if [ -x "$basedir/node" ]; then
18
- exec "$basedir/node" "$basedir/../../../node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/bin/vite.js" "$@"
14
+ exec "$basedir/node" "$basedir/../vite/bin/vite.js" "$@"
19
15
  else
20
- exec node "$basedir/../../../node_modules/.pnpm/vite@6.4.1_@types+node@24.10.4/node_modules/vite/bin/vite.js" "$@"
16
+ exec node "$basedir/../vite/bin/vite.js" "$@"
21
17
  fi
package/demo/package.json CHANGED
@@ -1,14 +1,16 @@
1
1
  {
2
2
  "name": "shared-i18n-demo",
3
- "version": "0.8.1",
3
+ "version": "0.9.0",
4
4
  "type": "module",
5
5
  "scripts": {
6
6
  "dev": "vite",
7
7
  "build": "tsc -b && vite build",
8
- "preview": "vite preview"
8
+ "preview": "vite preview",
9
+ "predev": "kill-port 5173",
10
+ "postdev": "echo 'Demo running at http://localhost:5173/shared-i18n/'"
9
11
  },
10
12
  "dependencies": {
11
- "@asafarim/country-language-selector": "^0.2.3",
13
+ "@asafarim/country-language-selector": "^0.4.1",
12
14
  "@asafarim/design-tokens": "^0.5.0",
13
15
  "@asafarim/shared-i18n": "workspace:*",
14
16
  "react": "^19.0.0",
@@ -19,7 +21,8 @@
19
21
  "@types/react-dom": "^19.0.0",
20
22
  "@vitejs/plugin-react": "^4.3.0",
21
23
  "typescript": "~5.8.3",
22
- "vite": "^6.0.0"
24
+ "vite": "^6.0.0",
25
+ "kill-port": "^2.0.1"
23
26
  },
24
27
  "publishConfig": {
25
28
  "access": "public"
@@ -0,0 +1,24 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8" />
5
+ <title>Shared i18n demo</title>
6
+ <script>
7
+ // SPA GitHub Pages fallback (rafgraph/spa-github-pages).
8
+ // Single-page apps for GitHub Pages — MIT license.
9
+ // Rewrites a deep URL into a single query string and redirects to the
10
+ // SPA index, which decodes it back into history.
11
+ var pathSegmentsToKeep = 1; // keep the `/shared-i18n` base path
12
+
13
+ var l = window.location;
14
+ l.replace(
15
+ l.protocol + '//' + l.hostname + (l.port ? ':' + l.port : '') +
16
+ l.pathname.split('/').slice(0, 1 + pathSegmentsToKeep).join('/') + '/?/' +
17
+ l.pathname.slice(1).split('/').slice(pathSegmentsToKeep).join('/').replace(/&/g, '~and~') +
18
+ (l.search ? '&' + l.search.slice(1).replace(/&/g, '~and~') : '') +
19
+ l.hash
20
+ );
21
+ </script>
22
+ </head>
23
+ <body></body>
24
+ </html>
@@ -1,4 +1,4 @@
1
- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100">
2
- <rect width="100" height="100" fill="#4F46E5"/>
3
- <text x="50" y="65" font-size="60" font-weight="bold" text-anchor="middle" fill="white">i18n</text>
4
- </svg>
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100">
2
+ <rect width="100" height="100" fill="#4F46E5"/>
3
+ <text x="50" y="65" font-size="60" font-weight="bold" text-anchor="middle" fill="white">i18n</text>
4
+ </svg>
@@ -1,24 +1,24 @@
1
- <svg width="180" height="180" viewBox="0 0 180 180" fill="none" xmlns="http://www.w3.org/2000/svg">
2
- <defs>
3
- <linearGradient id="bg" x1="0%" y1="0%" x2="100%" y2="100%">
4
- <stop offset="0%" stop-color="#3A5AFE" />
5
- <stop offset="100%" stop-color="#14B8A6" />
6
- </linearGradient>
7
- <linearGradient id="accent" x1="0%" y1="0%" x2="0%" y2="100%">
8
- <stop offset="0%" stop-color="#FFFFFF" stop-opacity="0.9" />
9
- <stop offset="100%" stop-color="#FFFFFF" stop-opacity="0.2" />
10
- </linearGradient>
11
- <filter id="shadow" x="-20%" y="-20%" width="140%" height="140%" color-interpolation-filters="sRGB">
12
- <feDropShadow dx="0" dy="8" stdDeviation="12" flood-color="#0B1220" flood-opacity="0.28" />
13
- </filter>
14
- </defs>
15
- <rect width="180" height="180" rx="32" fill="url(#bg)" filter="url(#shadow)" />
16
- <g transform="translate(45 45)">
17
- <path d="M45 0C20.147 0 0 20.147 0 45C0 69.853 20.147 90 45 90C69.853 90 90 69.853 90 45C90 20.147 69.853 0 45 0ZM45 72C29.088 72 15.75 58.662 15.75 42.75C15.75 26.838 29.088 13.5 45 13.5C60.912 13.5 74.25 26.838 74.25 42.75C74.25 58.662 60.912 72 45 72Z" fill="white" opacity="0.2" />
18
- <path d="M24 27H66C70.971 27 75 31.029 75 36V54C75 58.971 70.971 63 66 63H24C19.029 63 15 58.971 15 54V36C15 31.029 19.029 27 24 27Z" fill="url(#accent)" />
19
- <path d="M36 54V45C36 40.029 40.029 36 45 36C49.971 36 54 40.029 54 45V54" stroke="#0B1220" stroke-width="4" stroke-linecap="round" />
20
- <circle cx="45" cy="21" r="6" fill="white" />
21
- <path d="M33 69H57" stroke="white" stroke-width="4" stroke-linecap="round" opacity="0.7" />
22
- <path d="M27 15H63" stroke="white" stroke-width="4" stroke-linecap="round" opacity="0.4" />
23
- </g>
24
- </svg>
1
+ <svg width="180" height="180" viewBox="0 0 180 180" fill="none" xmlns="http://www.w3.org/2000/svg">
2
+ <defs>
3
+ <linearGradient id="bg" x1="0%" y1="0%" x2="100%" y2="100%">
4
+ <stop offset="0%" stop-color="#3A5AFE" />
5
+ <stop offset="100%" stop-color="#14B8A6" />
6
+ </linearGradient>
7
+ <linearGradient id="accent" x1="0%" y1="0%" x2="0%" y2="100%">
8
+ <stop offset="0%" stop-color="#FFFFFF" stop-opacity="0.9" />
9
+ <stop offset="100%" stop-color="#FFFFFF" stop-opacity="0.2" />
10
+ </linearGradient>
11
+ <filter id="shadow" x="-20%" y="-20%" width="140%" height="140%" color-interpolation-filters="sRGB">
12
+ <feDropShadow dx="0" dy="8" stdDeviation="12" flood-color="#0B1220" flood-opacity="0.28" />
13
+ </filter>
14
+ </defs>
15
+ <rect width="180" height="180" rx="32" fill="url(#bg)" filter="url(#shadow)" />
16
+ <g transform="translate(45 45)">
17
+ <path d="M45 0C20.147 0 0 20.147 0 45C0 69.853 20.147 90 45 90C69.853 90 90 69.853 90 45C90 20.147 69.853 0 45 0ZM45 72C29.088 72 15.75 58.662 15.75 42.75C15.75 26.838 29.088 13.5 45 13.5C60.912 13.5 74.25 26.838 74.25 42.75C74.25 58.662 60.912 72 45 72Z" fill="white" opacity="0.2" />
18
+ <path d="M24 27H66C70.971 27 75 31.029 75 36V54C75 58.971 70.971 63 66 63H24C19.029 63 15 58.971 15 54V36C15 31.029 19.029 27 24 27Z" fill="url(#accent)" />
19
+ <path d="M36 54V45C36 40.029 40.029 36 45 36C49.971 36 54 40.029 54 45V54" stroke="#0B1220" stroke-width="4" stroke-linecap="round" />
20
+ <circle cx="45" cy="21" r="6" fill="white" />
21
+ <path d="M33 69H57" stroke="white" stroke-width="4" stroke-linecap="round" opacity="0.7" />
22
+ <path d="M27 15H63" stroke="white" stroke-width="4" stroke-linecap="round" opacity="0.4" />
23
+ </g>
24
+ </svg>