vite-plugin-react-shopify 2.1.1 → 2.2.1
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.js +20 -1
- package/dist/runtime/index.d.ts +16 -13
- package/dist/runtime/index.js +86 -22
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -590,6 +590,21 @@ function pathToFileURL(filePath) {
|
|
|
590
590
|
return "file://" + absPath;
|
|
591
591
|
}
|
|
592
592
|
var log6 = logger("ssg:renderer");
|
|
593
|
+
var DEFAULT_LIQUID_FILTERS = {
|
|
594
|
+
textarea: " | newline_to_br",
|
|
595
|
+
image_picker: " | img_url: 'master'"
|
|
596
|
+
};
|
|
597
|
+
function buildLiquidFilterMap(settings, prefix) {
|
|
598
|
+
const map = {};
|
|
599
|
+
if (!settings) return map;
|
|
600
|
+
for (const s of settings) {
|
|
601
|
+
const filter = DEFAULT_LIQUID_FILTERS[s.type];
|
|
602
|
+
if (filter) {
|
|
603
|
+
map[`${prefix}${s.id}`] = filter;
|
|
604
|
+
}
|
|
605
|
+
}
|
|
606
|
+
return map;
|
|
607
|
+
}
|
|
593
608
|
function renderEntry(tmpFile, entry, projectRoot) {
|
|
594
609
|
return import(pathToFileURL(tmpFile)).then((mod) => {
|
|
595
610
|
const Component = mod.default;
|
|
@@ -612,11 +627,15 @@ function renderEntry(tmpFile, entry, projectRoot) {
|
|
|
612
627
|
return null;
|
|
613
628
|
}
|
|
614
629
|
globalThis.__shopify_ssg_target = entry.targetType;
|
|
630
|
+
const prefix = entry.targetType === "block" ? "block.settings." : "section.settings.";
|
|
631
|
+
const filterMap = buildLiquidFilterMap(shopifyMeta?.settings, prefix);
|
|
632
|
+
globalThis.__shopify_ssg_liquid_filters = filterMap;
|
|
615
633
|
const trackedExpressions = /* @__PURE__ */ new Set();
|
|
616
634
|
globalThis.__shopify_ssg_liquid_track = trackedExpressions;
|
|
617
635
|
const element = createElement(Component);
|
|
618
636
|
let html = renderToStaticMarkup(element);
|
|
619
637
|
delete globalThis.__shopify_ssg_liquid_track;
|
|
638
|
+
delete globalThis.__shopify_ssg_liquid_filters;
|
|
620
639
|
html = normalizeVoidElements(html);
|
|
621
640
|
html = normalizeStyleAttributes(html);
|
|
622
641
|
html = unwrapHtmlEntities(html);
|
|
@@ -992,7 +1011,7 @@ function shopifySSG(options) {
|
|
|
992
1011
|
if (id === "\0vite-plugin-shopify:runtime") {
|
|
993
1012
|
const exports = [
|
|
994
1013
|
`export { LiquidDataProvider, LiquidDataContext } from 'vite-plugin-shopify/runtime'`,
|
|
995
|
-
`export {
|
|
1014
|
+
`export { useLiquidValue, useLiquidValues, useSectionSettings, useBlockSettings, useSnippetParams, useBlockParams } from 'vite-plugin-shopify/runtime'`
|
|
996
1015
|
];
|
|
997
1016
|
return exports.join("\n");
|
|
998
1017
|
}
|
package/dist/runtime/index.d.ts
CHANGED
|
@@ -1,13 +1,21 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
|
|
3
|
-
declare function
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
3
|
+
declare function parseLiquidBoolean(value: string | boolean | undefined | null): boolean;
|
|
4
|
+
declare function parseLiquidNumber(value: string | number | undefined | null, defaultVal?: number): number;
|
|
5
|
+
type LiquidTypeMode = "string" | "number" | "boolean";
|
|
6
|
+
type Setter<T> = (val: T | ((prev: T) => T)) => void;
|
|
7
|
+
type ValueForMode<M extends LiquidTypeMode | undefined> = M extends "number" ? number : M extends "boolean" ? boolean : string | undefined;
|
|
8
|
+
declare function useLiquidValue(expr: string): [string | undefined, Setter<string | undefined>];
|
|
9
|
+
declare function useLiquidValue(expr: string, type: "string"): [string | undefined, Setter<string | undefined>];
|
|
10
|
+
declare function useLiquidValue(expr: string, type: "number"): [number, Setter<number>];
|
|
11
|
+
declare function useLiquidValue(expr: string, type: "boolean"): [boolean, Setter<boolean>];
|
|
12
|
+
type TypeModes<T extends Record<string, string>> = Partial<{
|
|
13
|
+
[K in keyof T & string]: LiquidTypeMode;
|
|
14
|
+
}>;
|
|
15
|
+
type InferValues<T extends Record<string, string>, Types extends TypeModes<T>> = {
|
|
16
|
+
[K in keyof T & string]: ValueForMode<Types[K]>;
|
|
10
17
|
};
|
|
18
|
+
declare function useLiquidValues<T extends Record<string, string>, const Types extends TypeModes<T> = {}>(map: T, types?: Types): InferValues<T, Types>;
|
|
11
19
|
declare function useSectionSettings(key: string): {
|
|
12
20
|
value: string | undefined;
|
|
13
21
|
};
|
|
@@ -21,12 +29,7 @@ declare function useBlockParams(key: string): {
|
|
|
21
29
|
value: string | undefined;
|
|
22
30
|
};
|
|
23
31
|
|
|
24
|
-
/** SSR-safe boolean parser: treats Liquid expression strings as truthy, real booleans as-is */
|
|
25
|
-
declare function parseLiquidBoolean(value: string | boolean | undefined | null): boolean;
|
|
26
|
-
/** SSR-safe number parser: returns defaultVal for unparseable SSR placeholders */
|
|
27
|
-
declare function parseLiquidNumber(value: string | number | undefined | null, defaultVal?: number): number;
|
|
28
|
-
|
|
29
32
|
declare const LiquidDataContext: react.Context<Record<string, any>>;
|
|
30
33
|
declare const LiquidDataProvider: react.Provider<Record<string, any>>;
|
|
31
34
|
|
|
32
|
-
export { LiquidDataContext, LiquidDataProvider, parseLiquidBoolean, parseLiquidNumber, useBlockParams, useBlockSettings,
|
|
35
|
+
export { LiquidDataContext, LiquidDataProvider, type LiquidTypeMode, parseLiquidBoolean, parseLiquidNumber, useBlockParams, useBlockSettings, useLiquidValue, useLiquidValues, useSectionSettings, useSnippetParams };
|
package/dist/runtime/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// src/runtime/hooks.ts
|
|
2
|
-
import { useContext } from "react";
|
|
2
|
+
import { useContext, useEffect, useState } from "react";
|
|
3
3
|
|
|
4
4
|
// src/runtime/provider.ts
|
|
5
5
|
import { createContext } from "react";
|
|
@@ -7,46 +7,40 @@ var LiquidDataContext = createContext({});
|
|
|
7
7
|
var LiquidDataProvider = LiquidDataContext.Provider;
|
|
8
8
|
|
|
9
9
|
// src/runtime/hooks.ts
|
|
10
|
-
function
|
|
10
|
+
function getLiquidFilter(expr) {
|
|
11
|
+
const filterMap = globalThis.__shopify_ssg_liquid_filters;
|
|
12
|
+
return filterMap?.[expr] ?? "";
|
|
13
|
+
}
|
|
14
|
+
function useLiquidRaw(expr) {
|
|
11
15
|
const data = useContext(LiquidDataContext);
|
|
12
16
|
if (typeof globalThis.document === "undefined") {
|
|
13
17
|
const tracker = globalThis.__shopify_ssg_liquid_track;
|
|
14
18
|
if (tracker) tracker.add(expr);
|
|
15
|
-
|
|
19
|
+
const filter = getLiquidFilter(expr);
|
|
20
|
+
return `{{ ${expr}${filter} }}`;
|
|
16
21
|
}
|
|
17
22
|
if (Object.prototype.hasOwnProperty.call(data, expr)) {
|
|
18
|
-
return
|
|
23
|
+
return data[expr];
|
|
19
24
|
}
|
|
20
|
-
return
|
|
25
|
+
return void 0;
|
|
21
26
|
}
|
|
22
|
-
function
|
|
27
|
+
function useLiquidRawValues(map) {
|
|
23
28
|
const data = useContext(LiquidDataContext);
|
|
24
29
|
if (typeof globalThis.document === "undefined") {
|
|
25
30
|
const tracker = globalThis.__shopify_ssg_liquid_track;
|
|
26
31
|
const values2 = {};
|
|
27
32
|
for (const [key, expr] of Object.entries(map)) {
|
|
28
33
|
if (tracker) tracker.add(expr);
|
|
29
|
-
|
|
34
|
+
const filter = getLiquidFilter(expr);
|
|
35
|
+
values2[key] = `{{ ${expr}${filter} }}`;
|
|
30
36
|
}
|
|
31
|
-
return
|
|
37
|
+
return values2;
|
|
32
38
|
}
|
|
33
39
|
const values = {};
|
|
34
40
|
for (const [key, expr] of Object.entries(map)) {
|
|
35
41
|
values[key] = Object.prototype.hasOwnProperty.call(data, expr) ? data[expr] : void 0;
|
|
36
42
|
}
|
|
37
|
-
return
|
|
38
|
-
}
|
|
39
|
-
function useSectionSettings(key) {
|
|
40
|
-
return useLiquid(`section.settings.${key}`);
|
|
41
|
-
}
|
|
42
|
-
function useBlockSettings(key) {
|
|
43
|
-
return useLiquid(`block.settings.${key}`);
|
|
44
|
-
}
|
|
45
|
-
function useSnippetParams(key) {
|
|
46
|
-
return useLiquid(key);
|
|
47
|
-
}
|
|
48
|
-
function useBlockParams(key) {
|
|
49
|
-
return useLiquid(key);
|
|
43
|
+
return values;
|
|
50
44
|
}
|
|
51
45
|
function parseLiquidBoolean(value) {
|
|
52
46
|
if (typeof value === "boolean") return value;
|
|
@@ -59,6 +53,76 @@ function parseLiquidNumber(value, defaultVal = 0) {
|
|
|
59
53
|
const num = Number(value);
|
|
60
54
|
return Number.isNaN(num) ? defaultVal : num;
|
|
61
55
|
}
|
|
56
|
+
function useLiquidValue(expr, type = "string") {
|
|
57
|
+
const raw = useLiquidRaw(expr);
|
|
58
|
+
const isSSR = typeof globalThis.document === "undefined";
|
|
59
|
+
let initialVal;
|
|
60
|
+
if (type === "boolean") {
|
|
61
|
+
initialVal = false;
|
|
62
|
+
} else if (type === "number") {
|
|
63
|
+
initialVal = isSSR ? raw : parseLiquidNumber(raw, 0);
|
|
64
|
+
} else {
|
|
65
|
+
initialVal = raw;
|
|
66
|
+
}
|
|
67
|
+
const [val, setVal] = useState(initialVal);
|
|
68
|
+
useEffect(() => {
|
|
69
|
+
if (type === "number") setVal(parseLiquidNumber(raw, 0));
|
|
70
|
+
else if (type === "boolean") setVal(parseLiquidBoolean(raw));
|
|
71
|
+
else setVal(raw);
|
|
72
|
+
}, [raw]);
|
|
73
|
+
return [val, setVal];
|
|
74
|
+
}
|
|
75
|
+
function useLiquidValues(map, types) {
|
|
76
|
+
const raw = useLiquidRawValues(map);
|
|
77
|
+
const keys = Object.keys(map);
|
|
78
|
+
const rawDep = keys.map((k) => raw[k]).join("\0");
|
|
79
|
+
const isSSR = typeof globalThis.document === "undefined";
|
|
80
|
+
const [parsed, setParsed] = useState(() => {
|
|
81
|
+
const vals = {};
|
|
82
|
+
for (const k of keys) {
|
|
83
|
+
const mode = types?.[k] ?? "string";
|
|
84
|
+
if (mode === "boolean") {
|
|
85
|
+
vals[k] = false;
|
|
86
|
+
} else if (mode === "number") {
|
|
87
|
+
vals[k] = isSSR ? raw[k] : parseLiquidNumber(raw[k], 0);
|
|
88
|
+
} else {
|
|
89
|
+
vals[k] = raw[k];
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
return vals;
|
|
93
|
+
});
|
|
94
|
+
useEffect(() => {
|
|
95
|
+
setParsed((prev) => {
|
|
96
|
+
let changed = false;
|
|
97
|
+
const next = { ...prev };
|
|
98
|
+
for (const k of keys) {
|
|
99
|
+
const mode = types?.[k] ?? "string";
|
|
100
|
+
let v;
|
|
101
|
+
if (mode === "number") v = parseLiquidNumber(raw[k], 0);
|
|
102
|
+
else if (mode === "boolean") v = parseLiquidBoolean(raw[k]);
|
|
103
|
+
else v = raw[k];
|
|
104
|
+
if (v !== prev[k]) {
|
|
105
|
+
next[k] = v;
|
|
106
|
+
changed = true;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
return changed ? next : prev;
|
|
110
|
+
});
|
|
111
|
+
}, [rawDep]);
|
|
112
|
+
return parsed;
|
|
113
|
+
}
|
|
114
|
+
function useSectionSettings(key) {
|
|
115
|
+
return { value: useLiquidRaw(`section.settings.${key}`) };
|
|
116
|
+
}
|
|
117
|
+
function useBlockSettings(key) {
|
|
118
|
+
return { value: useLiquidRaw(`block.settings.${key}`) };
|
|
119
|
+
}
|
|
120
|
+
function useSnippetParams(key) {
|
|
121
|
+
return { value: useLiquidRaw(key) };
|
|
122
|
+
}
|
|
123
|
+
function useBlockParams(key) {
|
|
124
|
+
return { value: useLiquidRaw(key) };
|
|
125
|
+
}
|
|
62
126
|
export {
|
|
63
127
|
LiquidDataContext,
|
|
64
128
|
LiquidDataProvider,
|
|
@@ -66,7 +130,7 @@ export {
|
|
|
66
130
|
parseLiquidNumber,
|
|
67
131
|
useBlockParams,
|
|
68
132
|
useBlockSettings,
|
|
69
|
-
|
|
133
|
+
useLiquidValue,
|
|
70
134
|
useLiquidValues,
|
|
71
135
|
useSectionSettings,
|
|
72
136
|
useSnippetParams
|