@foxford/den-preact 0.1.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/README.mdx ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ title: Den Preact
3
+ ---
4
+
5
+ # @foxford/den-preact
6
+
7
+ View adapter для Preact: остров, серверная отрисовка, слоты, клиентский вход и пресет сборки.
@@ -0,0 +1,20 @@
1
+ var __defProp = Object.defineProperty;
2
+ var __getOwnPropSymbols = Object.getOwnPropertySymbols;
3
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
4
+ var __propIsEnum = Object.prototype.propertyIsEnumerable;
5
+ var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
6
+ var __spreadValues = (a, b) => {
7
+ for (var prop in b || (b = {}))
8
+ if (__hasOwnProp.call(b, prop))
9
+ __defNormalProp(a, prop, b[prop]);
10
+ if (__getOwnPropSymbols)
11
+ for (var prop of __getOwnPropSymbols(b)) {
12
+ if (__propIsEnum.call(b, prop))
13
+ __defNormalProp(a, prop, b[prop]);
14
+ }
15
+ return a;
16
+ };
17
+
18
+ export {
19
+ __spreadValues
20
+ };
@@ -0,0 +1,165 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true});
2
+
3
+ var _chunkP4DSWCF6cjs = require('./chunk-P4DSWCF6.cjs');
4
+
5
+ // src/container-context.tsx
6
+ var _preact = require('preact');
7
+ var _hooks = require('preact/hooks');
8
+ var _adapter = require('@foxford/den/adapter');
9
+ var _logger = require('@foxford/logger');
10
+ var _jsxruntime = require('preact/jsx-runtime');
11
+ var ContainerContext = _preact.createContext.call(void 0, null);
12
+ var logger = _logger.log.getLogger("den-preact").getLogger("island");
13
+ function ContainerProvider({ value, children }) {
14
+ return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, ContainerContext.Provider, { value, children });
15
+ }
16
+ function useContainer() {
17
+ const container = _hooks.useContext.call(void 0, ContainerContext);
18
+ if (container === null) {
19
+ throw new Error("den-preact: useContainer() \u0432\u044B\u0437\u0432\u0430\u043D \u0432\u043D\u0435 ContainerProvider");
20
+ }
21
+ return container;
22
+ }
23
+ function installIslandResolver() {
24
+ _adapter.installResolver.call(void 0, (token) => {
25
+ var _a, _b;
26
+ let container = (_a = _hooks.useContext.call(void 0, ContainerContext)) != null ? _a : void 0;
27
+ if (!container) {
28
+ logger.error(`\u0440\u0435\u0437\u043E\u043B\u0432 \xAB${token.description}\xBB \u0432\u043D\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 (\u043D\u0435\u0442 container-context)`);
29
+ throw new Error(`den-preact: .resolve() \u0432\u044B\u0437\u0432\u0430\u043D \u0432\u043D\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 (\u043D\u0435\u0442 container-context) \u0434\u043B\u044F \xAB${token.description}\xBB`);
30
+ }
31
+ while (container) {
32
+ if (container.has(token)) {
33
+ logger.debug(`\u0440\u0435\u0437\u043E\u043B\u0432 \xAB${token.description}\xBB \u0432\u043E view`);
34
+ return container.resolve(token);
35
+ }
36
+ container = (_b = container.getParent) == null ? void 0 : _b.call(container);
37
+ }
38
+ logger.error(`\u0442\u043E\u043A\u0435\u043D \xAB${token.description}\xBB \u043D\u0435 \u0437\u0430\u0440\u0435\u0433\u0438\u0441\u0442\u0440\u0438\u0440\u043E\u0432\u0430\u043D \u0432 \u043A\u043E\u043D\u0442\u0435\u0439\u043D\u0435\u0440\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430`);
39
+ throw new Error(`den-preact: \u0442\u043E\u043A\u0435\u043D \xAB${token.description}\xBB \u043D\u0435 \u0437\u0430\u0440\u0435\u0433\u0438\u0441\u0442\u0440\u0438\u0440\u043E\u0432\u0430\u043D \u0432 \u043A\u043E\u043D\u0442\u0435\u0439\u043D\u0435\u0440\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430`);
40
+ });
41
+ }
42
+
43
+ // src/slot.tsx
44
+
45
+
46
+ var _define = require('@foxford/den/define');
47
+ var _island = require('@foxford/den/island');
48
+
49
+ var SlotFillContext = _preact.createContext.call(void 0, {});
50
+ function SlotHost({
51
+ fills,
52
+ children
53
+ }) {
54
+ return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, SlotFillContext.Provider, { value: fills != null ? fills : {}, children });
55
+ }
56
+ function Slot({ name }) {
57
+ const fill = _hooks.useContext.call(void 0, SlotFillContext)[name];
58
+ const container = useContainer();
59
+ const entry = container.has(_define.SlotRegistryToken) ? container.resolve(_define.SlotRegistryToken).get(name) : void 0;
60
+ if (!entry) {
61
+ throw new Error(
62
+ `den-preact: \u0441\u043B\u043E\u0442 \xAB${name}\xBB \u043D\u0435 \u0437\u0430\u0440\u0435\u0433\u0438\u0441\u0442\u0440\u0438\u0440\u043E\u0432\u0430\u043D \u0432 \u043A\u043E\u043D\u0442\u0435\u0439\u043D\u0435\u0440\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 \u2014 \u043E\u0431\u044A\u044F\u0432\u0438\u0442\u0435 \u0435\u0433\u043E \u0432 \`slots\` \u0434\u0435\u0441\u043A\u0440\u0438\u043F\u0442\u043E\u0440\u0430 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \u0438\u043B\u0438 \u043F\u0440\u043E\u0432\u0435\u0440\u044C\u0442\u0435 \u0438\u043C\u044F`
63
+ );
64
+ }
65
+ const slotAdapter = entry.viewLayer && _island.viewAdapterOf.call(void 0, entry.viewLayer);
66
+ if (slotAdapter && slotAdapter.type !== "preact") {
67
+ throw new Error(
68
+ `den-preact: \u0441\u043B\u043E\u0442 \xAB${name}\xBB \u043E\u0431\u044A\u044F\u0432\u043B\u0435\u043D \u0441 view-\u0441\u043B\u043E\u0435\u043C \xAB${slotAdapter.type}\xBB \u2014 \u0441\u043C\u0435\u0448\u0435\u043D\u0438\u0435 \u0444\u0440\u0435\u0439\u043C\u0432\u043E\u0440\u043A\u043E\u0432 \u0432 \u043E\u0434\u043D\u043E\u043C \u0434\u0435\u0440\u0435\u0432\u0435 \u043F\u043E\u043A\u0430 \u043D\u0435 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442\u0441\u044F`
69
+ );
70
+ }
71
+ const View = entry.view;
72
+ return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, "div", { "data-den-slot": name, children: [
73
+ View ? /* @__PURE__ */ _jsxruntime.jsx.call(void 0, View, {}) : null,
74
+ fill
75
+ ] });
76
+ }
77
+
78
+ // src/island.tsx
79
+
80
+
81
+
82
+
83
+
84
+
85
+
86
+
87
+
88
+
89
+
90
+ function IslandRuntime({
91
+ descriptor,
92
+ denState,
93
+ onDocument,
94
+ route,
95
+ slots
96
+ }) {
97
+ var _a;
98
+ const [container] = _hooks.useState.call(void 0, () => _island.createIslandContainer.call(void 0, descriptor));
99
+ const [seeded, setSeeded] = _hooks.useState.call(void 0, void 0);
100
+ if (container !== null && denState !== void 0 && denState !== seeded) {
101
+ setSeeded(denState);
102
+ _island.hydrateIslandState.call(void 0, container, descriptor, denState);
103
+ }
104
+ _hooks.useEffect.call(void 0, () => {
105
+ if (container === null) {
106
+ return;
107
+ }
108
+ _island.resolveEagerUnits.call(void 0, container, descriptor);
109
+ }, [container, descriptor]);
110
+ const routeKey = route === void 0 ? "" : JSON.stringify(route);
111
+ const activeRoute = _hooks.useMemo.call(void 0,
112
+ () => routeKey === "" ? void 0 : JSON.parse(routeKey),
113
+ [routeKey]
114
+ );
115
+ _hooks.useEffect.call(void 0, () => {
116
+ if (denState || container === null) {
117
+ return;
118
+ }
119
+ void _island.activateIslandViewModels.call(void 0, container, descriptor, activeRoute).then(() => {
120
+ onDocument == null ? void 0 : onDocument(_island.collectDocumentContribution.call(void 0, container, descriptor));
121
+ });
122
+ }, [activeRoute, container, denState, descriptor, onDocument]);
123
+ _hooks.useEffect.call(void 0, () => {
124
+ if (container === null) {
125
+ return;
126
+ }
127
+ return _island.registerIsland.call(void 0, _island.describeIsland.call(void 0, descriptor, denState));
128
+ }, [container, descriptor, denState]);
129
+ if (container === null) {
130
+ return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0,
131
+ "div",
132
+ {
133
+ style: {
134
+ background: "#fef2f2",
135
+ border: "1px solid #fca5a5",
136
+ borderRadius: 8,
137
+ color: "#b91c1c",
138
+ fontSize: 14,
139
+ padding: 12
140
+ },
141
+ children: [
142
+ "\u041E\u0441\u0442\u0440\u043E\u0432 \xAB",
143
+ (_a = descriptor.name) != null ? _a : "app",
144
+ "\xBB \u0443\u043F\u0430\u043B \u043F\u0440\u0438 \u0441\u0431\u043E\u0440\u043A\u0435 \u2014 \u043E\u0441\u0442\u0430\u043B\u044C\u043D\u0430\u044F \u0441\u0442\u0440\u0430\u043D\u0438\u0446\u0430 \u0440\u0430\u0431\u043E\u0442\u0430\u0435\u0442."
145
+ ]
146
+ }
147
+ );
148
+ }
149
+ const View = descriptor.view;
150
+ return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, ContainerProvider, { value: container, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, SlotHost, { fills: slots, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, View, {}) }) });
151
+ }
152
+ function createPreactIsland(descriptor) {
153
+ return function Island(props) {
154
+ return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, IslandRuntime, _chunkP4DSWCF6cjs.__spreadValues.call(void 0, { descriptor }, props));
155
+ };
156
+ }
157
+
158
+
159
+
160
+
161
+
162
+
163
+
164
+
165
+ exports.ContainerProvider = ContainerProvider; exports.useContainer = useContainer; exports.installIslandResolver = installIslandResolver; exports.SlotHost = SlotHost; exports.Slot = Slot; exports.createPreactIsland = createPreactIsland;
@@ -0,0 +1,20 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true});var __defProp = Object.defineProperty;
2
+ var __getOwnPropSymbols = Object.getOwnPropertySymbols;
3
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
4
+ var __propIsEnum = Object.prototype.propertyIsEnumerable;
5
+ var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
6
+ var __spreadValues = (a, b) => {
7
+ for (var prop in b || (b = {}))
8
+ if (__hasOwnProp.call(b, prop))
9
+ __defNormalProp(a, prop, b[prop]);
10
+ if (__getOwnPropSymbols)
11
+ for (var prop of __getOwnPropSymbols(b)) {
12
+ if (__propIsEnum.call(b, prop))
13
+ __defNormalProp(a, prop, b[prop]);
14
+ }
15
+ return a;
16
+ };
17
+
18
+
19
+
20
+ exports.__spreadValues = __spreadValues;
@@ -0,0 +1,165 @@
1
+ import {
2
+ __spreadValues
3
+ } from "./chunk-5JBD5THX.js";
4
+
5
+ // src/container-context.tsx
6
+ import { createContext } from "preact";
7
+ import { useContext } from "preact/hooks";
8
+ import { installResolver } from "@foxford/den/adapter";
9
+ import { log } from "@foxford/logger";
10
+ import { jsx } from "preact/jsx-runtime";
11
+ var ContainerContext = createContext(null);
12
+ var logger = log.getLogger("den-preact").getLogger("island");
13
+ function ContainerProvider({ value, children }) {
14
+ return /* @__PURE__ */ jsx(ContainerContext.Provider, { value, children });
15
+ }
16
+ function useContainer() {
17
+ const container = useContext(ContainerContext);
18
+ if (container === null) {
19
+ throw new Error("den-preact: useContainer() \u0432\u044B\u0437\u0432\u0430\u043D \u0432\u043D\u0435 ContainerProvider");
20
+ }
21
+ return container;
22
+ }
23
+ function installIslandResolver() {
24
+ installResolver((token) => {
25
+ var _a, _b;
26
+ let container = (_a = useContext(ContainerContext)) != null ? _a : void 0;
27
+ if (!container) {
28
+ logger.error(`\u0440\u0435\u0437\u043E\u043B\u0432 \xAB${token.description}\xBB \u0432\u043D\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 (\u043D\u0435\u0442 container-context)`);
29
+ throw new Error(`den-preact: .resolve() \u0432\u044B\u0437\u0432\u0430\u043D \u0432\u043D\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 (\u043D\u0435\u0442 container-context) \u0434\u043B\u044F \xAB${token.description}\xBB`);
30
+ }
31
+ while (container) {
32
+ if (container.has(token)) {
33
+ logger.debug(`\u0440\u0435\u0437\u043E\u043B\u0432 \xAB${token.description}\xBB \u0432\u043E view`);
34
+ return container.resolve(token);
35
+ }
36
+ container = (_b = container.getParent) == null ? void 0 : _b.call(container);
37
+ }
38
+ logger.error(`\u0442\u043E\u043A\u0435\u043D \xAB${token.description}\xBB \u043D\u0435 \u0437\u0430\u0440\u0435\u0433\u0438\u0441\u0442\u0440\u0438\u0440\u043E\u0432\u0430\u043D \u0432 \u043A\u043E\u043D\u0442\u0435\u0439\u043D\u0435\u0440\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430`);
39
+ throw new Error(`den-preact: \u0442\u043E\u043A\u0435\u043D \xAB${token.description}\xBB \u043D\u0435 \u0437\u0430\u0440\u0435\u0433\u0438\u0441\u0442\u0440\u0438\u0440\u043E\u0432\u0430\u043D \u0432 \u043A\u043E\u043D\u0442\u0435\u0439\u043D\u0435\u0440\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430`);
40
+ });
41
+ }
42
+
43
+ // src/slot.tsx
44
+ import { createContext as createContext2 } from "preact";
45
+ import { useContext as useContext2 } from "preact/hooks";
46
+ import { SlotRegistryToken } from "@foxford/den/define";
47
+ import { viewAdapterOf } from "@foxford/den/island";
48
+ import { jsx as jsx2, jsxs } from "preact/jsx-runtime";
49
+ var SlotFillContext = createContext2({});
50
+ function SlotHost({
51
+ fills,
52
+ children
53
+ }) {
54
+ return /* @__PURE__ */ jsx2(SlotFillContext.Provider, { value: fills != null ? fills : {}, children });
55
+ }
56
+ function Slot({ name }) {
57
+ const fill = useContext2(SlotFillContext)[name];
58
+ const container = useContainer();
59
+ const entry = container.has(SlotRegistryToken) ? container.resolve(SlotRegistryToken).get(name) : void 0;
60
+ if (!entry) {
61
+ throw new Error(
62
+ `den-preact: \u0441\u043B\u043E\u0442 \xAB${name}\xBB \u043D\u0435 \u0437\u0430\u0440\u0435\u0433\u0438\u0441\u0442\u0440\u0438\u0440\u043E\u0432\u0430\u043D \u0432 \u043A\u043E\u043D\u0442\u0435\u0439\u043D\u0435\u0440\u0435 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 \u2014 \u043E\u0431\u044A\u044F\u0432\u0438\u0442\u0435 \u0435\u0433\u043E \u0432 \`slots\` \u0434\u0435\u0441\u043A\u0440\u0438\u043F\u0442\u043E\u0440\u0430 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \u0438\u043B\u0438 \u043F\u0440\u043E\u0432\u0435\u0440\u044C\u0442\u0435 \u0438\u043C\u044F`
63
+ );
64
+ }
65
+ const slotAdapter = entry.viewLayer && viewAdapterOf(entry.viewLayer);
66
+ if (slotAdapter && slotAdapter.type !== "preact") {
67
+ throw new Error(
68
+ `den-preact: \u0441\u043B\u043E\u0442 \xAB${name}\xBB \u043E\u0431\u044A\u044F\u0432\u043B\u0435\u043D \u0441 view-\u0441\u043B\u043E\u0435\u043C \xAB${slotAdapter.type}\xBB \u2014 \u0441\u043C\u0435\u0448\u0435\u043D\u0438\u0435 \u0444\u0440\u0435\u0439\u043C\u0432\u043E\u0440\u043A\u043E\u0432 \u0432 \u043E\u0434\u043D\u043E\u043C \u0434\u0435\u0440\u0435\u0432\u0435 \u043F\u043E\u043A\u0430 \u043D\u0435 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442\u0441\u044F`
69
+ );
70
+ }
71
+ const View = entry.view;
72
+ return /* @__PURE__ */ jsxs("div", { "data-den-slot": name, children: [
73
+ View ? /* @__PURE__ */ jsx2(View, {}) : null,
74
+ fill
75
+ ] });
76
+ }
77
+
78
+ // src/island.tsx
79
+ import { useEffect, useMemo, useState } from "preact/hooks";
80
+ import {
81
+ activateIslandViewModels,
82
+ collectDocumentContribution,
83
+ createIslandContainer,
84
+ describeIsland,
85
+ hydrateIslandState,
86
+ registerIsland,
87
+ resolveEagerUnits
88
+ } from "@foxford/den/island";
89
+ import { jsx as jsx3, jsxs as jsxs2 } from "preact/jsx-runtime";
90
+ function IslandRuntime({
91
+ descriptor,
92
+ denState,
93
+ onDocument,
94
+ route,
95
+ slots
96
+ }) {
97
+ var _a;
98
+ const [container] = useState(() => createIslandContainer(descriptor));
99
+ const [seeded, setSeeded] = useState(void 0);
100
+ if (container !== null && denState !== void 0 && denState !== seeded) {
101
+ setSeeded(denState);
102
+ hydrateIslandState(container, descriptor, denState);
103
+ }
104
+ useEffect(() => {
105
+ if (container === null) {
106
+ return;
107
+ }
108
+ resolveEagerUnits(container, descriptor);
109
+ }, [container, descriptor]);
110
+ const routeKey = route === void 0 ? "" : JSON.stringify(route);
111
+ const activeRoute = useMemo(
112
+ () => routeKey === "" ? void 0 : JSON.parse(routeKey),
113
+ [routeKey]
114
+ );
115
+ useEffect(() => {
116
+ if (denState || container === null) {
117
+ return;
118
+ }
119
+ void activateIslandViewModels(container, descriptor, activeRoute).then(() => {
120
+ onDocument == null ? void 0 : onDocument(collectDocumentContribution(container, descriptor));
121
+ });
122
+ }, [activeRoute, container, denState, descriptor, onDocument]);
123
+ useEffect(() => {
124
+ if (container === null) {
125
+ return;
126
+ }
127
+ return registerIsland(describeIsland(descriptor, denState));
128
+ }, [container, descriptor, denState]);
129
+ if (container === null) {
130
+ return /* @__PURE__ */ jsxs2(
131
+ "div",
132
+ {
133
+ style: {
134
+ background: "#fef2f2",
135
+ border: "1px solid #fca5a5",
136
+ borderRadius: 8,
137
+ color: "#b91c1c",
138
+ fontSize: 14,
139
+ padding: 12
140
+ },
141
+ children: [
142
+ "\u041E\u0441\u0442\u0440\u043E\u0432 \xAB",
143
+ (_a = descriptor.name) != null ? _a : "app",
144
+ "\xBB \u0443\u043F\u0430\u043B \u043F\u0440\u0438 \u0441\u0431\u043E\u0440\u043A\u0435 \u2014 \u043E\u0441\u0442\u0430\u043B\u044C\u043D\u0430\u044F \u0441\u0442\u0440\u0430\u043D\u0438\u0446\u0430 \u0440\u0430\u0431\u043E\u0442\u0430\u0435\u0442."
145
+ ]
146
+ }
147
+ );
148
+ }
149
+ const View = descriptor.view;
150
+ return /* @__PURE__ */ jsx3(ContainerProvider, { value: container, children: /* @__PURE__ */ jsx3(SlotHost, { fills: slots, children: /* @__PURE__ */ jsx3(View, {}) }) });
151
+ }
152
+ function createPreactIsland(descriptor) {
153
+ return function Island(props) {
154
+ return /* @__PURE__ */ jsx3(IslandRuntime, __spreadValues({ descriptor }, props));
155
+ };
156
+ }
157
+
158
+ export {
159
+ ContainerProvider,
160
+ useContainer,
161
+ installIslandResolver,
162
+ SlotHost,
163
+ Slot,
164
+ createPreactIsland
165
+ };
package/client.cjs ADDED
@@ -0,0 +1,69 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true});
2
+
3
+
4
+ var _chunkJ2T5F5Q5cjs = require('./chunk-J2T5F5Q5.cjs');
5
+ require('./chunk-P4DSWCF6.cjs');
6
+
7
+ // src/client.ts
8
+ var _preact = require('preact');
9
+ var _island = require('@foxford/den/island');
10
+ var _logger = require('@foxford/logger');
11
+ var logger = _logger.log.getLogger("den-preact").getLogger("client");
12
+ var ROOT_MARK = "data-den-root";
13
+ var STATE_MARK = "data-den-state";
14
+ function readState(name) {
15
+ const tag = document.querySelector(`script[${STATE_MARK}="${name}"]`);
16
+ if (!(tag == null ? void 0 : tag.textContent)) {
17
+ logger.warn(`\u0441\u043E\u0441\u0442\u043E\u044F\u043D\u0438\u0435 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \xAB${name}\xBB \u0432 \u0434\u043E\u043A\u0443\u043C\u0435\u043D\u0442\u0435 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D\u043E \u2014 \u043F\u043E\u0434\u043D\u0438\u043C\u0430\u0435\u043C\u0441\u044F \u043D\u0430 \u0434\u0435\u0444\u043E\u043B\u0442\u043D\u043E\u043C`);
18
+ return {};
19
+ }
20
+ try {
21
+ return JSON.parse(tag.textContent);
22
+ } catch (error) {
23
+ logger.error(`\u0441\u043E\u0441\u0442\u043E\u044F\u043D\u0438\u0435 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \xAB${name}\xBB \u043D\u0435 \u0440\u0430\u0437\u043E\u0431\u0440\u0430\u0442\u044C:`, error);
24
+ return {};
25
+ }
26
+ }
27
+ function currentRoute() {
28
+ return {
29
+ params: {},
30
+ pathname: window.location.pathname,
31
+ search: window.location.search.replace(/^\?/, "")
32
+ };
33
+ }
34
+ var hydrated = /* @__PURE__ */ new WeakSet();
35
+ function hydrateApp(descriptor) {
36
+ if (false) {
37
+ void null.then(() => {
38
+ mountApp(descriptor);
39
+ });
40
+ return;
41
+ }
42
+ mountApp(descriptor);
43
+ }
44
+ function mountApp(descriptor) {
45
+ const node = document.querySelector(`[${ROOT_MARK}="${descriptor.name}"]`);
46
+ if (node === null) {
47
+ logger.error(`\u0443\u0437\u0435\u043B \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \xAB${descriptor.name}\xBB \u0432 \u0434\u043E\u043A\u0443\u043C\u0435\u043D\u0442\u0435 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D \u2014 \u043E\u0436\u0438\u0432\u043B\u044F\u0442\u044C \u043D\u0435\u0447\u0435\u0433\u043E`);
48
+ return;
49
+ }
50
+ if (hydrated.has(node)) {
51
+ logger.warn(`\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB \u0443\u0436\u0435 \u043E\u0436\u0438\u0432\u043B\u0435\u043D\u043E \u2014 \u0432\u0442\u043E\u0440\u043E\u0439 \u0432\u0445\u043E\u0434 \u043F\u0440\u043E\u043F\u0443\u0449\u0435\u043D`);
52
+ return;
53
+ }
54
+ hydrated.add(node);
55
+ _chunkJ2T5F5Q5cjs.installIslandResolver.call(void 0, );
56
+ const Island = _chunkJ2T5F5Q5cjs.createPreactIsland.call(void 0, descriptor);
57
+ const onDocument = (contribution) => {
58
+ _island.publishIslandDocument.call(void 0, node, contribution);
59
+ };
60
+ _preact.hydrate.call(void 0, _preact.h.call(void 0, Island, { denState: readState(descriptor.name), onDocument, route: currentRoute() }), node);
61
+ logger.info(`\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB \u043E\u0436\u0438\u0432\u043B\u0435\u043D\u043E`);
62
+ _island.onIslandNavigate.call(void 0, node, (route) => {
63
+ logger.debug(`\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB: \u043F\u0435\u0440\u0435\u0445\u043E\u0434 \u043D\u0430 \xAB${route.pathname}\xBB`);
64
+ _preact.render.call(void 0, _preact.h.call(void 0, Island, { onDocument, route }), node);
65
+ });
66
+ }
67
+
68
+
69
+ exports.hydrateApp = hydrateApp;
package/client.d.cts ADDED
@@ -0,0 +1,16 @@
1
+ import { IslandDescriptor } from '@foxford/den/island';
2
+
3
+ /**
4
+ * Оживляет фрагмент приложения в его узле и ведёт его через переходы хоста.
5
+ *
6
+ * В разработке первым делом подключается мост к расширению Preact Devtools: он же печатает
7
+ * предупреждения о расхождении гидрации. Подключается ЗДЕСЬ, а не пресетом сборки — тот
8
+ * вставляет его в entry, найденный через `.html`, а входа-страницы у приложения нет: его вход
9
+ * порождает сборка. Расширение видит ту копию рантайма, которая его импортировала, поэтому
10
+ * своя нужна каждому бандлу на странице.
11
+ *
12
+ * @param descriptor - Дескриптор приложения
13
+ */
14
+ declare function hydrateApp(descriptor: IslandDescriptor): void;
15
+
16
+ export { hydrateApp };
package/client.d.ts ADDED
@@ -0,0 +1,16 @@
1
+ import { IslandDescriptor } from '@foxford/den/island';
2
+
3
+ /**
4
+ * Оживляет фрагмент приложения в его узле и ведёт его через переходы хоста.
5
+ *
6
+ * В разработке первым делом подключается мост к расширению Preact Devtools: он же печатает
7
+ * предупреждения о расхождении гидрации. Подключается ЗДЕСЬ, а не пресетом сборки — тот
8
+ * вставляет его в entry, найденный через `.html`, а входа-страницы у приложения нет: его вход
9
+ * порождает сборка. Расширение видит ту копию рантайма, которая его импортировала, поэтому
10
+ * своя нужна каждому бандлу на странице.
11
+ *
12
+ * @param descriptor - Дескриптор приложения
13
+ */
14
+ declare function hydrateApp(descriptor: IslandDescriptor): void;
15
+
16
+ export { hydrateApp };
package/client.js ADDED
@@ -0,0 +1,69 @@
1
+ import {
2
+ createPreactIsland,
3
+ installIslandResolver
4
+ } from "./chunk-R2CWAR74.js";
5
+ import "./chunk-5JBD5THX.js";
6
+
7
+ // src/client.ts
8
+ import { h, hydrate, render } from "preact";
9
+ import { onIslandNavigate, publishIslandDocument } from "@foxford/den/island";
10
+ import { log } from "@foxford/logger";
11
+ var logger = log.getLogger("den-preact").getLogger("client");
12
+ var ROOT_MARK = "data-den-root";
13
+ var STATE_MARK = "data-den-state";
14
+ function readState(name) {
15
+ const tag = document.querySelector(`script[${STATE_MARK}="${name}"]`);
16
+ if (!(tag == null ? void 0 : tag.textContent)) {
17
+ logger.warn(`\u0441\u043E\u0441\u0442\u043E\u044F\u043D\u0438\u0435 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \xAB${name}\xBB \u0432 \u0434\u043E\u043A\u0443\u043C\u0435\u043D\u0442\u0435 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D\u043E \u2014 \u043F\u043E\u0434\u043D\u0438\u043C\u0430\u0435\u043C\u0441\u044F \u043D\u0430 \u0434\u0435\u0444\u043E\u043B\u0442\u043D\u043E\u043C`);
18
+ return {};
19
+ }
20
+ try {
21
+ return JSON.parse(tag.textContent);
22
+ } catch (error) {
23
+ logger.error(`\u0441\u043E\u0441\u0442\u043E\u044F\u043D\u0438\u0435 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \xAB${name}\xBB \u043D\u0435 \u0440\u0430\u0437\u043E\u0431\u0440\u0430\u0442\u044C:`, error);
24
+ return {};
25
+ }
26
+ }
27
+ function currentRoute() {
28
+ return {
29
+ params: {},
30
+ pathname: window.location.pathname,
31
+ search: window.location.search.replace(/^\?/, "")
32
+ };
33
+ }
34
+ var hydrated = /* @__PURE__ */ new WeakSet();
35
+ function hydrateApp(descriptor) {
36
+ if (import.meta.env.DEV) {
37
+ void import("preact/debug").then(() => {
38
+ mountApp(descriptor);
39
+ });
40
+ return;
41
+ }
42
+ mountApp(descriptor);
43
+ }
44
+ function mountApp(descriptor) {
45
+ const node = document.querySelector(`[${ROOT_MARK}="${descriptor.name}"]`);
46
+ if (node === null) {
47
+ logger.error(`\u0443\u0437\u0435\u043B \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F \xAB${descriptor.name}\xBB \u0432 \u0434\u043E\u043A\u0443\u043C\u0435\u043D\u0442\u0435 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D \u2014 \u043E\u0436\u0438\u0432\u043B\u044F\u0442\u044C \u043D\u0435\u0447\u0435\u0433\u043E`);
48
+ return;
49
+ }
50
+ if (hydrated.has(node)) {
51
+ logger.warn(`\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB \u0443\u0436\u0435 \u043E\u0436\u0438\u0432\u043B\u0435\u043D\u043E \u2014 \u0432\u0442\u043E\u0440\u043E\u0439 \u0432\u0445\u043E\u0434 \u043F\u0440\u043E\u043F\u0443\u0449\u0435\u043D`);
52
+ return;
53
+ }
54
+ hydrated.add(node);
55
+ installIslandResolver();
56
+ const Island = createPreactIsland(descriptor);
57
+ const onDocument = (contribution) => {
58
+ publishIslandDocument(node, contribution);
59
+ };
60
+ hydrate(h(Island, { denState: readState(descriptor.name), onDocument, route: currentRoute() }), node);
61
+ logger.info(`\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB \u043E\u0436\u0438\u0432\u043B\u0435\u043D\u043E`);
62
+ onIslandNavigate(node, (route) => {
63
+ logger.debug(`\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB: \u043F\u0435\u0440\u0435\u0445\u043E\u0434 \u043D\u0430 \xAB${route.pathname}\xBB`);
64
+ render(h(Island, { onDocument, route }), node);
65
+ });
66
+ }
67
+ export {
68
+ hydrateApp
69
+ };
package/index.cjs ADDED
@@ -0,0 +1,45 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true});
2
+
3
+
4
+
5
+
6
+
7
+
8
+ var _chunkJ2T5F5Q5cjs = require('./chunk-J2T5F5Q5.cjs');
9
+ require('./chunk-P4DSWCF6.cjs');
10
+
11
+ // src/render-island.tsx
12
+ var _preactrendertostring = require('preact-render-to-string');
13
+ var _jsxruntime = require('preact/jsx-runtime');
14
+ function renderPreactIsland(descriptor, { container, slots }) {
15
+ const View = descriptor.view;
16
+ const tree = /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkJ2T5F5Q5cjs.ContainerProvider, { value: container, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkJ2T5F5Q5cjs.SlotHost, { fills: slots, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, View, {}) }) });
17
+ const serverRender = descriptor.serverRender;
18
+ if (serverRender) {
19
+ return serverRender(tree, (node) => _preactrendertostring.renderToString.call(void 0, node));
20
+ }
21
+ return { html: _preactrendertostring.renderToString.call(void 0, tree) };
22
+ }
23
+
24
+ // src/index.ts
25
+ var CLIENT_BUNDLE = false;
26
+ function renderIslandOnClient() {
27
+ throw new Error("den-preact: \u0441\u0435\u0440\u0432\u0435\u0440\u043D\u044B\u0439 \u0440\u0435\u043D\u0434\u0435\u0440 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 \u0432 \u0431\u0440\u0430\u0443\u0437\u0435\u0440\u043D\u043E\u043C \u0432\u044B\u0445\u043E\u0434\u0435 \u043D\u0435 \u0441\u043E\u0431\u0440\u0430\u043D");
28
+ }
29
+ function preactAdapter() {
30
+ return {
31
+ createIsland: _chunkJ2T5F5Q5cjs.createPreactIsland,
32
+ installResolver: _chunkJ2T5F5Q5cjs.installIslandResolver,
33
+ renderIsland: CLIENT_BUNDLE ? renderIslandOnClient : renderPreactIsland,
34
+ type: "preact"
35
+ };
36
+ }
37
+
38
+
39
+
40
+
41
+
42
+
43
+
44
+
45
+ exports.ContainerProvider = _chunkJ2T5F5Q5cjs.ContainerProvider; exports.Slot = _chunkJ2T5F5Q5cjs.Slot; exports.SlotHost = _chunkJ2T5F5Q5cjs.SlotHost; exports.createPreactIsland = _chunkJ2T5F5Q5cjs.createPreactIsland; exports.installIslandResolver = _chunkJ2T5F5Q5cjs.installIslandResolver; exports.preactAdapter = preactAdapter; exports.useContainer = _chunkJ2T5F5Q5cjs.useContainer;
package/index.d.cts ADDED
@@ -0,0 +1,74 @@
1
+ import { IslandRoute, DocumentContribution, IslandDescriptor, ServerRender, ViewAdapter } from '@foxford/den/island';
2
+ import * as preact from 'preact';
3
+ import { ComponentChildren, ComponentType, VNode } from 'preact';
4
+ import { Container } from '@foxford/ioc';
5
+
6
+ declare function ContainerProvider({ value, children }: {
7
+ value: Container;
8
+ children: ComponentChildren;
9
+ }): preact.JSX.Element;
10
+ /** Контейнер острова напрямую; обычно хватает `Definition.resolve()`. */
11
+ declare function useContainer(): Container;
12
+ /**
13
+ * Ставит preact-стратегию резолва в общий шов `@foxford/den/adapter`.
14
+ *
15
+ * Зовётся из `preactAdapter().installResolver()`: шов один на процесс и работает last-wins.
16
+ */
17
+ declare function installIslandResolver(): void;
18
+
19
+ /** Пропсы острова: серверное состояние, адрес и внешние заполнители слотов. */
20
+ interface IslandProps {
21
+ /** Состояние с сервера (ключ = `token.description` VM). */
22
+ denState?: Record<string, unknown>;
23
+ /** Адрес, на котором остров стоит. Меняется — VM активируются заново, тем же вызовом. */
24
+ route?: IslandRoute;
25
+ /** Внешний контент слотов по имени. */
26
+ slots?: Record<string, ComponentChildren>;
27
+ /** Куда отдать вклад в документ — заголовок и meta, посчитанные по состоянию VM. */
28
+ onDocument?: (contribution: DocumentContribution) => void;
29
+ }
30
+ /**
31
+ * Делает из дескриптора компонент острова. Зовётся ядром через `ViewAdapter.createIsland`.
32
+ *
33
+ * @param descriptor - Дескриптор острова
34
+ */
35
+ declare function createPreactIsland(descriptor: IslandDescriptor): ComponentType<IslandProps>;
36
+
37
+ /**
38
+ * Провайдер внешнего контента слотов; оборачивает view острова.
39
+ *
40
+ * @param props.fills - Карта «имя слота → контент» от оркестратора
41
+ */
42
+ declare function SlotHost({ fills, children, }: {
43
+ fills?: Record<string, ComponentChildren>;
44
+ children: ComponentChildren;
45
+ }): preact.JSX.Element;
46
+ /**
47
+ * Рисует слот по имени: локальный `view` слота плюс внешний контент оркестратора.
48
+ *
49
+ * По имени, а не по ссылке на дескриптор: слоты объявляются в дескрипторе приложения, и
50
+ * импорт объекта во view замкнул бы цикл. Запись берётся из реестра слотов в контейнере.
51
+ *
52
+ * @param props.name - Ключ слота из карты `slots` дескриптора
53
+ */
54
+ declare function Slot({ name }: {
55
+ name: string;
56
+ }): VNode;
57
+
58
+ /**
59
+ * Серверный рендер приложения на preact — сужение ядерного `ServerRender` до дерева preact.
60
+ *
61
+ * Ядро дерево не типизирует: для него это непрозрачное значение. Приложение пишет проход
62
+ * в терминах своего фреймворка, поэтому импортирует этот тип.
63
+ */
64
+ type PreactServerRender = ServerRender<VNode>;
65
+
66
+ /**
67
+ * Preact-адаптер view — реализация порта `ViewAdapter` из `@foxford/den/island`.
68
+ *
69
+ * Объявляется приложением через `defineLayer(ViewLayerToken, { adapter })`. Дефолта нет ни у
70
+ * ядра, ни у хоста: фреймворк за приложение не выбирают.
71
+ */
72
+ declare function preactAdapter(): ViewAdapter;
73
+
74
+ export { ContainerProvider, type IslandProps, type PreactServerRender, Slot, SlotHost, createPreactIsland, installIslandResolver, preactAdapter, useContainer };
package/index.d.ts ADDED
@@ -0,0 +1,74 @@
1
+ import { IslandRoute, DocumentContribution, IslandDescriptor, ServerRender, ViewAdapter } from '@foxford/den/island';
2
+ import * as preact from 'preact';
3
+ import { ComponentChildren, ComponentType, VNode } from 'preact';
4
+ import { Container } from '@foxford/ioc';
5
+
6
+ declare function ContainerProvider({ value, children }: {
7
+ value: Container;
8
+ children: ComponentChildren;
9
+ }): preact.JSX.Element;
10
+ /** Контейнер острова напрямую; обычно хватает `Definition.resolve()`. */
11
+ declare function useContainer(): Container;
12
+ /**
13
+ * Ставит preact-стратегию резолва в общий шов `@foxford/den/adapter`.
14
+ *
15
+ * Зовётся из `preactAdapter().installResolver()`: шов один на процесс и работает last-wins.
16
+ */
17
+ declare function installIslandResolver(): void;
18
+
19
+ /** Пропсы острова: серверное состояние, адрес и внешние заполнители слотов. */
20
+ interface IslandProps {
21
+ /** Состояние с сервера (ключ = `token.description` VM). */
22
+ denState?: Record<string, unknown>;
23
+ /** Адрес, на котором остров стоит. Меняется — VM активируются заново, тем же вызовом. */
24
+ route?: IslandRoute;
25
+ /** Внешний контент слотов по имени. */
26
+ slots?: Record<string, ComponentChildren>;
27
+ /** Куда отдать вклад в документ — заголовок и meta, посчитанные по состоянию VM. */
28
+ onDocument?: (contribution: DocumentContribution) => void;
29
+ }
30
+ /**
31
+ * Делает из дескриптора компонент острова. Зовётся ядром через `ViewAdapter.createIsland`.
32
+ *
33
+ * @param descriptor - Дескриптор острова
34
+ */
35
+ declare function createPreactIsland(descriptor: IslandDescriptor): ComponentType<IslandProps>;
36
+
37
+ /**
38
+ * Провайдер внешнего контента слотов; оборачивает view острова.
39
+ *
40
+ * @param props.fills - Карта «имя слота → контент» от оркестратора
41
+ */
42
+ declare function SlotHost({ fills, children, }: {
43
+ fills?: Record<string, ComponentChildren>;
44
+ children: ComponentChildren;
45
+ }): preact.JSX.Element;
46
+ /**
47
+ * Рисует слот по имени: локальный `view` слота плюс внешний контент оркестратора.
48
+ *
49
+ * По имени, а не по ссылке на дескриптор: слоты объявляются в дескрипторе приложения, и
50
+ * импорт объекта во view замкнул бы цикл. Запись берётся из реестра слотов в контейнере.
51
+ *
52
+ * @param props.name - Ключ слота из карты `slots` дескриптора
53
+ */
54
+ declare function Slot({ name }: {
55
+ name: string;
56
+ }): VNode;
57
+
58
+ /**
59
+ * Серверный рендер приложения на preact — сужение ядерного `ServerRender` до дерева preact.
60
+ *
61
+ * Ядро дерево не типизирует: для него это непрозрачное значение. Приложение пишет проход
62
+ * в терминах своего фреймворка, поэтому импортирует этот тип.
63
+ */
64
+ type PreactServerRender = ServerRender<VNode>;
65
+
66
+ /**
67
+ * Preact-адаптер view — реализация порта `ViewAdapter` из `@foxford/den/island`.
68
+ *
69
+ * Объявляется приложением через `defineLayer(ViewLayerToken, { adapter })`. Дефолта нет ни у
70
+ * ядра, ни у хоста: фреймворк за приложение не выбирают.
71
+ */
72
+ declare function preactAdapter(): ViewAdapter;
73
+
74
+ export { ContainerProvider, type IslandProps, type PreactServerRender, Slot, SlotHost, createPreactIsland, installIslandResolver, preactAdapter, useContainer };
package/index.js ADDED
@@ -0,0 +1,45 @@
1
+ import {
2
+ ContainerProvider,
3
+ Slot,
4
+ SlotHost,
5
+ createPreactIsland,
6
+ installIslandResolver,
7
+ useContainer
8
+ } from "./chunk-R2CWAR74.js";
9
+ import "./chunk-5JBD5THX.js";
10
+
11
+ // src/render-island.tsx
12
+ import { renderToString } from "preact-render-to-string";
13
+ import { jsx } from "preact/jsx-runtime";
14
+ function renderPreactIsland(descriptor, { container, slots }) {
15
+ const View = descriptor.view;
16
+ const tree = /* @__PURE__ */ jsx(ContainerProvider, { value: container, children: /* @__PURE__ */ jsx(SlotHost, { fills: slots, children: /* @__PURE__ */ jsx(View, {}) }) });
17
+ const serverRender = descriptor.serverRender;
18
+ if (serverRender) {
19
+ return serverRender(tree, (node) => renderToString(node));
20
+ }
21
+ return { html: renderToString(tree) };
22
+ }
23
+
24
+ // src/index.ts
25
+ var CLIENT_BUNDLE = import.meta.env.PROD && !import.meta.env.SSR;
26
+ function renderIslandOnClient() {
27
+ throw new Error("den-preact: \u0441\u0435\u0440\u0432\u0435\u0440\u043D\u044B\u0439 \u0440\u0435\u043D\u0434\u0435\u0440 \u043E\u0441\u0442\u0440\u043E\u0432\u0430 \u0432 \u0431\u0440\u0430\u0443\u0437\u0435\u0440\u043D\u043E\u043C \u0432\u044B\u0445\u043E\u0434\u0435 \u043D\u0435 \u0441\u043E\u0431\u0440\u0430\u043D");
28
+ }
29
+ function preactAdapter() {
30
+ return {
31
+ createIsland: createPreactIsland,
32
+ installResolver: installIslandResolver,
33
+ renderIsland: CLIENT_BUNDLE ? renderIslandOnClient : renderPreactIsland,
34
+ type: "preact"
35
+ };
36
+ }
37
+ export {
38
+ ContainerProvider,
39
+ Slot,
40
+ SlotHost,
41
+ createPreactIsland,
42
+ installIslandResolver,
43
+ preactAdapter,
44
+ useContainer
45
+ };
package/package.json ADDED
@@ -0,0 +1,76 @@
1
+ {
2
+ "name": "@foxford/den-preact",
3
+ "version": "0.1.0",
4
+ "description": "Den Preact view adapter — остров, серверная отрисовка, слоты, пресет сборки",
5
+ "keywords": [
6
+ "foxford",
7
+ "den",
8
+ "preact",
9
+ "view"
10
+ ],
11
+ "license": "MIT",
12
+ "author": "Foxford Co",
13
+ "maintainers": [
14
+ {
15
+ "name": "Roman Olin",
16
+ "email": "r.v.olin@foxford.ru",
17
+ "team": "core-frontend"
18
+ }
19
+ ],
20
+ "type": "module",
21
+ "dependencies": {
22
+ "@foxford/den": "^3.2.2",
23
+ "@foxford/logger": "^1.2.2"
24
+ },
25
+ "peerDependencies": {
26
+ "@preact/preset-vite": ">=2",
27
+ "preact": ">=10",
28
+ "preact-render-to-string": ">=6"
29
+ },
30
+ "peerDependenciesMeta": {
31
+ "@preact/preset-vite": {
32
+ "optional": true
33
+ }
34
+ },
35
+ "main": "./index.cjs",
36
+ "module": "./index.js",
37
+ "exports": {
38
+ ".": {
39
+ "import": "./index.js",
40
+ "require": "./index.cjs",
41
+ "types": "./index.d.ts"
42
+ },
43
+ "./client": {
44
+ "import": "./client.js",
45
+ "require": "./client.cjs",
46
+ "types": "./client.d.ts"
47
+ },
48
+ "./preset": {
49
+ "import": "./preset.js",
50
+ "require": "./preset.cjs",
51
+ "types": "./preset.d.ts"
52
+ }
53
+ },
54
+ "files": [
55
+ "README.mdx",
56
+ "chunk-5JBD5THX.js",
57
+ "chunk-J2T5F5Q5.cjs",
58
+ "chunk-P4DSWCF6.cjs",
59
+ "chunk-R2CWAR74.js",
60
+ "client.cjs",
61
+ "client.d.cts",
62
+ "client.d.ts",
63
+ "client.js",
64
+ "index.cjs",
65
+ "index.d.cts",
66
+ "index.d.ts",
67
+ "index.js",
68
+ "package.json",
69
+ "preset.cjs",
70
+ "preset.d.cts",
71
+ "preset.d.ts",
72
+ "preset.js"
73
+ ],
74
+ "sha": "fdf4e14",
75
+ "scripts": {}
76
+ }
package/preset.cjs ADDED
@@ -0,0 +1,37 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }require('./chunk-P4DSWCF6.cjs');
2
+
3
+ // src/preset.ts
4
+ var _presetvite = require('@preact/preset-vite'); var _presetvite2 = _interopRequireDefault(_presetvite);
5
+ var CLIENT_ENTRY = "@foxford/den-preact/client";
6
+ var STYLED = "styled-components";
7
+ var runtimeSingleton = {
8
+ config: () => ({
9
+ resolve: { dedupe: ["preact", "preact-render-to-string"] },
10
+ ssr: { external: ["preact", "preact-render-to-string"] }
11
+ }),
12
+ name: "den-preact:runtime-singleton"
13
+ };
14
+ function preact(options = {}) {
15
+ var _a, _b;
16
+ const plugins = (_b = (_a = options.babel) == null ? void 0 : _a.plugins) != null ? _b : [];
17
+ return {
18
+ clientEntry: CLIENT_ENTRY,
19
+ // Prefresh выключен: у приложения нет dev-сервера сборщика — `den dev` пересобирает
20
+ // выход и перезапускает процесс.
21
+ plugins: [_presetvite2.default.call(void 0, { babel: { plugins }, prefreshEnabled: false }), runtimeSingleton],
22
+ // Проверка тут потому, что цена ошибки — МОЛЧАНИЕ. Без сборочной поддержки
23
+ // styled-components считает идентификатор компонента счётчиком: порядок вычисления в
24
+ // серверном и клиентском выходах разный, имена классов расходятся, и это видно только
25
+ // рухнувшей гидрацией в браузере.
26
+ validate: (dependencies) => {
27
+ if (!dependencies.includes(STYLED) || JSON.stringify(plugins).includes(STYLED)) {
28
+ return null;
29
+ }
30
+ return `\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \u0437\u0430\u0432\u0438\u0441\u0438\u0442 \u043E\u0442 ${STYLED}, \u043D\u043E \u0432 \u043F\u0440\u0435\u0441\u0435\u0442\u0435 \u043D\u0435\u0442 \u0435\u0433\u043E babel-\u043F\u043B\u0430\u0433\u0438\u043D\u0430. \u0411\u0435\u0437 \u043D\u0435\u0433\u043E \u0438\u043C\u0435\u043D\u0430 \u043A\u043B\u0430\u0441\u0441\u043E\u0432 \u0440\u0430\u0441\u0445\u043E\u0434\u044F\u0442\u0441\u044F \u043C\u0435\u0436\u0434\u0443 \u0441\u0435\u0440\u0432\u0435\u0440\u043D\u044B\u043C \u0438 \u043A\u043B\u0438\u0435\u043D\u0442\u0441\u043A\u0438\u043C \u0432\u044B\u0445\u043E\u0434\u043E\u043C, \u0438 \u0433\u0438\u0434\u0440\u0430\u0446\u0438\u044F \u0440\u0443\u0448\u0438\u0442\u0441\u044F \u043D\u0430 \u043A\u0430\u0436\u0434\u043E\u043C \u0443\u0437\u043B\u0435. \u041E\u0431\u044A\u044F\u0432\u0438\u0442\u0435 \u0435\u0433\u043E \u0432 \u043A\u043E\u043D\u0444\u0438\u0433\u0435: preact({ babel: { plugins: [['babel-plugin-${STYLED}', { displayName: true, ssr: true }]] } })`;
31
+ },
32
+ view: "preact"
33
+ };
34
+ }
35
+
36
+
37
+ exports.preact = preact;
package/preset.d.cts ADDED
@@ -0,0 +1,18 @@
1
+ import { AppBuildPreset } from '@foxford/den/build';
2
+
3
+ interface PreactOptions {
4
+ /**
5
+ * Babel-плагины приложения. Пресет их не выбирает: слой стилей — специфика приложения.
6
+ */
7
+ babel?: {
8
+ plugins?: unknown[];
9
+ };
10
+ }
11
+ /**
12
+ * Пресет preact-приложения.
13
+ *
14
+ * @param options - Babel-плагины приложения
15
+ */
16
+ declare function preact(options?: PreactOptions): AppBuildPreset;
17
+
18
+ export { type PreactOptions, preact };
package/preset.d.ts ADDED
@@ -0,0 +1,18 @@
1
+ import { AppBuildPreset } from '@foxford/den/build';
2
+
3
+ interface PreactOptions {
4
+ /**
5
+ * Babel-плагины приложения. Пресет их не выбирает: слой стилей — специфика приложения.
6
+ */
7
+ babel?: {
8
+ plugins?: unknown[];
9
+ };
10
+ }
11
+ /**
12
+ * Пресет preact-приложения.
13
+ *
14
+ * @param options - Babel-плагины приложения
15
+ */
16
+ declare function preact(options?: PreactOptions): AppBuildPreset;
17
+
18
+ export { type PreactOptions, preact };
package/preset.js ADDED
@@ -0,0 +1,37 @@
1
+ import "./chunk-5JBD5THX.js";
2
+
3
+ // src/preset.ts
4
+ import preactPlugin from "@preact/preset-vite";
5
+ var CLIENT_ENTRY = "@foxford/den-preact/client";
6
+ var STYLED = "styled-components";
7
+ var runtimeSingleton = {
8
+ config: () => ({
9
+ resolve: { dedupe: ["preact", "preact-render-to-string"] },
10
+ ssr: { external: ["preact", "preact-render-to-string"] }
11
+ }),
12
+ name: "den-preact:runtime-singleton"
13
+ };
14
+ function preact(options = {}) {
15
+ var _a, _b;
16
+ const plugins = (_b = (_a = options.babel) == null ? void 0 : _a.plugins) != null ? _b : [];
17
+ return {
18
+ clientEntry: CLIENT_ENTRY,
19
+ // Prefresh выключен: у приложения нет dev-сервера сборщика — `den dev` пересобирает
20
+ // выход и перезапускает процесс.
21
+ plugins: [preactPlugin({ babel: { plugins }, prefreshEnabled: false }), runtimeSingleton],
22
+ // Проверка тут потому, что цена ошибки — МОЛЧАНИЕ. Без сборочной поддержки
23
+ // styled-components считает идентификатор компонента счётчиком: порядок вычисления в
24
+ // серверном и клиентском выходах разный, имена классов расходятся, и это видно только
25
+ // рухнувшей гидрацией в браузере.
26
+ validate: (dependencies) => {
27
+ if (!dependencies.includes(STYLED) || JSON.stringify(plugins).includes(STYLED)) {
28
+ return null;
29
+ }
30
+ return `\u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \u0437\u0430\u0432\u0438\u0441\u0438\u0442 \u043E\u0442 ${STYLED}, \u043D\u043E \u0432 \u043F\u0440\u0435\u0441\u0435\u0442\u0435 \u043D\u0435\u0442 \u0435\u0433\u043E babel-\u043F\u043B\u0430\u0433\u0438\u043D\u0430. \u0411\u0435\u0437 \u043D\u0435\u0433\u043E \u0438\u043C\u0435\u043D\u0430 \u043A\u043B\u0430\u0441\u0441\u043E\u0432 \u0440\u0430\u0441\u0445\u043E\u0434\u044F\u0442\u0441\u044F \u043C\u0435\u0436\u0434\u0443 \u0441\u0435\u0440\u0432\u0435\u0440\u043D\u044B\u043C \u0438 \u043A\u043B\u0438\u0435\u043D\u0442\u0441\u043A\u0438\u043C \u0432\u044B\u0445\u043E\u0434\u043E\u043C, \u0438 \u0433\u0438\u0434\u0440\u0430\u0446\u0438\u044F \u0440\u0443\u0448\u0438\u0442\u0441\u044F \u043D\u0430 \u043A\u0430\u0436\u0434\u043E\u043C \u0443\u0437\u043B\u0435. \u041E\u0431\u044A\u044F\u0432\u0438\u0442\u0435 \u0435\u0433\u043E \u0432 \u043A\u043E\u043D\u0444\u0438\u0433\u0435: preact({ babel: { plugins: [['babel-plugin-${STYLED}', { displayName: true, ssr: true }]] } })`;
31
+ },
32
+ view: "preact"
33
+ };
34
+ }
35
+ export {
36
+ preact
37
+ };