langsys-js-react 0.6.6 → 0.7.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/dist/index.mjs CHANGED
@@ -1,16 +1,45 @@
1
- import { createSignal, tSignal, currentlyLoadedLocale, sTranslations, Translate as Translate$1, Phrase as Phrase$1, PHRASE_MARKER_ATTR, LangsysApp as LangsysApp$1 } from 'langsys-js-typescript';
2
- export { LangsysAppAPI, canonicalizeLocale, createSignal, currentlyLoadedLocale, sTranslations, tSignal as t } from 'langsys-js-typescript';
3
- import { useSyncExternalStore, useState, useRef, useEffect, createElement } from 'react';
1
+ import { LangsysApp, scopeFromSeed, createSignal, tSignal, currentlyLoadedLocale, sTranslations, writeEnabled, notifyNavigation, renderServerMessage, renderBlock, currentRequestScope, CONTENT_BLOCK_MARKER_ATTR, PHRASE_MARKER_ATTR, registerBlock, warnUnregistered, isTranslationExcluded, warnUnrenderedBlock, Translate as Translate$1, Phrase as Phrase$1 } from 'langsys-js-typescript';
2
+ export { DEFAULT_SERVER_MESSAGE_CATEGORY, LangsysAppAPI, LangsysConfigurationError, LegacyFormatError, SnapshotError, canonicalizeLocale, createSignal, currentlyLoadedLocale, inCategory, interpolate, isCategoryRef, localeHeaders, notifyNavigation, renderServerMessage, resolveServerMessages, sTranslations, setWriteGrant, tSignal as t } from 'langsys-js-typescript';
3
+ import * as React from 'react';
4
+ import { createContext, useState, useInsertionEffect, createElement, useContext, useSyncExternalStore, useEffect, useMemo, useRef, isValidElement, cloneElement, Fragment, Children } from 'react';
5
+ import { NON_TRANSLATABLE_ELEMENTS } from 'langsys-js-typescript/pure';
4
6
 
5
7
  // src/index.ts
6
- function useSignal(signal) {
7
- return useSyncExternalStore(signal.subscribe, signal.get, signal.get);
8
+ var SeedScope = createContext(null);
9
+ var noSubscription = () => () => {
10
+ };
11
+ function useServerSnapshotWindow() {
12
+ return useSyncExternalStore(
13
+ noSubscription,
14
+ () => false,
15
+ () => true
16
+ );
8
17
  }
18
+ function useSeedScopeRunner() {
19
+ const scope = useContext(SeedScope);
20
+ const inWindow = useServerSnapshotWindow();
21
+ return scope && inWindow ? (fn) => scope.run(fn) : (fn) => fn();
22
+ }
23
+ function LangsysProvider({ seed, children }) {
24
+ const [scope] = useState(() => seed ? scopeFromSeed(seed) : null);
25
+ useInsertionEffect(() => {
26
+ if (seed) LangsysApp.seedCatalog(seed.catalog, seed.locale, seed);
27
+ }, []);
28
+ return createElement(SeedScope.Provider, { value: scope }, children);
29
+ }
30
+ var LangsysApp2 = LangsysApp;
9
31
  function createLocaleStore(initial = "en-US") {
10
32
  return createSignal(initial);
11
33
  }
34
+
35
+ // src/adapters.ts
36
+ function useSignal(signal) {
37
+ const scope = useContext(SeedScope);
38
+ return useSyncExternalStore(signal.subscribe, signal.get, scope ? () => scope.run(signal.get) : signal.get);
39
+ }
12
40
  function useT() {
13
- return useSignal(tSignal);
41
+ const scope = useContext(SeedScope);
42
+ return useSyncExternalStore(tSignal.subscribe, tSignal.get, scope ? () => scope.t : tSignal.get);
14
43
  }
15
44
  function useCurrentLocale() {
16
45
  return useSignal(currentlyLoadedLocale);
@@ -23,123 +52,428 @@ function useLocaleStore(initial = "en-US") {
23
52
  const locale = useSignal(store);
24
53
  return [locale, store.set, store];
25
54
  }
55
+ var writeEnabledServerSnapshot = () => void 0;
56
+ function useWriteEnabled() {
57
+ return useSyncExternalStore(writeEnabled.subscribe, writeEnabled.get, writeEnabledServerSnapshot);
58
+ }
59
+ function useNotifyNavigation(location) {
60
+ useEffect(() => {
61
+ notifyNavigation();
62
+ }, [location]);
63
+ }
64
+ function useRenderServerMessage() {
65
+ const t = useT();
66
+ const inSeedScope = useSeedScopeRunner();
67
+ return useMemo(
68
+ () => (entry, category) => inSeedScope(() => renderServerMessage(entry, category)),
69
+ // eslint-disable-next-line react-hooks/exhaustive-deps
70
+ [t]
71
+ );
72
+ }
73
+ function DontTranslate({ tag = "span", className, children }) {
74
+ return createElement(
75
+ tag,
76
+ { translate: "no", "data-ls-dont-translate": "", className },
77
+ children
78
+ );
79
+ }
80
+
81
+ // src/block-nodes.ts
82
+ var PORTAL = /* @__PURE__ */ Symbol.for("react.portal");
83
+ var PROP_TO_ATTR = { className: "class", htmlFor: "for" };
84
+ function attrValue(value) {
85
+ if (typeof value === "function" || typeof value === "object" || value === void 0 || value === false) return void 0;
86
+ return value === true ? "" : String(value);
87
+ }
88
+ function attrsOf(props) {
89
+ const out = {};
90
+ for (const [name, value] of Object.entries(props)) {
91
+ if (name === "children" || name === "key" || name === "ref") continue;
92
+ const attr = attrValue(value);
93
+ if (attr !== void 0) out[PROP_TO_ATTR[name] ?? name] = attr;
94
+ }
95
+ return Object.keys(out).length ? out : void 0;
96
+ }
97
+ var CONTEXT = /* @__PURE__ */ Symbol.for("react.context");
98
+ var read = React.use;
99
+ function isContext(node) {
100
+ return typeof node === "object" && node !== null && node.$$typeof === CONTEXT;
101
+ }
102
+ function isUsable(node) {
103
+ if (typeof node !== "object" || node === null) return false;
104
+ return typeof node.then === "function" || node.$$typeof === CONTEXT;
105
+ }
106
+ function isParamValue(value) {
107
+ return typeof value === "string" || typeof value === "number" || typeof value === "boolean" || isDate(value);
108
+ }
109
+ function isDate(value) {
110
+ return Object.prototype.toString.call(value) === "[object Date]";
111
+ }
112
+ var oneShotItems = /* @__PURE__ */ new WeakMap();
113
+ function itemsOf(list) {
114
+ if (list[Symbol.iterator]() !== list) return Array.from(list);
115
+ let items = oneShotItems.get(list);
116
+ if (!items) oneShotItems.set(list, items = Array.from(list));
117
+ return items;
118
+ }
119
+ function isIterable(node) {
120
+ return typeof node === "object" && node !== null && !isValidElement(node) && typeof node[Symbol.iterator] === "function";
121
+ }
122
+ function isPortal(node) {
123
+ return typeof node === "object" && node !== null && node.$$typeof === PORTAL;
124
+ }
125
+ function toBlockNodes(children) {
126
+ const elements = [];
127
+ const portals = [];
128
+ const nested = [];
129
+ let failure;
130
+ function mapLevel(level, parent) {
131
+ const out = [];
132
+ const visit = (node) => {
133
+ if (failure || node === null || node === void 0 || typeof node === "boolean") return;
134
+ if (typeof node === "string" || typeof node === "number" || typeof node === "bigint") {
135
+ out.push({ text: String(node) });
136
+ return;
137
+ }
138
+ if (Array.isArray(node)) return node.forEach(visit);
139
+ if (isPortal(node)) {
140
+ if (parent === null) portals.push(node);
141
+ else nested[parent].push(node);
142
+ return;
143
+ }
144
+ if (!isValidElement(node)) {
145
+ failure = `an unsupported child (${typeof node})`;
146
+ return;
147
+ }
148
+ const props = node.props;
149
+ if (node.type === DontTranslate) return visit(DontTranslate(props));
150
+ if (typeof node.type !== "string") {
151
+ failure = "a component, provider, lazy or Suspense child, whose DOM is unknown until React renders it";
152
+ return;
153
+ }
154
+ if (props.dangerouslySetInnerHTML) {
155
+ failure = "dangerouslySetInnerHTML, an HTML string rather than a tree";
156
+ return;
157
+ }
158
+ const index = elements.push(node) - 1;
159
+ nested[index] = [];
160
+ const kids = mapLevel(props.children, index);
161
+ const attrs = attrsOf(props);
162
+ out.push({ tag: node.type, ...attrs ? { attrs } : {}, ...kids.length ? { children: kids } : {} });
163
+ };
164
+ Children.toArray(withoutFragments(level)).forEach(visit);
165
+ return out;
166
+ }
167
+ const nodes = mapLevel(children, null);
168
+ return failure ? { ok: false, reason: failure } : { ok: true, nodes, elements, portals, nested };
169
+ }
170
+ var ATTR_TO_PROP = { class: "className", for: "htmlFor" };
171
+ var literally = (text) => text.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
172
+ function propFor(attr, props) {
173
+ const same = new RegExp(`^${literally(attr)}$`, "i");
174
+ return ATTR_TO_PROP[attr] ?? Object.keys(props).find((name) => same.test(name)) ?? attr;
175
+ }
176
+ function toReactNodes(nodes, elements, nested = []) {
177
+ return nodes.flatMap((node) => {
178
+ if ("text" in node) return [node.text];
179
+ if ("comment" in node) return [];
180
+ const original = elements[node.source];
181
+ const originalProps = original.props;
182
+ const changed = {};
183
+ for (const [attr, value] of Object.entries(node.attrs)) {
184
+ if (value === true) continue;
185
+ const prop = propFor(attr, originalProps);
186
+ if ((attrValue(originalProps[prop]) ?? "") !== value) changed[prop] = value;
187
+ }
188
+ const kids = [...toReactNodes(node.children, elements, nested), ...nested[node.source] ?? []];
189
+ return [kids.length ? cloneElement(original, changed, ...kids) : cloneElement(original, { ...changed, children: void 0 })];
190
+ });
191
+ }
192
+ function hasRuntimeValues(children, skipExcluded = false) {
193
+ let run = [];
194
+ const flush = () => {
195
+ const hit = run.filter((p) => String(p).trim() !== "").length > 1;
196
+ run = [];
197
+ return hit;
198
+ };
199
+ for (const c of [...inRun(children), null]) {
200
+ if (typeof c === "string" || typeof c === "number" || typeof c === "bigint") {
201
+ run.push(c);
202
+ continue;
203
+ }
204
+ if (flush()) return true;
205
+ if (!isValidElement(c)) continue;
206
+ const node = c.type === DontTranslate ? DontTranslate(c.props) : c;
207
+ if (typeof node.type !== "string") continue;
208
+ const props = node.props;
209
+ if (skipExcluded && opaqueInPhrase(node.type, props)) continue;
210
+ if (hasRuntimeValues(props.children, skipExcluded)) return true;
211
+ }
212
+ return false;
213
+ }
214
+ function withoutFragments(node) {
215
+ if (read && isContext(node)) return withoutFragments(read(node));
216
+ if (Array.isArray(node)) return node.map(withoutFragments);
217
+ if (isIterable(node)) return Array.from(node, withoutFragments);
218
+ if (isValidElement(node) && node.type === Fragment) return [withoutFragments(node.props.children)];
219
+ return node;
220
+ }
221
+ function inRun(level) {
222
+ return Children.toArray(withoutFragments(level));
223
+ }
224
+ function opaqueInPhrase(tag, props) {
225
+ return NON_TRANSLATABLE_ELEMENTS.includes(tag) || isTranslationExcluded(attributeReader(tag, attrsOf(props)));
226
+ }
227
+ function attributeReader(tagName, attrs) {
228
+ const valueOf = (name) => Object.entries(attrs ?? {}).find(([key]) => key === name)?.[1];
229
+ return { tagName, getAttribute: (name) => valueOf(name) ?? null, hasAttribute: (name) => valueOf(name) !== void 0 };
230
+ }
231
+ function withNodeParams(children, given) {
232
+ const nodes = {};
233
+ const rest = {};
234
+ const props = /* @__PURE__ */ Object.create(null);
235
+ for (const [name, param] of Object.entries(given)) {
236
+ const value = read && isUsable(param) ? read(param) : param;
237
+ if (value === null || value === void 0) rest[name] = "";
238
+ else if (typeof value === "bigint") rest[name] = String(value);
239
+ else if (isParamValue(value)) rest[name] = value;
240
+ else {
241
+ nodes[name] = isIterable(value) && !Array.isArray(value) ? itemsOf(value) : value;
242
+ props[`%${name}%`] = props[`{${name}}`] = value;
243
+ }
244
+ }
245
+ const names = Object.keys(nodes);
246
+ if (!names.length) return { children, params: rest };
247
+ const alternatives = names.map(literally).join("|");
248
+ const split = new RegExp(`%(${alternatives})%|(%[A-Za-z_][A-Za-z0-9_]*%)|\\{(${alternatives})\\}`);
249
+ const inText = /* @__PURE__ */ new Set();
250
+ const ownProps = (element) => {
251
+ let out;
252
+ for (const [prop, value] of Object.entries(element)) {
253
+ if (prop === "children" || typeof value !== "string") continue;
254
+ if (value in props) (out ??= {})[prop] = props[value];
255
+ else {
256
+ for (const match of value.matchAll(new RegExp(split.source, "g"))) {
257
+ const name = match[1] ?? match[3];
258
+ if (name !== void 0) inText.add(name);
259
+ }
260
+ }
261
+ }
262
+ return out;
263
+ };
264
+ const visit = (node) => {
265
+ if (typeof node === "string") {
266
+ const parts = node.split(new RegExp(split.source, "g"));
267
+ const out = [];
268
+ let text = "";
269
+ for (let i = 0; i < parts.length; i += 4) {
270
+ text += parts[i] + (parts[i + 2] ?? "");
271
+ const name = parts[i + 1] ?? parts[i + 3];
272
+ if (name === void 0) continue;
273
+ if (text) out.push(text);
274
+ text = "";
275
+ out.push(createElement(Fragment, { key: i + 1 }, nodes[name]));
276
+ }
277
+ if (out.length === 0) return node;
278
+ if (text) out.push(text);
279
+ return out;
280
+ }
281
+ if (Array.isArray(node)) {
282
+ const kids2 = node.map(visit);
283
+ return kids2.some((kid, i) => kid !== node[i]) ? kids2 : node;
284
+ }
285
+ if (!isValidElement(node)) return node;
286
+ if (typeof node.type !== "string" && node.type !== Fragment && node.type !== DontTranslate) return node;
287
+ const attrs = typeof node.type === "string" ? ownProps(node.props) : void 0;
288
+ const own = node.props.children;
289
+ if (own === void 0) return attrs ? cloneElement(node, attrs) : node;
290
+ const kids = Array.isArray(own) ? own.map(visit) : [visit(own)];
291
+ const same = Array.isArray(own) ? kids.every((kid, i) => kid === own[i]) : kids[0] === own;
292
+ return same && !attrs ? node : cloneElement(node, attrs, ...kids);
293
+ };
294
+ const rendered = visit(children);
295
+ for (const name of inText) rest[name] = String(props[`%${name}%`]);
296
+ return { children: rendered, params: rest };
297
+ }
298
+ var BlockCategory = createContext(void 0);
299
+ function useUnitCategory(named, namedPrevious) {
300
+ const block = useContext(BlockCategory);
301
+ const outerCategory = block?.category;
302
+ const outerPrevious = block?.previousCategory;
303
+ return useMemo(() => {
304
+ if (named !== void 0 || !block) return { category: named ?? "", previousCategory: namedPrevious };
305
+ return { category: block.category, previousCategory: namedPrevious ?? block.previousCategory };
306
+ }, [named, namedPrevious, block !== void 0, outerCategory, outerPrevious]);
307
+ }
308
+
309
+ // src/components/Translate.tsx
26
310
  function Translate({
27
- category = "",
311
+ category: named,
312
+ previousCategory: namedPrevious,
28
313
  custom_id = "",
29
314
  label = "",
30
- params,
315
+ params: given,
31
316
  tag = "translate",
32
317
  className,
33
- children
318
+ children: content,
319
+ "data-ls-unnamed": unmarked
34
320
  }) {
321
+ const unit = useUnitCategory(named, namedPrevious);
322
+ const { category, previousCategory } = unit;
323
+ const { children, params } = given ? withNodeParams(content, given) : { children: content, params: given };
324
+ const t = useT();
35
325
  const hostRef = useRef(null);
36
326
  const instanceRef = useRef(void 0);
327
+ const mapped = toBlockNodes(children);
328
+ const unnamedValues = unmarked !== void 0 || hasRuntimeValues(children);
329
+ const options = {
330
+ category,
331
+ ...previousCategory === void 0 || previousCategory === null ? {} : { previousCategory },
332
+ params,
333
+ label,
334
+ ...custom_id ? { id: custom_id } : {},
335
+ ...unnamedValues ? { register: false } : {}
336
+ };
337
+ const inSeedScope = useSeedScopeRunner();
338
+ const rendered = mapped.ok ? inSeedScope(() => renderBlock(mapped.nodes, options)) : null;
339
+ const scope = currentRequestScope();
340
+ const register = (host) => {
341
+ if (!mapped.ok || !rendered || rendered.shape === "empty") return;
342
+ if (unnamedValues) warnUnnamed(unmarked !== void 0);
343
+ void registerBlock(mapped.nodes, { ...options, host });
344
+ };
345
+ if (scope) {
346
+ register();
347
+ if (!mapped.ok) warnUnrenderedBlock(mapped.reason);
348
+ }
349
+ const blockKey = rendered ? `${category}\0${custom_id}\0${rendered.customId}` : null;
350
+ useEffect(() => {
351
+ register(hostRef.current ?? void 0);
352
+ }, [t, blockKey, tag]);
37
353
  useEffect(() => {
38
354
  const host = hostRef.current;
39
- if (!host) return;
40
- const instance = new Translate$1(host, { category, custom_id, label, params });
355
+ if (mapped.ok || !host) return;
356
+ if (unnamedValues) warnUnnamed(unmarked !== void 0);
357
+ const instance = new Translate$1(host, {
358
+ category,
359
+ ...previousCategory === void 0 || previousCategory === null ? {} : { previousCategory },
360
+ custom_id,
361
+ label,
362
+ params,
363
+ ...unnamedValues ? { register: false } : {}
364
+ });
41
365
  instanceRef.current = instance;
42
366
  return () => {
43
367
  instance.destroy();
44
368
  instanceRef.current = void 0;
45
369
  };
46
- }, [category, custom_id, label]);
370
+ }, [mapped.ok, category, previousCategory, custom_id, label, tag]);
47
371
  useEffect(() => {
48
372
  instanceRef.current?.setParams(params);
49
373
  });
50
- return createElement(tag, { ref: hostRef, className }, children);
374
+ if (mapped.ok && rendered) {
375
+ return createElement(
376
+ tag,
377
+ { ref: hostRef, className, ...rendered.hostAttrs },
378
+ ...toReactNodes(rendered.nodes, mapped.elements, mapped.nested),
379
+ ...mapped.portals
380
+ );
381
+ }
382
+ return createElement(
383
+ tag,
384
+ { ref: hostRef, className, ...custom_id ? { [CONTENT_BLOCK_MARKER_ATTR]: custom_id } : {} },
385
+ createElement(
386
+ BlockCategory.Provider,
387
+ { value: unit },
388
+ ...children !== content && Array.isArray(children) ? children : [children]
389
+ )
390
+ );
51
391
  }
52
- function Phrase({ category = "", params = {}, tag = "span", className, children }) {
392
+ function warnUnnamed(unmarked) {
393
+ warnUnregistered(
394
+ unmarked ? "a value the build transform left as written: inside MathML or SVG, <script> or <style>, or an element that holds text only" : "a value the build transform did not name: it is not enabled (langsys-js-react/vite, /babel or /next), or the value is a conditional, which it leaves as written"
395
+ );
396
+ }
397
+ function Phrase({
398
+ category: named,
399
+ previousCategory: namedPrevious,
400
+ params: given = {},
401
+ tag = "span",
402
+ className,
403
+ children: content,
404
+ "data-ls-unnamed": unmarked
405
+ }) {
406
+ const inherited = useUnitCategory(named, namedPrevious);
407
+ const { category, previousCategory } = inherited;
408
+ const { children, params } = withNodeParams(content, given ?? {});
409
+ const t = useT();
53
410
  const hostRef = useRef(null);
54
411
  const instanceRef = useRef(void 0);
412
+ const mapped = toBlockNodes(children);
413
+ const unit = mapped.ok ? [{ tag, attrs: { [PHRASE_MARKER_ATTR]: "" }, children: mapped.nodes }] : null;
414
+ const unnamedValues = unmarked !== void 0 || hasRuntimeValues(children, true);
415
+ const moved = previousCategory === void 0 || previousCategory === null ? {} : { previousCategory };
416
+ const options = { category, ...moved, params, ...unnamedValues ? { register: false } : {} };
417
+ const inSeedScope = useSeedScopeRunner();
418
+ const rendered = unit ? inSeedScope(() => renderBlock(unit, options)) : null;
419
+ const scope = currentRequestScope();
420
+ const register = (host2) => {
421
+ if (!unit) return;
422
+ if (unnamedValues) warnUnnamed2(unmarked !== void 0);
423
+ void registerBlock(unit, { ...options, host: host2 });
424
+ };
425
+ if (scope) {
426
+ register();
427
+ if (!mapped.ok) warnUnrenderedBlock(mapped.reason);
428
+ }
55
429
  useEffect(() => {
56
- const host = hostRef.current;
57
- if (!host) return;
58
- const instance = new Phrase$1(host, { category, params });
430
+ register(hostRef.current ?? void 0);
431
+ }, [t, category, rendered ? JSON.stringify(unit) : null]);
432
+ useEffect(() => {
433
+ const host2 = hostRef.current;
434
+ if (mapped.ok || !host2) return;
435
+ if (unnamedValues) warnUnnamed2(unmarked !== void 0);
436
+ const instance = new Phrase$1(host2, {
437
+ category,
438
+ ...moved,
439
+ params,
440
+ ...unnamedValues ? { register: false } : {}
441
+ });
59
442
  instanceRef.current = instance;
60
443
  return () => {
61
444
  instance.destroy();
62
445
  instanceRef.current = void 0;
63
446
  };
64
- }, [category]);
447
+ }, [mapped.ok, category, previousCategory, tag]);
65
448
  useEffect(() => {
66
449
  instanceRef.current?.setParams(params);
67
450
  });
68
- return createElement(tag, { ref: hostRef, className, [PHRASE_MARKER_ATTR]: "" }, children);
69
- }
70
- function DontTranslate({ tag = "span", className, children }) {
451
+ const host = rendered?.nodes[0];
452
+ if (mapped.ok && host && "tag" in host) {
453
+ const { class: _class, ...hostAttrs } = host.attrs;
454
+ return createElement(
455
+ tag,
456
+ { ref: hostRef, className, ...hostAttrs },
457
+ ...toReactNodes(host.children, [createElement(tag), ...mapped.elements], [[], ...mapped.nested]),
458
+ ...mapped.portals
459
+ );
460
+ }
71
461
  return createElement(
72
462
  tag,
73
- { translate: "no", "data-ls-dont-translate": "", className },
74
- children
463
+ { ref: hostRef, className, [PHRASE_MARKER_ATTR]: "" },
464
+ createElement(
465
+ BlockCategory.Provider,
466
+ { value: inherited },
467
+ ...children !== content && Array.isArray(children) ? children : [children]
468
+ )
469
+ );
470
+ }
471
+ function warnUnnamed2(unmarked) {
472
+ warnUnregistered(
473
+ unmarked ? "a value the build transform left as written in a phrase whose values are all marked: in a translated <svg>, or an element that holds text only" : "a value the build transform did not name: it is not enabled (langsys-js-react/vite, /babel or /next), or the value is a conditional, which it leaves as written"
75
474
  );
76
475
  }
77
476
 
78
- // src/index.ts
79
- var LangsysAppReact = class {
80
- /** Initialize Langsys. Pass a `Signal<string>` (from `createLocaleStore`) as `UserLocaleStore`. */
81
- init(config) {
82
- return LangsysApp$1.init(config);
83
- }
84
- get Translations() {
85
- return LangsysApp$1.Translations;
86
- }
87
- get translationsLoadingPromise() {
88
- return LangsysApp$1.translationsLoadingPromise;
89
- }
90
- /** Current translation function. Reads fresh state on every call (not reactive on its own — use `useT()` in components). */
91
- get t() {
92
- return LangsysApp$1.t;
93
- }
94
- get debug() {
95
- return LangsysApp$1.debug;
96
- }
97
- refresh() {
98
- return LangsysApp$1.refresh();
99
- }
100
- getCountries(inLocale) {
101
- return LangsysApp$1.getCountries(inLocale);
102
- }
103
- getCountryName(forCountryCode, inLocale) {
104
- return LangsysApp$1.getCountryName(forCountryCode, inLocale);
105
- }
106
- getCurrencies(inLocale) {
107
- return LangsysApp$1.getCurrencies(inLocale);
108
- }
109
- getCurrencyName(forCurrencyCode, inLocale) {
110
- return LangsysApp$1.getCurrencyName(forCurrencyCode, inLocale);
111
- }
112
- getDialCodes(inLocale) {
113
- return LangsysApp$1.getDialCodes(inLocale);
114
- }
115
- getLocales(inLocale) {
116
- return LangsysApp$1.getLocales(inLocale);
117
- }
118
- getLocalesFlat(inLocale) {
119
- return LangsysApp$1.getLocalesFlat(inLocale);
120
- }
121
- getLocalesData(inLocale, forceRefresh) {
122
- return LangsysApp$1.getLocalesData(inLocale, forceRefresh);
123
- }
124
- getLocalesFormat(format = "", inLocale) {
125
- return LangsysApp$1.getLocalesFormat(format, inLocale);
126
- }
127
- getLocaleName(forLocale, shortName, inLocale) {
128
- return LangsysApp$1.getLocaleName(forLocale, shortName, inLocale);
129
- }
130
- getLocaleNameWithLookup(forLocale, shortName, inLocale) {
131
- return LangsysApp$1.getLocaleNameWithLookup(forLocale, shortName, inLocale);
132
- }
133
- /** @deprecated use `getLocaleNameWithLookup` or `getLocaleName` */
134
- getLanguageName(forLocale, shortName, inLocale) {
135
- return LangsysApp$1.getLanguageName(forLocale, shortName, inLocale);
136
- }
137
- detectPreferredLocale(acceptLanguageHeader, supportedLocales) {
138
- return LangsysApp$1.detectPreferredLocale(acceptLanguageHeader, supportedLocales);
139
- }
140
- };
141
- var LangsysApp = new LangsysAppReact();
142
-
143
- export { DontTranslate, LangsysApp, Phrase, Translate, createLocaleStore, useCurrentLocale, useLocaleStore, useSignal, useT, useTranslations };
477
+ export { DontTranslate, LangsysApp2 as LangsysApp, LangsysProvider, Phrase, Translate, createLocaleStore, useCurrentLocale, useLocaleStore, useNotifyNavigation, useRenderServerMessage, useSignal, useT, useTranslations, useWriteEnabled };
144
478
  //# sourceMappingURL=index.mjs.map
145
479
  //# sourceMappingURL=index.mjs.map