@thekatze/locolize-react 0.0.0-stage → 0.1.0-test.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.
@@ -0,0 +1,11 @@
1
+ import { Snapshot } from "@thekatze/locolize-core/internal";
2
+ import { Locolize } from "@thekatze/locolize-core";
3
+ //#region src/context.d.ts
4
+ export type LocolizeContextValue = {
5
+ runtime: Locolize;
6
+ /** Changes on every runtime change, so consumers re-render. */
7
+ snapshot: Snapshot;
8
+ };
9
+ export declare const LocolizeContext: import("react").Context<LocolizeContextValue | null>;
10
+ export declare function useLocolize(): LocolizeContextValue;
11
+ //#endregion
@@ -0,0 +1,10 @@
1
+ import { createContext, use } from "react";
2
+ //#region src/context.ts
3
+ const LocolizeContext = createContext(null);
4
+ function useLocolize() {
5
+ const context = use(LocolizeContext);
6
+ if (!context) throw new Error("useI18n() and <Message> must be used inside <LocolizeProvider>.");
7
+ return context;
8
+ }
9
+ //#endregion
10
+ export { LocolizeContext, useLocolize };
@@ -0,0 +1,3 @@
1
+ import { MessageComponent, MessageProps } from "./types.js";
2
+ import { LocolizeProvider, Message, useI18n } from "./react.js";
3
+ export { LocolizeProvider, Message, type MessageComponent, type MessageProps, useI18n };
package/dist/index.js ADDED
@@ -0,0 +1 @@
1
+ export { LocolizeProvider, Message, useI18n } from "./react.js";
@@ -0,0 +1,4 @@
1
+ import { Mode } from "./types.js";
2
+ //#region src/inline.d.ts
3
+ export declare const mode: Mode;
4
+ //#endregion
package/dist/inline.js ADDED
@@ -0,0 +1,38 @@
1
+ import { useLocolize } from "./context.js";
2
+ import { jsx } from "react/jsx-runtime";
3
+ import { isInlineRuntime } from "@thekatze/locolize-core/internal";
4
+ //#region src/inline.tsx
5
+ function InspectedMessage({ message, data }) {
6
+ const { runtime } = useLocolize();
7
+ if (!isInlineRuntime(runtime)) return message(data);
8
+ const { text, edited } = runtime.textOf(message, data);
9
+ return /* @__PURE__ */ jsx("span", {
10
+ "data-locolize-message": "",
11
+ "data-locolize-edited": edited ? "" : void 0,
12
+ ref: (element) => element ? runtime.track(element, {
13
+ message,
14
+ data
15
+ }) : void 0,
16
+ children: text
17
+ });
18
+ }
19
+ /** Loads and mounts the overlay. The cleanup also cancels a pending load. */
20
+ function mount(runtime) {
21
+ if (!isInlineRuntime(runtime)) return () => {};
22
+ let dispose;
23
+ let cancelled = false;
24
+ (async () => {
25
+ const { mountOverlay } = await import("@thekatze/locolize-overlay");
26
+ if (!cancelled) dispose = mountOverlay(runtime);
27
+ })();
28
+ return () => {
29
+ cancelled = true;
30
+ dispose?.();
31
+ };
32
+ }
33
+ const mode = {
34
+ Message: InspectedMessage,
35
+ mount
36
+ };
37
+ //#endregion
38
+ export { mode };
@@ -0,0 +1,4 @@
1
+ import { Mode } from "./types.js";
2
+ //#region src/plain.d.ts
3
+ export declare const mode: Mode;
4
+ //#endregion
package/dist/plain.js ADDED
@@ -0,0 +1,10 @@
1
+ //#region src/plain.ts
2
+ function PlainMessage({ message, data }) {
3
+ return message(data);
4
+ }
5
+ const mode = {
6
+ Message: PlainMessage,
7
+ mount: void 0
8
+ };
9
+ //#endregion
10
+ export { mode };
@@ -0,0 +1,21 @@
1
+ import { MessageProps } from "./types.js";
2
+ import { PropsWithChildren, ReactNode } from "react";
3
+ import { AnyMessage, Locolize, TranslateFn } from "@thekatze/locolize-core";
4
+ //#region src/react.d.ts
5
+ export declare function LocolizeProvider({ locolize, children }: PropsWithChildren<{
6
+ /** From `createLocolize()`, created once at module level. */
7
+ locolize: Locolize;
8
+ }>): ReactNode;
9
+ /**
10
+ * Renders a message. Prefer it over `t()` for text on the page: with inline
11
+ * editing, the overlay can then point at exactly this message.
12
+ */
13
+ export declare function Message<F extends AnyMessage>(props: MessageProps<F>): ReactNode;
14
+ /** `t()` is for strings outside of markup, like `placeholder` or `title`. */
15
+ export declare function useI18n(): {
16
+ t: TranslateFn;
17
+ locale: string;
18
+ locales: readonly string[];
19
+ setLocale: (locale: string) => Promise<void>;
20
+ };
21
+ //#endregion
package/dist/react.js ADDED
@@ -0,0 +1,32 @@
1
+ import { LocolizeContext, useLocolize } from "./context.js";
2
+ import { useEffect, useMemo, useSyncExternalStore } from "react";
3
+ import { mode } from "#mode";
4
+ import { jsx } from "react/jsx-runtime";
5
+ //#region src/react.tsx
6
+ function LocolizeProvider({ locolize, children }) {
7
+ const snapshot = useSyncExternalStore(locolize.subscribe, locolize.getSnapshot);
8
+ useEffect(() => mode.mount?.(locolize), [locolize]);
9
+ const value = useMemo(() => ({
10
+ runtime: locolize,
11
+ snapshot
12
+ }), [locolize, snapshot]);
13
+ return /* @__PURE__ */ jsx(LocolizeContext, {
14
+ value,
15
+ children
16
+ });
17
+ }
18
+ function Message(props) {
19
+ return /* @__PURE__ */ jsx(mode.Message, { ...props });
20
+ }
21
+ /** `t()` is for strings outside of markup, like `placeholder` or `title`. */
22
+ function useI18n() {
23
+ const { runtime, snapshot } = useLocolize();
24
+ return useMemo(() => ({
25
+ t: runtime.t,
26
+ locale: snapshot.locale,
27
+ locales: runtime.config.locales,
28
+ setLocale: runtime.setLocale
29
+ }), [runtime, snapshot]);
30
+ }
31
+ //#endregion
32
+ export { LocolizeProvider, Message, useI18n };
@@ -0,0 +1,30 @@
1
+ import { ReactNode } from "react";
2
+ import { AnyMessage, IsAny, MessageData } from "@thekatze/locolize-core/internal";
3
+ import { Locolize } from "@thekatze/locolize-core";
4
+ //#region src/types.d.ts
5
+ export type MessageDataProp<D> = IsAny<D> extends true ? {
6
+ data?: unknown;
7
+ } : [D] extends [undefined] ? {
8
+ data?: never;
9
+ } : undefined extends D ? {
10
+ data?: Exclude<D, undefined>;
11
+ } : {} extends D ? {
12
+ data?: D;
13
+ } : {
14
+ data: D;
15
+ };
16
+ export type MessageProps<F extends AnyMessage> = {
17
+ message: F;
18
+ } & MessageDataProp<MessageData<F>>;
19
+ export type MessageComponent = <F extends AnyMessage>(props: MessageProps<F>) => ReactNode;
20
+ export type MessageImplProps = {
21
+ message: AnyMessage;
22
+ data?: unknown;
23
+ };
24
+ /** What `#mode` provides: the plain build or the inline editing one. */
25
+ export interface Mode {
26
+ Message: MessageComponent;
27
+ /** Mounts the overlay; returns the cleanup. */
28
+ mount: ((locolize: Locolize) => () => void) | undefined;
29
+ }
30
+ //#endregion
package/dist/types.js ADDED
File without changes
package/package.json CHANGED
@@ -1,6 +1,37 @@
1
1
  {
2
2
  "name": "@thekatze/locolize-react",
3
- "version": "0.0.0-stage",
4
- "stub": true,
5
- "description": "Temporary package placeholder for staged publishing"
6
- }
3
+ "version": "0.1.0-test.0",
4
+ "description": "React 19 bindings for Locolize: LocolizeProvider, useI18n and <Message>.",
5
+ "repository": {
6
+ "type": "git",
7
+ "url": "git+https://github.com/enXess-ag/locolize-js.git",
8
+ "directory": "packages/react"
9
+ },
10
+ "type": "module",
11
+ "sideEffects": false,
12
+ "files": [
13
+ "dist"
14
+ ],
15
+ "exports": {
16
+ ".": {
17
+ "types": "./dist/index.d.ts",
18
+ "default": "./dist/index.js"
19
+ }
20
+ },
21
+ "imports": {
22
+ "#mode": {
23
+ "locolize-inline": "./dist/inline.js",
24
+ "default": "./dist/plain.js"
25
+ }
26
+ },
27
+ "publishConfig": {
28
+ "access": "public"
29
+ },
30
+ "dependencies": {
31
+ "@thekatze/locolize-core": "0.1.0-test.0",
32
+ "@thekatze/locolize-overlay": "0.1.0-test.0"
33
+ },
34
+ "peerDependencies": {
35
+ "react": "^19.0.0"
36
+ }
37
+ }
package/README.md DELETED
@@ -1,3 +0,0 @@
1
- # Temporary Holding Version
2
-
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.