@foxford/den 3.3.0 → 3.5.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 CHANGED
@@ -84,9 +84,16 @@ const { status, html, state, head, headHtml, redirect, assets } = await renderAp
84
84
  pathname: '/legal/general',
85
85
  search: '?from=footer',
86
86
  context: { cookies, headers }, // реквизиты браузерного запроса
87
+ inputs: { 'host:User': user, 'host:Settings': settings }, // входные данные хоста по ключу token.description
87
88
  })
88
89
  ```
89
90
 
91
+ `inputs` — то, что хост знает про запрос и отдаёт приложению данными: посетитель, настройки
92
+ площадки, эксперименты (токены — в `@foxford/contracts`). Приложение объявляет, что принимает,
93
+ полем `inputs` дескриптора и читает через `requires`; ядро биндит объявленное в контейнер
94
+ острова, кладёт в `state` рядом с VM и в браузере биндит оттуда же — единица не различает
95
+ сторон. Не объявленное в контейнер не попадает, не присланное не биндится.
96
+
90
97
  `status` — исход запроса: `200` значит «вот страница», всё остальное значит, что страницы по
91
98
  этому адресу нет, и тело такого ответа выбирает хост. `state` едет в документ и гидрирует
92
99
  остров в браузере, `headHtml` — стили, собранные во время рендера. `assets` — ссылки на
@@ -177,11 +184,16 @@ describeDocument(): DocumentContribution {
177
184
 
178
185
  Рантайм вокруг дескриптора отдаёт три ручки:
179
186
 
180
- | Ручка | Ответ |
181
- | -------------------------------- | ------------------------------------------- |
182
- | `GET /_render?url=<path+search>` | `200` + ответ `renderApp` телом |
183
- | `GET /_routes` | `200` + массив regex-строк заявки на адреса |
184
- | `GET /_health` | `200 ok` |
187
+ | Ручка | Ответ |
188
+ | -------------------------------------- | ------------------------------------------- |
189
+ | `QUERY /_render` + `{ url, inputs? }` | `200` + ответ `renderApp` телом |
190
+ | `GET /_render?url=<path+search>` | то же без входных данных хоста |
191
+ | `GET /_routes` | `200` + массив regex-строк заявки на адреса |
192
+ | `GET /_health` | `200 ok` |
193
+
194
+ `QUERY` — безопасный метод с телом (RFC 9110): адрес и входные данные хоста едут JSON-ом,
195
+ потому что заголовкам они не по размеру. `GET` остаётся для хоста, который входных данных
196
+ не шлёт.
185
197
 
186
198
  **Статус HTTP описывает транспорт, а исход страницы едет полем `status` в теле.** `200` значит
187
199
  «приложение ответило» — хоть `404`, хоть редиректом. Всё остальное значит «до приложения не
package/adapter.d.cts CHANGED
@@ -1,4 +1,4 @@
1
- export { R as RequestContext } from './types-Dx5qGiwk.cjs';
1
+ export { R as RequestContext } from './types-BxMQ-VOd.cjs';
2
2
  import { Token } from '@foxford/ioc';
3
3
 
4
4
  /**
package/adapter.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- export { R as RequestContext } from './types-Dx5qGiwk.js';
1
+ export { R as RequestContext } from './types-BxMQ-VOd.js';
2
2
  import { Token } from '@foxford/ioc';
3
3
 
4
4
  /**
@@ -19,6 +19,57 @@ function isDocumentSource(value) {
19
19
  return typeof value === "object" && value !== null && typeof value.describeDocument === "function";
20
20
  }
21
21
 
22
+ // src/island/inputs.ts
23
+ function islandInputsOf(descriptor, source) {
24
+ var _a;
25
+ const inputs = {};
26
+ if (source === void 0) {
27
+ return inputs;
28
+ }
29
+ for (const token of (_a = descriptor.requires) != null ? _a : []) {
30
+ const value = source[token.description];
31
+ if (value !== void 0) {
32
+ inputs[token.description] = value;
33
+ }
34
+ }
35
+ return inputs;
36
+ }
37
+ function bindIslandInputs(container, descriptor, inputs) {
38
+ var _a;
39
+ if (inputs === void 0) {
40
+ return;
41
+ }
42
+ for (const token of (_a = descriptor.requires) != null ? _a : []) {
43
+ const value = inputs[token.description];
44
+ if (value !== void 0) {
45
+ container.bind(token).toValue(value);
46
+ }
47
+ }
48
+ }
49
+ function parseCookieHeader(header) {
50
+ const cookies = {};
51
+ for (const part of (header != null ? header : "").split(";")) {
52
+ const eq = part.indexOf("=");
53
+ if (eq < 1) {
54
+ continue;
55
+ }
56
+ const name = part.slice(0, eq).trim();
57
+ if (name && !(name in cookies)) {
58
+ cookies[name] = part.slice(eq + 1).trim();
59
+ }
60
+ }
61
+ return cookies;
62
+ }
63
+ function browserRequestContext() {
64
+ const cookie = typeof document === "undefined" ? void 0 : document.cookie;
65
+ return { cookies: parseCookieHeader(cookie), headers: {} };
66
+ }
67
+ function bindRequestContext(container, context) {
68
+ if (context !== void 0) {
69
+ container.bind(_chunk6QV4L6R2cjs.RequestContextToken).toValue(context);
70
+ }
71
+ }
72
+
22
73
  // src/island/runtime.ts
23
74
  var _ioc = require('@foxford/ioc');
24
75
  var appContainer = null;
@@ -55,12 +106,14 @@ function registerIslandParts(container, descriptor, islandLog) {
55
106
  }
56
107
  function createIslandContainer(descriptor, options = {}) {
57
108
  var _a, _b, _c;
58
- const { parent = getAppContainer() } = options;
109
+ const { context, inputs, parent = getAppContainer() } = options;
59
110
  const appLog = (_b = _logger.log.getLogger((_a = descriptor.name) != null ? _a : "app")) != null ? _b : _chunkA6ZPAM6Zcjs.logger;
60
111
  const islandLog = (_c = appLog.getLogger("client")) != null ? _c : appLog;
61
112
  try {
62
113
  const container = parent.createChild();
63
114
  container.bind(_chunkA6ZPAM6Zcjs.LoggerToken).toValue(islandLog);
115
+ bindRequestContext(container, context);
116
+ bindIslandInputs(container, descriptor, inputs);
64
117
  registerIslandParts(container, descriptor, islandLog);
65
118
  return container;
66
119
  } catch (error) {
@@ -166,14 +219,12 @@ function renderApp(descriptor, request) {
166
219
  pathname: request.pathname,
167
220
  search: (_b = request.search) != null ? _b : ""
168
221
  };
169
- const container = createIslandContainer(descriptor, { parent: request.parent });
222
+ const inputs = islandInputsOf(descriptor, request.inputs);
223
+ const container = createIslandContainer(descriptor, { context: request.context, inputs, parent: request.parent });
170
224
  if (container === null) {
171
225
  throw new Error(`den/island: \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB \u043D\u0435 \u0441\u043E\u0431\u0440\u0430\u043B\u043E\u0441\u044C \u2014 \u0440\u0435\u043D\u0434\u0435\u0440 \u043D\u0435\u0432\u043E\u0437\u043C\u043E\u0436\u0435\u043D`);
172
226
  }
173
227
  try {
174
- if (request.context) {
175
- container.bind(_chunk6QV4L6R2cjs.RequestContextToken).toValue(request.context);
176
- }
177
228
  yield activateIslandViewModels(container, descriptor, route);
178
229
  const contribution = collectDocumentContribution(container, descriptor);
179
230
  const { data, head, redirect, status = STATUS_OK } = contribution;
@@ -181,7 +232,7 @@ function renderApp(descriptor, request) {
181
232
  return { data, head, html: "", redirect, state: {}, status };
182
233
  }
183
234
  const assets = (_c = contribution.assets) != null ? _c : descriptor.assets;
184
- const state = collectIslandState(container, descriptor);
235
+ const state = _chunkT5QVCXVBcjs.__spreadValues.call(void 0, _chunkT5QVCXVBcjs.__spreadValues.call(void 0, {}, inputs), collectIslandState(container, descriptor));
185
236
  if (descriptor.view === void 0 || descriptor.viewLayer === void 0) {
186
237
  return { assets, data, head, html: "", state, status };
187
238
  }
@@ -242,4 +293,9 @@ function pathPattern(pattern) {
242
293
 
243
294
 
244
295
 
245
- exports.isDocumentSource = isDocumentSource; exports.getAppContainer = getAppContainer; exports.createIslandContainer = createIslandContainer; exports.hydrateIslandState = hydrateIslandState; exports.activateIslandViewModels = activateIslandViewModels; exports.collectIslandState = collectIslandState; exports.collectDocumentContribution = collectDocumentContribution; exports.resolveEagerUnits = resolveEagerUnits; exports.renderApp = renderApp; exports.normalizeRoutes = normalizeRoutes; exports.matchRoute = matchRoute; exports.pathPattern = pathPattern;
296
+
297
+
298
+
299
+
300
+
301
+ exports.isDocumentSource = isDocumentSource; exports.islandInputsOf = islandInputsOf; exports.bindIslandInputs = bindIslandInputs; exports.parseCookieHeader = parseCookieHeader; exports.browserRequestContext = browserRequestContext; exports.bindRequestContext = bindRequestContext; exports.getAppContainer = getAppContainer; exports.createIslandContainer = createIslandContainer; exports.hydrateIslandState = hydrateIslandState; exports.activateIslandViewModels = activateIslandViewModels; exports.collectIslandState = collectIslandState; exports.collectDocumentContribution = collectDocumentContribution; exports.resolveEagerUnits = resolveEagerUnits; exports.renderApp = renderApp; exports.normalizeRoutes = normalizeRoutes; exports.matchRoute = matchRoute; exports.pathPattern = pathPattern;
@@ -19,6 +19,57 @@ function isDocumentSource(value) {
19
19
  return typeof value === "object" && value !== null && typeof value.describeDocument === "function";
20
20
  }
21
21
 
22
+ // src/island/inputs.ts
23
+ function islandInputsOf(descriptor, source) {
24
+ var _a;
25
+ const inputs = {};
26
+ if (source === void 0) {
27
+ return inputs;
28
+ }
29
+ for (const token of (_a = descriptor.requires) != null ? _a : []) {
30
+ const value = source[token.description];
31
+ if (value !== void 0) {
32
+ inputs[token.description] = value;
33
+ }
34
+ }
35
+ return inputs;
36
+ }
37
+ function bindIslandInputs(container, descriptor, inputs) {
38
+ var _a;
39
+ if (inputs === void 0) {
40
+ return;
41
+ }
42
+ for (const token of (_a = descriptor.requires) != null ? _a : []) {
43
+ const value = inputs[token.description];
44
+ if (value !== void 0) {
45
+ container.bind(token).toValue(value);
46
+ }
47
+ }
48
+ }
49
+ function parseCookieHeader(header) {
50
+ const cookies = {};
51
+ for (const part of (header != null ? header : "").split(";")) {
52
+ const eq = part.indexOf("=");
53
+ if (eq < 1) {
54
+ continue;
55
+ }
56
+ const name = part.slice(0, eq).trim();
57
+ if (name && !(name in cookies)) {
58
+ cookies[name] = part.slice(eq + 1).trim();
59
+ }
60
+ }
61
+ return cookies;
62
+ }
63
+ function browserRequestContext() {
64
+ const cookie = typeof document === "undefined" ? void 0 : document.cookie;
65
+ return { cookies: parseCookieHeader(cookie), headers: {} };
66
+ }
67
+ function bindRequestContext(container, context) {
68
+ if (context !== void 0) {
69
+ container.bind(RequestContextToken).toValue(context);
70
+ }
71
+ }
72
+
22
73
  // src/island/runtime.ts
23
74
  import { Container } from "@foxford/ioc";
24
75
  var appContainer = null;
@@ -55,12 +106,14 @@ function registerIslandParts(container, descriptor, islandLog) {
55
106
  }
56
107
  function createIslandContainer(descriptor, options = {}) {
57
108
  var _a, _b, _c;
58
- const { parent = getAppContainer() } = options;
109
+ const { context, inputs, parent = getAppContainer() } = options;
59
110
  const appLog = (_b = log.getLogger((_a = descriptor.name) != null ? _a : "app")) != null ? _b : logger;
60
111
  const islandLog = (_c = appLog.getLogger("client")) != null ? _c : appLog;
61
112
  try {
62
113
  const container = parent.createChild();
63
114
  container.bind(LoggerToken).toValue(islandLog);
115
+ bindRequestContext(container, context);
116
+ bindIslandInputs(container, descriptor, inputs);
64
117
  registerIslandParts(container, descriptor, islandLog);
65
118
  return container;
66
119
  } catch (error) {
@@ -166,14 +219,12 @@ function renderApp(descriptor, request) {
166
219
  pathname: request.pathname,
167
220
  search: (_b = request.search) != null ? _b : ""
168
221
  };
169
- const container = createIslandContainer(descriptor, { parent: request.parent });
222
+ const inputs = islandInputsOf(descriptor, request.inputs);
223
+ const container = createIslandContainer(descriptor, { context: request.context, inputs, parent: request.parent });
170
224
  if (container === null) {
171
225
  throw new Error(`den/island: \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \xAB${descriptor.name}\xBB \u043D\u0435 \u0441\u043E\u0431\u0440\u0430\u043B\u043E\u0441\u044C \u2014 \u0440\u0435\u043D\u0434\u0435\u0440 \u043D\u0435\u0432\u043E\u0437\u043C\u043E\u0436\u0435\u043D`);
172
226
  }
173
227
  try {
174
- if (request.context) {
175
- container.bind(RequestContextToken).toValue(request.context);
176
- }
177
228
  yield activateIslandViewModels(container, descriptor, route);
178
229
  const contribution = collectDocumentContribution(container, descriptor);
179
230
  const { data, head, redirect, status = STATUS_OK } = contribution;
@@ -181,7 +232,7 @@ function renderApp(descriptor, request) {
181
232
  return { data, head, html: "", redirect, state: {}, status };
182
233
  }
183
234
  const assets = (_c = contribution.assets) != null ? _c : descriptor.assets;
184
- const state = collectIslandState(container, descriptor);
235
+ const state = __spreadValues(__spreadValues({}, inputs), collectIslandState(container, descriptor));
185
236
  if (descriptor.view === void 0 || descriptor.viewLayer === void 0) {
186
237
  return { assets, data, head, html: "", state, status };
187
238
  }
@@ -231,6 +282,11 @@ function pathPattern(pattern) {
231
282
 
232
283
  export {
233
284
  isDocumentSource,
285
+ islandInputsOf,
286
+ bindIslandInputs,
287
+ parseCookieHeader,
288
+ browserRequestContext,
289
+ bindRequestContext,
234
290
  getAppContainer,
235
291
  createIslandContainer,
236
292
  hydrateIslandState,
@@ -1,4 +1,4 @@
1
- import { a as DefineServiceOptions, S as ServiceDefinition, b as DefineViewModelOptions, V as ViewModelDefinition, D as DefineRepositoryOptions, d as RepositoryDefinition } from './types-Dx5qGiwk.js';
1
+ import { a as DefineServiceOptions, S as ServiceDefinition, b as DefineViewModelOptions, V as ViewModelDefinition, D as DefineRepositoryOptions, d as RepositoryDefinition } from './types-BxMQ-VOd.js';
2
2
  import { Token } from '@foxford/ioc';
3
3
 
4
4
  /**
@@ -1,4 +1,4 @@
1
- import { a as DefineServiceOptions, S as ServiceDefinition, b as DefineViewModelOptions, V as ViewModelDefinition, D as DefineRepositoryOptions, d as RepositoryDefinition } from './types-Dx5qGiwk.cjs';
1
+ import { a as DefineServiceOptions, S as ServiceDefinition, b as DefineViewModelOptions, V as ViewModelDefinition, D as DefineRepositoryOptions, d as RepositoryDefinition } from './types-BxMQ-VOd.cjs';
2
2
  import { Token } from '@foxford/ioc';
3
3
 
4
4
  /**
@@ -1,4 +1,4 @@
1
- import { c as Definition, L as LayerDefinition } from './types-Dx5qGiwk.cjs';
1
+ import { c as Definition, L as LayerDefinition } from './types-BxMQ-VOd.cjs';
2
2
  import { Container } from '@foxford/ioc';
3
3
 
4
4
  /**
@@ -1,4 +1,4 @@
1
- import { c as Definition, L as LayerDefinition } from './types-Dx5qGiwk.js';
1
+ import { c as Definition, L as LayerDefinition } from './types-BxMQ-VOd.js';
2
2
  import { Container } from '@foxford/ioc';
3
3
 
4
4
  /**
package/define.d.cts CHANGED
@@ -1,6 +1,6 @@
1
- export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-CwAXed2X.cjs';
2
- export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-DouHW8RK.cjs';
3
- export { D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, d as RepositoryDefinition, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, V as ViewModelDefinition } from './types-Dx5qGiwk.cjs';
1
+ export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-C0MI-J32.cjs';
2
+ export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-BEeHNEph.cjs';
3
+ export { D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, d as RepositoryDefinition, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, V as ViewModelDefinition } from './types-BxMQ-VOd.cjs';
4
4
  import { Token, Container } from '@foxford/ioc';
5
5
  import { HierarchicalLogger } from '@foxford/logger';
6
6
 
package/define.d.ts CHANGED
@@ -1,6 +1,6 @@
1
- export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-q_T4hqeP.js';
2
- export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-TkqbLySB.js';
3
- export { D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, d as RepositoryDefinition, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, V as ViewModelDefinition } from './types-Dx5qGiwk.js';
1
+ export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-AO7JI6Cb.js';
2
+ export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-CdWdFM16.js';
3
+ export { D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, d as RepositoryDefinition, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, V as ViewModelDefinition } from './types-BxMQ-VOd.js';
4
4
  import { Token, Container } from '@foxford/ioc';
5
5
  import { HierarchicalLogger } from '@foxford/logger';
6
6
 
@@ -1,5 +1,5 @@
1
- import { S as SlotDefinition } from './define-slot-TkqbLySB.js';
2
- import { L as LayerDefinition, c as Definition } from './types-Dx5qGiwk.js';
1
+ import { S as SlotDefinition } from './define-slot-CdWdFM16.js';
2
+ import { L as LayerDefinition, c as Definition } from './types-BxMQ-VOd.js';
3
3
  import { Token } from '@foxford/ioc';
4
4
 
5
5
  /**
@@ -50,6 +50,18 @@ interface IslandDescriptor {
50
50
  * ездит через denState.
51
51
  */
52
52
  viewModels?: ReadonlyArray<Definition<unknown>>;
53
+ /**
54
+ * Что приложению нужно от хоста: токены из `@foxford/contracts` — посетитель, настройки
55
+ * площадки, конфиг транспорта, эксперименты.
56
+ *
57
+ * Заявку на данные закрывает ядро: объявленные токены биндятся в контейнер острова из
58
+ * входных данных хоста (на сервере из запроса, в браузере из состояния документа), и они
59
+ * едут одинаково обоими транспортами — аргументом `renderApp` в процессе хоста и телом
60
+ * запроса за сетью. Заявку на живой код (возможность другого приложения) закрывает
61
+ * исполнитель по своим правилам — по сети такое не ездит, ядро о ней не знает.
62
+ * Единицы читают полученное через свой `requires`. Не объявленное не биндится.
63
+ */
64
+ requires?: ReadonlyArray<Token<unknown>>;
53
65
  /**
54
66
  * Единицы, которые обязаны жить с загрузки, а не с первого резолва.
55
67
  *
@@ -1,5 +1,5 @@
1
- import { S as SlotDefinition } from './define-slot-DouHW8RK.cjs';
2
- import { L as LayerDefinition, c as Definition } from './types-Dx5qGiwk.cjs';
1
+ import { S as SlotDefinition } from './define-slot-BEeHNEph.cjs';
2
+ import { L as LayerDefinition, c as Definition } from './types-BxMQ-VOd.cjs';
3
3
  import { Token } from '@foxford/ioc';
4
4
 
5
5
  /**
@@ -50,6 +50,18 @@ interface IslandDescriptor {
50
50
  * ездит через denState.
51
51
  */
52
52
  viewModels?: ReadonlyArray<Definition<unknown>>;
53
+ /**
54
+ * Что приложению нужно от хоста: токены из `@foxford/contracts` — посетитель, настройки
55
+ * площадки, конфиг транспорта, эксперименты.
56
+ *
57
+ * Заявку на данные закрывает ядро: объявленные токены биндятся в контейнер острова из
58
+ * входных данных хоста (на сервере из запроса, в браузере из состояния документа), и они
59
+ * едут одинаково обоими транспортами — аргументом `renderApp` в процессе хоста и телом
60
+ * запроса за сетью. Заявку на живой код (возможность другого приложения) закрывает
61
+ * исполнитель по своим правилам — по сети такое не ездит, ядро о ней не знает.
62
+ * Единицы читают полученное через свой `requires`. Не объявленное не биндится.
63
+ */
64
+ requires?: ReadonlyArray<Token<unknown>>;
53
65
  /**
54
66
  * Единицы, которые обязаны жить с загрузки, а не с первого резолва.
55
67
  *
package/index.d.cts CHANGED
@@ -1,11 +1,11 @@
1
- import { C as Core, i as ContainerManager, R as RequestContext, j as GuardRunner, k as Guard, l as GuardResult, N as NavigationManager, m as NavigationEntry, n as NavigationInterceptor, o as Disposable, p as LeaveGuardResult, q as StateSerializer, r as DefineGuardOptions, G as GuardDefinition, E as ExtensionConfig, s as DefineExtensionOptions, t as ExtensionDefinition, A as ActionGuard, u as DefineActionGuardOptions, v as ActionGuardDefinition, w as LayoutConfig, x as DefineLayoutOptions, y as LayoutDefinition, h as LayerConfig, z as DefineLayerOptions, L as LayerDefinition } from './types-Dx5qGiwk.cjs';
2
- export { B as Activatable, F as ActivatableToken, H as ContainerManagerToken, D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, I as GuardRunnerToken, J as NavigationManagerToken, d as RepositoryDefinition, K as RequestContextToken, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, M as StateCache, O as StateParticipant, P as StateRegistry, Q as StateRegistryToken, T as StateSerializerToken, V as ViewModelDefinition } from './types-Dx5qGiwk.cjs';
1
+ import { C as Core, j as ContainerManager, R as RequestContext, k as GuardRunner, l as Guard, m as GuardResult, N as NavigationManager, n as NavigationEntry, o as NavigationInterceptor, p as Disposable, q as LeaveGuardResult, r as StateSerializer, s as DefineGuardOptions, G as GuardDefinition, E as ExtensionConfig, t as DefineExtensionOptions, u as ExtensionDefinition, A as ActionGuard, v as DefineActionGuardOptions, w as ActionGuardDefinition, x as LayoutConfig, y as DefineLayoutOptions, z as LayoutDefinition, h as LayerConfig, B as DefineLayerOptions, L as LayerDefinition } from './types-BxMQ-VOd.cjs';
2
+ export { F as Activatable, H as ActivatableToken, I as ContainerManagerToken, D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, J as GuardRunnerToken, K as NavigationManagerToken, d as RepositoryDefinition, i as RequestContextToken, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, M as StateCache, O as StateParticipant, P as StateRegistry, Q as StateRegistryToken, T as StateSerializerToken, V as ViewModelDefinition } from './types-BxMQ-VOd.cjs';
3
3
  import { Container, Token } from '@foxford/ioc';
4
4
  import { DefinitionResolver } from './adapter.cjs';
5
- export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-CwAXed2X.cjs';
6
- export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-DouHW8RK.cjs';
7
- export { V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken } from './view-adapter-DF1me25J.cjs';
8
- import './descriptor-w8oxeIAe.cjs';
5
+ export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-C0MI-J32.cjs';
6
+ export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-BEeHNEph.cjs';
7
+ export { V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken } from './view-adapter-DMLlp3Iu.cjs';
8
+ import './descriptor-C2j6Zz6c.cjs';
9
9
  import './server-render-CocWXQKC.cjs';
10
10
 
11
11
  /**
package/index.d.ts CHANGED
@@ -1,11 +1,11 @@
1
- import { C as Core, i as ContainerManager, R as RequestContext, j as GuardRunner, k as Guard, l as GuardResult, N as NavigationManager, m as NavigationEntry, n as NavigationInterceptor, o as Disposable, p as LeaveGuardResult, q as StateSerializer, r as DefineGuardOptions, G as GuardDefinition, E as ExtensionConfig, s as DefineExtensionOptions, t as ExtensionDefinition, A as ActionGuard, u as DefineActionGuardOptions, v as ActionGuardDefinition, w as LayoutConfig, x as DefineLayoutOptions, y as LayoutDefinition, h as LayerConfig, z as DefineLayerOptions, L as LayerDefinition } from './types-Dx5qGiwk.js';
2
- export { B as Activatable, F as ActivatableToken, H as ContainerManagerToken, D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, I as GuardRunnerToken, J as NavigationManagerToken, d as RepositoryDefinition, K as RequestContextToken, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, M as StateCache, O as StateParticipant, P as StateRegistry, Q as StateRegistryToken, T as StateSerializerToken, V as ViewModelDefinition } from './types-Dx5qGiwk.js';
1
+ import { C as Core, j as ContainerManager, R as RequestContext, k as GuardRunner, l as Guard, m as GuardResult, N as NavigationManager, n as NavigationEntry, o as NavigationInterceptor, p as Disposable, q as LeaveGuardResult, r as StateSerializer, s as DefineGuardOptions, G as GuardDefinition, E as ExtensionConfig, t as DefineExtensionOptions, u as ExtensionDefinition, A as ActionGuard, v as DefineActionGuardOptions, w as ActionGuardDefinition, x as LayoutConfig, y as DefineLayoutOptions, z as LayoutDefinition, h as LayerConfig, B as DefineLayerOptions, L as LayerDefinition } from './types-BxMQ-VOd.js';
2
+ export { F as Activatable, H as ActivatableToken, I as ContainerManagerToken, D as DefineRepositoryOptions, a as DefineServiceOptions, b as DefineViewModelOptions, c as Definition, J as GuardRunnerToken, K as NavigationManagerToken, d as RepositoryDefinition, i as RequestContextToken, S as ServiceDefinition, e as SlotEntry, f as SlotRegistry, g as SlotRegistryToken, M as StateCache, O as StateParticipant, P as StateRegistry, Q as StateRegistryToken, T as StateSerializerToken, V as ViewModelDefinition } from './types-BxMQ-VOd.js';
3
3
  import { Container, Token } from '@foxford/ioc';
4
4
  import { DefinitionResolver } from './adapter.js';
5
- export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-q_T4hqeP.js';
6
- export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-TkqbLySB.js';
7
- export { V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken } from './view-adapter-BV62bdhM.js';
8
- import './descriptor-tWPa9j-x.js';
5
+ export { d as defineRepository, a as defineService, b as defineViewModel } from './define-repository-AO7JI6Cb.js';
6
+ export { D as DefineSlotOptions, S as SlotDefinition, d as defineSlot } from './define-slot-CdWdFM16.js';
7
+ export { V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken } from './view-adapter-DNLRSFka.js';
8
+ import './descriptor-BSaHM5B4.js';
9
9
  import './server-render-CocWXQKC.js';
10
10
 
11
11
  /**
package/island/index.cjs CHANGED
@@ -11,13 +11,20 @@
11
11
 
12
12
 
13
13
 
14
- var _chunkXDM6J4LJcjs = require('../chunk-XDM6J4LJ.cjs');
14
+
15
+
16
+
17
+
18
+
19
+ var _chunkJMRHLOBDcjs = require('../chunk-JMRHLOBD.cjs');
15
20
 
16
21
 
17
22
 
18
23
 
19
24
  var _chunkXOJ2VWX4cjs = require('../chunk-XOJ2VWX4.cjs');
20
- require('../chunk-6QV4L6R2.cjs');
25
+
26
+
27
+ var _chunk6QV4L6R2cjs = require('../chunk-6QV4L6R2.cjs');
21
28
  require('../chunk-A6ZPAM6Z.cjs');
22
29
 
23
30
 
@@ -139,4 +146,10 @@ function describeIsland(descriptor, denState) {
139
146
 
140
147
 
141
148
 
142
- exports.DOCUMENT_EVENT = DOCUMENT_EVENT; exports.ISLAND_ERRORS_KEY = ISLAND_ERRORS_KEY; exports.NAVIGATE_EVENT = NAVIGATE_EVENT; exports.ViewLayerToken = _chunkXOJ2VWX4cjs.ViewLayerToken; exports.activateIslandViewModels = _chunkXDM6J4LJcjs.activateIslandViewModels; exports.collectDocumentContribution = _chunkXDM6J4LJcjs.collectDocumentContribution; exports.collectIslandState = _chunkXDM6J4LJcjs.collectIslandState; exports.createIslandContainer = _chunkXDM6J4LJcjs.createIslandContainer; exports.describeIsland = describeIsland; exports.getAppContainer = _chunkXDM6J4LJcjs.getAppContainer; exports.getIslandsSnapshot = getIslandsSnapshot; exports.hydrateIslandState = _chunkXDM6J4LJcjs.hydrateIslandState; exports.isDocumentSource = _chunkXDM6J4LJcjs.isDocumentSource; exports.matchRoute = _chunkXDM6J4LJcjs.matchRoute; exports.navigateIsland = navigateIsland; exports.normalizeRoutes = _chunkXDM6J4LJcjs.normalizeRoutes; exports.onIslandDocument = onIslandDocument; exports.onIslandNavigate = onIslandNavigate; exports.pathPattern = _chunkXDM6J4LJcjs.pathPattern; exports.publishIslandDocument = publishIslandDocument; exports.registerIsland = registerIsland; exports.renderApp = _chunkXDM6J4LJcjs.renderApp; exports.reportIslandError = reportIslandError; exports.resolveEagerUnits = _chunkXDM6J4LJcjs.resolveEagerUnits; exports.resolveViewAdapter = _chunkXOJ2VWX4cjs.resolveViewAdapter; exports.slotAddress = slotAddress; exports.subscribeIslands = subscribeIslands; exports.viewAdapterOf = _chunkXOJ2VWX4cjs.viewAdapterOf;
149
+
150
+
151
+
152
+
153
+
154
+
155
+ exports.DOCUMENT_EVENT = DOCUMENT_EVENT; exports.ISLAND_ERRORS_KEY = ISLAND_ERRORS_KEY; exports.NAVIGATE_EVENT = NAVIGATE_EVENT; exports.RequestContextToken = _chunk6QV4L6R2cjs.RequestContextToken; exports.ViewLayerToken = _chunkXOJ2VWX4cjs.ViewLayerToken; exports.activateIslandViewModels = _chunkJMRHLOBDcjs.activateIslandViewModels; exports.bindIslandInputs = _chunkJMRHLOBDcjs.bindIslandInputs; exports.bindRequestContext = _chunkJMRHLOBDcjs.bindRequestContext; exports.browserRequestContext = _chunkJMRHLOBDcjs.browserRequestContext; exports.collectDocumentContribution = _chunkJMRHLOBDcjs.collectDocumentContribution; exports.collectIslandState = _chunkJMRHLOBDcjs.collectIslandState; exports.createIslandContainer = _chunkJMRHLOBDcjs.createIslandContainer; exports.describeIsland = describeIsland; exports.getAppContainer = _chunkJMRHLOBDcjs.getAppContainer; exports.getIslandsSnapshot = getIslandsSnapshot; exports.hydrateIslandState = _chunkJMRHLOBDcjs.hydrateIslandState; exports.isDocumentSource = _chunkJMRHLOBDcjs.isDocumentSource; exports.islandInputsOf = _chunkJMRHLOBDcjs.islandInputsOf; exports.matchRoute = _chunkJMRHLOBDcjs.matchRoute; exports.navigateIsland = navigateIsland; exports.normalizeRoutes = _chunkJMRHLOBDcjs.normalizeRoutes; exports.onIslandDocument = onIslandDocument; exports.onIslandNavigate = onIslandNavigate; exports.parseCookieHeader = _chunkJMRHLOBDcjs.parseCookieHeader; exports.pathPattern = _chunkJMRHLOBDcjs.pathPattern; exports.publishIslandDocument = publishIslandDocument; exports.registerIsland = registerIsland; exports.renderApp = _chunkJMRHLOBDcjs.renderApp; exports.reportIslandError = reportIslandError; exports.resolveEagerUnits = _chunkJMRHLOBDcjs.resolveEagerUnits; exports.resolveViewAdapter = _chunkXOJ2VWX4cjs.resolveViewAdapter; exports.slotAddress = slotAddress; exports.subscribeIslands = subscribeIslands; exports.viewAdapterOf = _chunkXOJ2VWX4cjs.viewAdapterOf;
@@ -1,10 +1,11 @@
1
- import { A as AppAssets, I as IslandDescriptor } from '../descriptor-w8oxeIAe.cjs';
1
+ import { A as AppAssets, I as IslandDescriptor } from '../descriptor-C2j6Zz6c.cjs';
2
+ import { R as RequestContext } from '../types-BxMQ-VOd.cjs';
3
+ export { i as RequestContextToken } from '../types-BxMQ-VOd.cjs';
2
4
  import { Container } from '@foxford/ioc';
3
- import { R as RequestContext } from '../types-Dx5qGiwk.cjs';
4
- export { A as AppRoute, R as RouteDeclaration, a as RouteMatch, m as matchRoute, n as normalizeRoutes, p as pathPattern } from '../routes-B0hDrkiF.cjs';
5
+ export { A as AppRoute, R as RouteDeclaration, a as RouteMatch, m as matchRoute, n as normalizeRoutes, p as pathPattern } from '../routes-BvV405k4.cjs';
5
6
  export { R as RenderTree, a as ServerRender, S as ServerRenderResult } from '../server-render-CocWXQKC.cjs';
6
- export { R as RenderIslandOptions, V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken, r as resolveViewAdapter, v as viewAdapterOf } from '../view-adapter-DF1me25J.cjs';
7
- import '../define-slot-DouHW8RK.cjs';
7
+ export { R as RenderIslandOptions, V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken, r as resolveViewAdapter, v as viewAdapterOf } from '../view-adapter-DMLlp3Iu.cjs';
8
+ import '../define-slot-BEeHNEph.cjs';
8
9
 
9
10
  /** Вклад приложения в `<head>` документа. */
10
11
  interface DocumentHead {
@@ -124,6 +125,18 @@ interface CreateIslandContainerOptions {
124
125
  * сервисы. Хост биндит их один раз в app-контейнер, а резолв поднимается по parent-chain.
125
126
  */
126
127
  parent?: Container;
128
+ /**
129
+ * Реквизиты запроса — заголовки и куки. На сервере их даёт исполнитель (хост либо сетевой
130
+ * рантайм из `X-Forwarded-*`), в браузере адаптер берёт их из документа. Биндятся под
131
+ * `RequestContextToken` до регистрации единиц, поэтому единица вправе их требовать на
132
+ * обеих сторонах.
133
+ */
134
+ context?: RequestContext;
135
+ /**
136
+ * Входные данные хоста по ключу `token.description` — биндятся те, что дескриптор объявил
137
+ * в `requires`. На сервере — из запроса, в браузере — из состояния документа.
138
+ */
139
+ inputs?: Record<string, unknown>;
127
140
  }
128
141
  /**
129
142
  * Собирает контейнер острова: scope-логгер, биндинги хоста, регистрация units + VM + слотов.
@@ -240,6 +253,43 @@ declare function publishIslandDocument(node: EventTarget, contribution: Document
240
253
  */
241
254
  declare function onIslandDocument(node: EventTarget, onDocument: (contribution: DocumentContribution) => void): () => void;
242
255
 
256
+ /**
257
+ * Входные данные, объявленные дескриптором, из переданного набора.
258
+ *
259
+ * @param descriptor - Дескриптор острова
260
+ * @param source - Набор по ключу `token.description`: тело запроса либо состояние документа
261
+ * @returns Только объявленные и присутствующие ключи
262
+ */
263
+ declare function islandInputsOf(descriptor: IslandDescriptor, source: Record<string, unknown> | undefined): Record<string, unknown>;
264
+ /**
265
+ * Биндит входные данные в контейнер острова под объявленными токенами.
266
+ *
267
+ * Не присланное не биндится: единица, которая требует такой токен, упадёт на резолве, и это
268
+ * честный отказ — хост не отдал то, без чего приложение работать не обязано.
269
+ *
270
+ * @param container - Контейнер острова
271
+ * @param descriptor - Дескриптор острова
272
+ * @param inputs - Входные данные по ключу `token.description`
273
+ */
274
+ declare function bindIslandInputs(container: Container, descriptor: IslandDescriptor, inputs: Record<string, unknown> | undefined): void;
275
+ /** Разбирает `Cookie` в карту. Дубли: побеждает первый, как и в браузере. */
276
+ declare function parseCookieHeader(header: string | undefined): Record<string, string>;
277
+ /**
278
+ * Реквизиты запроса в браузере: куки документа, заголовков нет.
279
+ *
280
+ * Биндится в контейнер острова при сборке, чтобы единица, требующая `RequestContextToken`,
281
+ * резолвилась на обеих сторонах одинаково; иначе приложению пришлось бы держать две
282
+ * реализации и переключать их по среде.
283
+ */
284
+ declare function browserRequestContext(): RequestContext;
285
+ /**
286
+ * Биндит реквизиты запроса в контейнер острова.
287
+ *
288
+ * @param container - Контейнер острова
289
+ * @param context - Реквизиты: серверные из `X-Forwarded-*`, браузерные из документа
290
+ */
291
+ declare function bindRequestContext(container: Container, context: RequestContext | undefined): void;
292
+
243
293
  /** Запрос на рендер приложения. */
244
294
  interface RenderAppRequest {
245
295
  /** Путь без search, с ведущим слэшем: `/legal/general`. */
@@ -254,6 +304,12 @@ interface RenderAppRequest {
254
304
  * транспортов: в процессе хоста их даёт хост, за сетью — сетевой рантайм из `X-Forwarded-*`.
255
305
  */
256
306
  context?: RequestContext;
307
+ /**
308
+ * Входные данные хоста по ключу `token.description`: посетитель, настройки, эксперименты.
309
+ * В контейнер попадают только те, что дескриптор объявил в `requires`; они же уезжают в
310
+ * состояние ответа, чтобы остров в браузере получил их вместе с состоянием VM.
311
+ */
312
+ inputs?: Record<string, unknown>;
257
313
  /**
258
314
  * Родитель контейнера приложения: через него приезжает всё, что настроил исполнитель, —
259
315
  * логгер, конфиг HTTP, выданные возможности. По умолчанию — app-scope контейнер.
@@ -356,4 +412,4 @@ declare function getAppContainer(): Container;
356
412
  */
357
413
  declare function slotAddress(app: string, slot: string): string;
358
414
 
359
- export { AppAssets, type CreateIslandContainerOptions, DOCUMENT_EVENT, type DocumentContribution, type DocumentHead, type DocumentSource, ISLAND_ERRORS_KEY, IslandDescriptor, type IslandErrorContext, type IslandErrorPhase, type IslandErrorReport, type IslandRecord, type IslandRoute, NAVIGATE_EVENT, type RenderAppRequest, type RenderAppResult, activateIslandViewModels, collectDocumentContribution, collectIslandState, createIslandContainer, describeIsland, getAppContainer, getIslandsSnapshot, hydrateIslandState, isDocumentSource, navigateIsland, onIslandDocument, onIslandNavigate, publishIslandDocument, registerIsland, renderApp, reportIslandError, resolveEagerUnits, slotAddress, subscribeIslands };
415
+ export { AppAssets, type CreateIslandContainerOptions, DOCUMENT_EVENT, type DocumentContribution, type DocumentHead, type DocumentSource, ISLAND_ERRORS_KEY, IslandDescriptor, type IslandErrorContext, type IslandErrorPhase, type IslandErrorReport, type IslandRecord, type IslandRoute, NAVIGATE_EVENT, type RenderAppRequest, type RenderAppResult, RequestContext, activateIslandViewModels, bindIslandInputs, bindRequestContext, browserRequestContext, collectDocumentContribution, collectIslandState, createIslandContainer, describeIsland, getAppContainer, getIslandsSnapshot, hydrateIslandState, isDocumentSource, islandInputsOf, navigateIsland, onIslandDocument, onIslandNavigate, parseCookieHeader, publishIslandDocument, registerIsland, renderApp, reportIslandError, resolveEagerUnits, slotAddress, subscribeIslands };
package/island/index.d.ts CHANGED
@@ -1,10 +1,11 @@
1
- import { A as AppAssets, I as IslandDescriptor } from '../descriptor-tWPa9j-x.js';
1
+ import { A as AppAssets, I as IslandDescriptor } from '../descriptor-BSaHM5B4.js';
2
+ import { R as RequestContext } from '../types-BxMQ-VOd.js';
3
+ export { i as RequestContextToken } from '../types-BxMQ-VOd.js';
2
4
  import { Container } from '@foxford/ioc';
3
- import { R as RequestContext } from '../types-Dx5qGiwk.js';
4
- export { A as AppRoute, R as RouteDeclaration, a as RouteMatch, m as matchRoute, n as normalizeRoutes, p as pathPattern } from '../routes-0uXJ0fux.js';
5
+ export { A as AppRoute, R as RouteDeclaration, a as RouteMatch, m as matchRoute, n as normalizeRoutes, p as pathPattern } from '../routes-Di3K_0uQ.js';
5
6
  export { R as RenderTree, a as ServerRender, S as ServerRenderResult } from '../server-render-CocWXQKC.js';
6
- export { R as RenderIslandOptions, V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken, r as resolveViewAdapter, v as viewAdapterOf } from '../view-adapter-BV62bdhM.js';
7
- import '../define-slot-TkqbLySB.js';
7
+ export { R as RenderIslandOptions, V as ViewAdapter, a as ViewLayerDefinition, b as ViewLayerToken, r as resolveViewAdapter, v as viewAdapterOf } from '../view-adapter-DNLRSFka.js';
8
+ import '../define-slot-CdWdFM16.js';
8
9
 
9
10
  /** Вклад приложения в `<head>` документа. */
10
11
  interface DocumentHead {
@@ -124,6 +125,18 @@ interface CreateIslandContainerOptions {
124
125
  * сервисы. Хост биндит их один раз в app-контейнер, а резолв поднимается по parent-chain.
125
126
  */
126
127
  parent?: Container;
128
+ /**
129
+ * Реквизиты запроса — заголовки и куки. На сервере их даёт исполнитель (хост либо сетевой
130
+ * рантайм из `X-Forwarded-*`), в браузере адаптер берёт их из документа. Биндятся под
131
+ * `RequestContextToken` до регистрации единиц, поэтому единица вправе их требовать на
132
+ * обеих сторонах.
133
+ */
134
+ context?: RequestContext;
135
+ /**
136
+ * Входные данные хоста по ключу `token.description` — биндятся те, что дескриптор объявил
137
+ * в `requires`. На сервере — из запроса, в браузере — из состояния документа.
138
+ */
139
+ inputs?: Record<string, unknown>;
127
140
  }
128
141
  /**
129
142
  * Собирает контейнер острова: scope-логгер, биндинги хоста, регистрация units + VM + слотов.
@@ -240,6 +253,43 @@ declare function publishIslandDocument(node: EventTarget, contribution: Document
240
253
  */
241
254
  declare function onIslandDocument(node: EventTarget, onDocument: (contribution: DocumentContribution) => void): () => void;
242
255
 
256
+ /**
257
+ * Входные данные, объявленные дескриптором, из переданного набора.
258
+ *
259
+ * @param descriptor - Дескриптор острова
260
+ * @param source - Набор по ключу `token.description`: тело запроса либо состояние документа
261
+ * @returns Только объявленные и присутствующие ключи
262
+ */
263
+ declare function islandInputsOf(descriptor: IslandDescriptor, source: Record<string, unknown> | undefined): Record<string, unknown>;
264
+ /**
265
+ * Биндит входные данные в контейнер острова под объявленными токенами.
266
+ *
267
+ * Не присланное не биндится: единица, которая требует такой токен, упадёт на резолве, и это
268
+ * честный отказ — хост не отдал то, без чего приложение работать не обязано.
269
+ *
270
+ * @param container - Контейнер острова
271
+ * @param descriptor - Дескриптор острова
272
+ * @param inputs - Входные данные по ключу `token.description`
273
+ */
274
+ declare function bindIslandInputs(container: Container, descriptor: IslandDescriptor, inputs: Record<string, unknown> | undefined): void;
275
+ /** Разбирает `Cookie` в карту. Дубли: побеждает первый, как и в браузере. */
276
+ declare function parseCookieHeader(header: string | undefined): Record<string, string>;
277
+ /**
278
+ * Реквизиты запроса в браузере: куки документа, заголовков нет.
279
+ *
280
+ * Биндится в контейнер острова при сборке, чтобы единица, требующая `RequestContextToken`,
281
+ * резолвилась на обеих сторонах одинаково; иначе приложению пришлось бы держать две
282
+ * реализации и переключать их по среде.
283
+ */
284
+ declare function browserRequestContext(): RequestContext;
285
+ /**
286
+ * Биндит реквизиты запроса в контейнер острова.
287
+ *
288
+ * @param container - Контейнер острова
289
+ * @param context - Реквизиты: серверные из `X-Forwarded-*`, браузерные из документа
290
+ */
291
+ declare function bindRequestContext(container: Container, context: RequestContext | undefined): void;
292
+
243
293
  /** Запрос на рендер приложения. */
244
294
  interface RenderAppRequest {
245
295
  /** Путь без search, с ведущим слэшем: `/legal/general`. */
@@ -254,6 +304,12 @@ interface RenderAppRequest {
254
304
  * транспортов: в процессе хоста их даёт хост, за сетью — сетевой рантайм из `X-Forwarded-*`.
255
305
  */
256
306
  context?: RequestContext;
307
+ /**
308
+ * Входные данные хоста по ключу `token.description`: посетитель, настройки, эксперименты.
309
+ * В контейнер попадают только те, что дескриптор объявил в `requires`; они же уезжают в
310
+ * состояние ответа, чтобы остров в браузере получил их вместе с состоянием VM.
311
+ */
312
+ inputs?: Record<string, unknown>;
257
313
  /**
258
314
  * Родитель контейнера приложения: через него приезжает всё, что настроил исполнитель, —
259
315
  * логгер, конфиг HTTP, выданные возможности. По умолчанию — app-scope контейнер.
@@ -356,4 +412,4 @@ declare function getAppContainer(): Container;
356
412
  */
357
413
  declare function slotAddress(app: string, slot: string): string;
358
414
 
359
- export { AppAssets, type CreateIslandContainerOptions, DOCUMENT_EVENT, type DocumentContribution, type DocumentHead, type DocumentSource, ISLAND_ERRORS_KEY, IslandDescriptor, type IslandErrorContext, type IslandErrorPhase, type IslandErrorReport, type IslandRecord, type IslandRoute, NAVIGATE_EVENT, type RenderAppRequest, type RenderAppResult, activateIslandViewModels, collectDocumentContribution, collectIslandState, createIslandContainer, describeIsland, getAppContainer, getIslandsSnapshot, hydrateIslandState, isDocumentSource, navigateIsland, onIslandDocument, onIslandNavigate, publishIslandDocument, registerIsland, renderApp, reportIslandError, resolveEagerUnits, slotAddress, subscribeIslands };
415
+ export { AppAssets, type CreateIslandContainerOptions, DOCUMENT_EVENT, type DocumentContribution, type DocumentHead, type DocumentSource, ISLAND_ERRORS_KEY, IslandDescriptor, type IslandErrorContext, type IslandErrorPhase, type IslandErrorReport, type IslandRecord, type IslandRoute, NAVIGATE_EVENT, type RenderAppRequest, type RenderAppResult, RequestContext, activateIslandViewModels, bindIslandInputs, bindRequestContext, browserRequestContext, collectDocumentContribution, collectIslandState, createIslandContainer, describeIsland, getAppContainer, getIslandsSnapshot, hydrateIslandState, isDocumentSource, islandInputsOf, navigateIsland, onIslandDocument, onIslandNavigate, parseCookieHeader, publishIslandDocument, registerIsland, renderApp, reportIslandError, resolveEagerUnits, slotAddress, subscribeIslands };
package/island/index.js CHANGED
@@ -1,23 +1,30 @@
1
1
  import {
2
2
  activateIslandViewModels,
3
+ bindIslandInputs,
4
+ bindRequestContext,
5
+ browserRequestContext,
3
6
  collectDocumentContribution,
4
7
  collectIslandState,
5
8
  createIslandContainer,
6
9
  getAppContainer,
7
10
  hydrateIslandState,
8
11
  isDocumentSource,
12
+ islandInputsOf,
9
13
  matchRoute,
10
14
  normalizeRoutes,
15
+ parseCookieHeader,
11
16
  pathPattern,
12
17
  renderApp,
13
18
  resolveEagerUnits
14
- } from "../chunk-SOH2TL2N.js";
19
+ } from "../chunk-VO3ORM7Z.js";
15
20
  import {
16
21
  ViewLayerToken,
17
22
  resolveViewAdapter,
18
23
  viewAdapterOf
19
24
  } from "../chunk-E23E2VUC.js";
20
- import "../chunk-3RX2OSUL.js";
25
+ import {
26
+ RequestContextToken
27
+ } from "../chunk-3RX2OSUL.js";
21
28
  import "../chunk-TPBI6TOU.js";
22
29
  import {
23
30
  __spreadValues
@@ -114,8 +121,12 @@ export {
114
121
  DOCUMENT_EVENT,
115
122
  ISLAND_ERRORS_KEY,
116
123
  NAVIGATE_EVENT,
124
+ RequestContextToken,
117
125
  ViewLayerToken,
118
126
  activateIslandViewModels,
127
+ bindIslandInputs,
128
+ bindRequestContext,
129
+ browserRequestContext,
119
130
  collectDocumentContribution,
120
131
  collectIslandState,
121
132
  createIslandContainer,
@@ -124,11 +135,13 @@ export {
124
135
  getIslandsSnapshot,
125
136
  hydrateIslandState,
126
137
  isDocumentSource,
138
+ islandInputsOf,
127
139
  matchRoute,
128
140
  navigateIsland,
129
141
  normalizeRoutes,
130
142
  onIslandDocument,
131
143
  onIslandNavigate,
144
+ parseCookieHeader,
132
145
  pathPattern,
133
146
  publishIslandDocument,
134
147
  registerIsland,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@foxford/den",
3
- "version": "3.3.0",
3
+ "version": "3.5.0",
4
4
  "description": "Den — декларативный метафреймворк Foxford (core runtime)",
5
5
  "keywords": [
6
6
  "foxford",
@@ -30,7 +30,7 @@
30
30
  "den": "./den.js"
31
31
  },
32
32
  "dependencies": {
33
- "fastify": "^5.11.2",
33
+ "fastify": "^5.12.1",
34
34
  "@foxford/ioc": "^1.1.2",
35
35
  "@foxford/logger": "^1.2.2"
36
36
  },
@@ -99,41 +99,41 @@
99
99
  "chunk-E56BKBQZ.js",
100
100
  "chunk-G6RT4EBO.cjs",
101
101
  "chunk-H5DKRHHQ.cjs",
102
+ "chunk-JMRHLOBD.cjs",
102
103
  "chunk-KQAB6C6Q.cjs",
103
104
  "chunk-RG7ZV5BD.js",
104
- "chunk-SOH2TL2N.js",
105
105
  "chunk-T5QVCXVB.cjs",
106
106
  "chunk-TPBI6TOU.js",
107
+ "chunk-VO3ORM7Z.js",
107
108
  "chunk-WBHHHICS.js",
108
- "chunk-XDM6J4LJ.cjs",
109
109
  "chunk-XOJ2VWX4.cjs",
110
- "define-repository-CwAXed2X.d.cts",
111
- "define-repository-q_T4hqeP.d.ts",
112
- "define-slot-DouHW8RK.d.cts",
113
- "define-slot-TkqbLySB.d.ts",
110
+ "define-repository-AO7JI6Cb.d.ts",
111
+ "define-repository-C0MI-J32.d.cts",
112
+ "define-slot-BEeHNEph.d.cts",
113
+ "define-slot-CdWdFM16.d.ts",
114
114
  "define.cjs",
115
115
  "define.d.cts",
116
116
  "define.d.ts",
117
117
  "define.js",
118
118
  "den.js",
119
- "descriptor-tWPa9j-x.d.ts",
120
- "descriptor-w8oxeIAe.d.cts",
119
+ "descriptor-BSaHM5B4.d.ts",
120
+ "descriptor-C2j6Zz6c.d.cts",
121
121
  "index.cjs",
122
122
  "index.d.cts",
123
123
  "index.d.ts",
124
124
  "index.js",
125
125
  "island",
126
126
  "package.json",
127
- "routes-0uXJ0fux.d.ts",
128
- "routes-B0hDrkiF.d.cts",
127
+ "routes-BvV405k4.d.cts",
128
+ "routes-Di3K_0uQ.d.ts",
129
129
  "serve",
130
130
  "server-render-CocWXQKC.d.cts",
131
131
  "server-render-CocWXQKC.d.ts",
132
- "types-Dx5qGiwk.d.cts",
133
- "types-Dx5qGiwk.d.ts",
134
- "view-adapter-BV62bdhM.d.ts",
135
- "view-adapter-DF1me25J.d.cts"
132
+ "types-BxMQ-VOd.d.cts",
133
+ "types-BxMQ-VOd.d.ts",
134
+ "view-adapter-DMLlp3Iu.d.cts",
135
+ "view-adapter-DNLRSFka.d.ts"
136
136
  ],
137
- "sha": "28782dc",
137
+ "sha": "a0e9213",
138
138
  "scripts": {}
139
139
  }
@@ -1,4 +1,4 @@
1
- import { G as GuardDefinition } from './types-Dx5qGiwk.cjs';
1
+ import { G as GuardDefinition } from './types-BxMQ-VOd.cjs';
2
2
 
3
3
  /** Маршрут с политикой доступа. */
4
4
  interface RouteDeclaration {
@@ -1,4 +1,4 @@
1
- import { G as GuardDefinition } from './types-Dx5qGiwk.js';
1
+ import { G as GuardDefinition } from './types-BxMQ-VOd.js';
2
2
 
3
3
  /** Маршрут с политикой доступа. */
4
4
  interface RouteDeclaration {
package/serve/index.cjs CHANGED
@@ -5,7 +5,8 @@ var _chunkKQAB6C6Qcjs = require('../chunk-KQAB6C6Q.cjs');
5
5
 
6
6
 
7
7
 
8
- var _chunkXDM6J4LJcjs = require('../chunk-XDM6J4LJ.cjs');
8
+
9
+ var _chunkJMRHLOBDcjs = require('../chunk-JMRHLOBD.cjs');
9
10
  require('../chunk-XOJ2VWX4.cjs');
10
11
  require('../chunk-6QV4L6R2.cjs');
11
12
 
@@ -69,28 +70,14 @@ function registerAssets(instance, source) {
69
70
 
70
71
  var DEFAULT_SLOW_RENDER_MS = 1e3;
71
72
  function claim(app) {
72
- return _chunkXDM6J4LJcjs.normalizeRoutes.call(void 0, app.routes).map((route) => route.source);
73
+ return _chunkJMRHLOBDcjs.normalizeRoutes.call(void 0, app.routes).map((route) => route.source);
73
74
  }
74
75
  function matchClaim(app, pathname) {
75
76
  var _a, _b;
76
77
  if (claim(app).length === 0) {
77
78
  return {};
78
79
  }
79
- return (_b = (_a = _chunkXDM6J4LJcjs.matchRoute.call(void 0, app.routes, pathname)) == null ? void 0 : _a.params) != null ? _b : null;
80
- }
81
- function parseCookies(header) {
82
- const cookies = {};
83
- for (const part of (header != null ? header : "").split(";")) {
84
- const eq = part.indexOf("=");
85
- if (eq < 1) {
86
- continue;
87
- }
88
- const name = part.slice(0, eq).trim();
89
- if (name && !(name in cookies)) {
90
- cookies[name] = part.slice(eq + 1).trim();
91
- }
92
- }
93
- return cookies;
80
+ return (_b = (_a = _chunkJMRHLOBDcjs.matchRoute.call(void 0, app.routes, pathname)) == null ? void 0 : _a.params) != null ? _b : null;
94
81
  }
95
82
  function browserContext(req) {
96
83
  const headers = {};
@@ -107,7 +94,7 @@ function browserContext(req) {
107
94
  if (typeof cookie === "string" && cookie !== "") {
108
95
  headers.cookie = cookie;
109
96
  }
110
- return { cookies: parseCookies(cookie), headers };
97
+ return { cookies: _chunkJMRHLOBDcjs.parseCookieHeader.call(void 0, cookie), headers };
111
98
  }
112
99
  var appPlugin = (instance, options) => {
113
100
  var _a, _b;
@@ -119,30 +106,50 @@ var appPlugin = (instance, options) => {
119
106
  void reply.header("cache-control", "no-store");
120
107
  return claim(app);
121
108
  });
122
- instance.get("/_render", (req, reply) => _chunkT5QVCXVBcjs.__async.call(void 0, null, null, function* () {
123
- const target = req.query.url;
124
- if (typeof target !== "string" || !target.startsWith("/")) {
125
- return reply.code(400).send({ error: "\u043D\u0435 \u043F\u0435\u0440\u0435\u0434\u0430\u043D \u0438\u043B\u0438 \u043D\u0435\u0432\u0430\u043B\u0438\u0434\u0435\u043D \u043F\u0430\u0440\u0430\u043C\u0435\u0442\u0440 url" });
126
- }
127
- const { pathname, search } = new URL(target, "http://localhost");
128
- const params = matchClaim(app, pathname);
129
- if (params === null) {
130
- serveLog.error(`\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F`);
131
- return reply.code(404).send({ error: `\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F` });
132
- }
133
- const startedAt = Date.now();
134
- try {
135
- const result = yield _chunkXDM6J4LJcjs.renderApp.call(void 0, app, { context: browserContext(req), params, pathname, search });
136
- const elapsed = Date.now() - startedAt;
137
- if (elapsed >= slowRenderMs) {
138
- serveLog.warn(`\u043C\u0435\u0434\u043B\u0435\u043D\u043D\u044B\u0439 \u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB: ${String(elapsed)}\u043C\u0441`);
109
+ function handleRender(req, reply, target, inputs) {
110
+ return _chunkT5QVCXVBcjs.__async.call(void 0, this, null, function* () {
111
+ if (typeof target !== "string" || !target.startsWith("/")) {
112
+ return reply.code(400).send({ error: "\u043D\u0435 \u043F\u0435\u0440\u0435\u0434\u0430\u043D \u0438\u043B\u0438 \u043D\u0435\u0432\u0430\u043B\u0438\u0434\u0435\u043D \u043F\u0430\u0440\u0430\u043C\u0435\u0442\u0440 url" });
139
113
  }
140
- return result;
141
- } catch (error) {
142
- serveLog.error(`\u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB \u0443\u043F\u0430\u043B \u0437\u0430 ${String(Date.now() - startedAt)}\u043C\u0441`, error);
143
- return reply.send(error instanceof Error ? error : new Error(String(error)));
144
- }
145
- }));
114
+ if (inputs !== void 0 && (typeof inputs !== "object" || inputs === null || Array.isArray(inputs))) {
115
+ return reply.code(400).send({ error: "inputs \u0434\u043E\u043B\u0436\u043D\u044B \u0431\u044B\u0442\u044C \u043E\u0431\u044A\u0435\u043A\u0442\u043E\u043C \u043F\u043E \u043A\u043B\u044E\u0447\u0443 token.description" });
116
+ }
117
+ const { pathname, search } = new URL(target, "http://localhost");
118
+ const params = matchClaim(app, pathname);
119
+ if (params === null) {
120
+ serveLog.error(`\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F`);
121
+ return reply.code(404).send({ error: `\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F` });
122
+ }
123
+ const startedAt = Date.now();
124
+ try {
125
+ const result = yield _chunkJMRHLOBDcjs.renderApp.call(void 0, app, {
126
+ context: browserContext(req),
127
+ inputs,
128
+ params,
129
+ pathname,
130
+ search
131
+ });
132
+ const elapsed = Date.now() - startedAt;
133
+ if (elapsed >= slowRenderMs) {
134
+ serveLog.warn(`\u043C\u0435\u0434\u043B\u0435\u043D\u043D\u044B\u0439 \u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB: ${String(elapsed)}\u043C\u0441`);
135
+ }
136
+ return result;
137
+ } catch (error) {
138
+ serveLog.error(`\u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB \u0443\u043F\u0430\u043B \u0437\u0430 ${String(Date.now() - startedAt)}\u043C\u0441`, error);
139
+ return reply.send(error instanceof Error ? error : new Error(String(error)));
140
+ }
141
+ });
142
+ }
143
+ instance.get("/_render", (req, reply) => handleRender(req, reply, req.query.url, void 0));
144
+ instance.route({
145
+ handler: (req, reply) => {
146
+ var _a2;
147
+ const body = (_a2 = req.body) != null ? _a2 : {};
148
+ return handleRender(req, reply, body.url, body.inputs);
149
+ },
150
+ method: "QUERY",
151
+ url: "/_render"
152
+ });
146
153
  return Promise.resolve();
147
154
  };
148
155
 
package/serve/index.d.cts CHANGED
@@ -1,8 +1,8 @@
1
1
  import { FastifyInstance, FastifyPluginAsync } from 'fastify';
2
- import { I as IslandDescriptor } from '../descriptor-w8oxeIAe.cjs';
3
- import { A as AppRoute } from '../routes-B0hDrkiF.cjs';
4
- import '../define-slot-DouHW8RK.cjs';
5
- import '../types-Dx5qGiwk.cjs';
2
+ import { I as IslandDescriptor } from '../descriptor-C2j6Zz6c.cjs';
3
+ import { A as AppRoute } from '../routes-BvV405k4.cjs';
4
+ import '../define-slot-BEeHNEph.cjs';
5
+ import '../types-BxMQ-VOd.cjs';
6
6
  import '@foxford/ioc';
7
7
 
8
8
  /** Что раздаётся и по какому префиксу. */
package/serve/index.d.ts CHANGED
@@ -1,8 +1,8 @@
1
1
  import { FastifyInstance, FastifyPluginAsync } from 'fastify';
2
- import { I as IslandDescriptor } from '../descriptor-tWPa9j-x.js';
3
- import { A as AppRoute } from '../routes-0uXJ0fux.js';
4
- import '../define-slot-TkqbLySB.js';
5
- import '../types-Dx5qGiwk.js';
2
+ import { I as IslandDescriptor } from '../descriptor-BSaHM5B4.js';
3
+ import { A as AppRoute } from '../routes-Di3K_0uQ.js';
4
+ import '../define-slot-CdWdFM16.js';
5
+ import '../types-BxMQ-VOd.js';
6
6
  import '@foxford/ioc';
7
7
 
8
8
  /** Что раздаётся и по какому префиксу. */
package/serve/index.js CHANGED
@@ -4,8 +4,9 @@ import {
4
4
  import {
5
5
  matchRoute,
6
6
  normalizeRoutes,
7
+ parseCookieHeader,
7
8
  renderApp
8
- } from "../chunk-SOH2TL2N.js";
9
+ } from "../chunk-VO3ORM7Z.js";
9
10
  import "../chunk-E23E2VUC.js";
10
11
  import "../chunk-3RX2OSUL.js";
11
12
  import {
@@ -78,20 +79,6 @@ function matchClaim(app, pathname) {
78
79
  }
79
80
  return (_b = (_a = matchRoute(app.routes, pathname)) == null ? void 0 : _a.params) != null ? _b : null;
80
81
  }
81
- function parseCookies(header) {
82
- const cookies = {};
83
- for (const part of (header != null ? header : "").split(";")) {
84
- const eq = part.indexOf("=");
85
- if (eq < 1) {
86
- continue;
87
- }
88
- const name = part.slice(0, eq).trim();
89
- if (name && !(name in cookies)) {
90
- cookies[name] = part.slice(eq + 1).trim();
91
- }
92
- }
93
- return cookies;
94
- }
95
82
  function browserContext(req) {
96
83
  const headers = {};
97
84
  const forwarded = {
@@ -107,7 +94,7 @@ function browserContext(req) {
107
94
  if (typeof cookie === "string" && cookie !== "") {
108
95
  headers.cookie = cookie;
109
96
  }
110
- return { cookies: parseCookies(cookie), headers };
97
+ return { cookies: parseCookieHeader(cookie), headers };
111
98
  }
112
99
  var appPlugin = (instance, options) => {
113
100
  var _a, _b;
@@ -119,30 +106,50 @@ var appPlugin = (instance, options) => {
119
106
  void reply.header("cache-control", "no-store");
120
107
  return claim(app);
121
108
  });
122
- instance.get("/_render", (req, reply) => __async(null, null, function* () {
123
- const target = req.query.url;
124
- if (typeof target !== "string" || !target.startsWith("/")) {
125
- return reply.code(400).send({ error: "\u043D\u0435 \u043F\u0435\u0440\u0435\u0434\u0430\u043D \u0438\u043B\u0438 \u043D\u0435\u0432\u0430\u043B\u0438\u0434\u0435\u043D \u043F\u0430\u0440\u0430\u043C\u0435\u0442\u0440 url" });
126
- }
127
- const { pathname, search } = new URL(target, "http://localhost");
128
- const params = matchClaim(app, pathname);
129
- if (params === null) {
130
- serveLog.error(`\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F`);
131
- return reply.code(404).send({ error: `\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F` });
132
- }
133
- const startedAt = Date.now();
134
- try {
135
- const result = yield renderApp(app, { context: browserContext(req), params, pathname, search });
136
- const elapsed = Date.now() - startedAt;
137
- if (elapsed >= slowRenderMs) {
138
- serveLog.warn(`\u043C\u0435\u0434\u043B\u0435\u043D\u043D\u044B\u0439 \u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB: ${String(elapsed)}\u043C\u0441`);
109
+ function handleRender(req, reply, target, inputs) {
110
+ return __async(this, null, function* () {
111
+ if (typeof target !== "string" || !target.startsWith("/")) {
112
+ return reply.code(400).send({ error: "\u043D\u0435 \u043F\u0435\u0440\u0435\u0434\u0430\u043D \u0438\u043B\u0438 \u043D\u0435\u0432\u0430\u043B\u0438\u0434\u0435\u043D \u043F\u0430\u0440\u0430\u043C\u0435\u0442\u0440 url" });
139
113
  }
140
- return result;
141
- } catch (error) {
142
- serveLog.error(`\u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB \u0443\u043F\u0430\u043B \u0437\u0430 ${String(Date.now() - startedAt)}\u043C\u0441`, error);
143
- return reply.send(error instanceof Error ? error : new Error(String(error)));
144
- }
145
- }));
114
+ if (inputs !== void 0 && (typeof inputs !== "object" || inputs === null || Array.isArray(inputs))) {
115
+ return reply.code(400).send({ error: "inputs \u0434\u043E\u043B\u0436\u043D\u044B \u0431\u044B\u0442\u044C \u043E\u0431\u044A\u0435\u043A\u0442\u043E\u043C \u043F\u043E \u043A\u043B\u044E\u0447\u0443 token.description" });
116
+ }
117
+ const { pathname, search } = new URL(target, "http://localhost");
118
+ const params = matchClaim(app, pathname);
119
+ if (params === null) {
120
+ serveLog.error(`\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F`);
121
+ return reply.code(404).send({ error: `\u043F\u0443\u0442\u044C \xAB${pathname}\xBB \u0432\u043D\u0435 \u0437\u0430\u044F\u0432\u043A\u0438 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F` });
122
+ }
123
+ const startedAt = Date.now();
124
+ try {
125
+ const result = yield renderApp(app, {
126
+ context: browserContext(req),
127
+ inputs,
128
+ params,
129
+ pathname,
130
+ search
131
+ });
132
+ const elapsed = Date.now() - startedAt;
133
+ if (elapsed >= slowRenderMs) {
134
+ serveLog.warn(`\u043C\u0435\u0434\u043B\u0435\u043D\u043D\u044B\u0439 \u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB: ${String(elapsed)}\u043C\u0441`);
135
+ }
136
+ return result;
137
+ } catch (error) {
138
+ serveLog.error(`\u0440\u0435\u043D\u0434\u0435\u0440 \xAB${pathname}\xBB \u0443\u043F\u0430\u043B \u0437\u0430 ${String(Date.now() - startedAt)}\u043C\u0441`, error);
139
+ return reply.send(error instanceof Error ? error : new Error(String(error)));
140
+ }
141
+ });
142
+ }
143
+ instance.get("/_render", (req, reply) => handleRender(req, reply, req.query.url, void 0));
144
+ instance.route({
145
+ handler: (req, reply) => {
146
+ var _a2;
147
+ const body = (_a2 = req.body) != null ? _a2 : {};
148
+ return handleRender(req, reply, body.url, body.inputs);
149
+ },
150
+ method: "QUERY",
151
+ url: "/_render"
152
+ });
146
153
  return Promise.resolve();
147
154
  };
148
155
 
@@ -774,4 +774,4 @@ declare const ActivatableToken: Token<Activatable>;
774
774
  */
775
775
  declare const RequestContextToken: Token<RequestContext>;
776
776
 
777
- export { type ActionGuard as A, type Activatable as B, type Core as C, type DefineRepositoryOptions as D, type ExtensionConfig as E, ActivatableToken as F, type GuardDefinition as G, ContainerManagerToken as H, GuardRunnerToken as I, NavigationManagerToken as J, RequestContextToken as K, type LayerDefinition as L, StateCache as M, type NavigationManager as N, type StateParticipant as O, StateRegistry as P, StateRegistryToken as Q, type RequestContext as R, type ServiceDefinition as S, StateSerializerToken as T, type ViewModelDefinition as V, type DefineServiceOptions as a, type DefineViewModelOptions as b, type Definition as c, type RepositoryDefinition as d, type SlotEntry as e, SlotRegistry as f, SlotRegistryToken as g, type LayerConfig as h, type ContainerManager as i, type GuardRunner as j, type Guard as k, type GuardResult as l, type NavigationEntry as m, type NavigationInterceptor as n, type Disposable as o, type LeaveGuardResult as p, type StateSerializer as q, type DefineGuardOptions as r, type DefineExtensionOptions as s, type ExtensionDefinition as t, type DefineActionGuardOptions as u, type ActionGuardDefinition as v, type LayoutConfig as w, type DefineLayoutOptions as x, type LayoutDefinition as y, type DefineLayerOptions as z };
777
+ export { type ActionGuard as A, type DefineLayerOptions as B, type Core as C, type DefineRepositoryOptions as D, type ExtensionConfig as E, type Activatable as F, type GuardDefinition as G, ActivatableToken as H, ContainerManagerToken as I, GuardRunnerToken as J, NavigationManagerToken as K, type LayerDefinition as L, StateCache as M, type NavigationManager as N, type StateParticipant as O, StateRegistry as P, StateRegistryToken as Q, type RequestContext as R, type ServiceDefinition as S, StateSerializerToken as T, type ViewModelDefinition as V, type DefineServiceOptions as a, type DefineViewModelOptions as b, type Definition as c, type RepositoryDefinition as d, type SlotEntry as e, SlotRegistry as f, SlotRegistryToken as g, type LayerConfig as h, RequestContextToken as i, type ContainerManager as j, type GuardRunner as k, type Guard as l, type GuardResult as m, type NavigationEntry as n, type NavigationInterceptor as o, type Disposable as p, type LeaveGuardResult as q, type StateSerializer as r, type DefineGuardOptions as s, type DefineExtensionOptions as t, type ExtensionDefinition as u, type DefineActionGuardOptions as v, type ActionGuardDefinition as w, type LayoutConfig as x, type DefineLayoutOptions as y, type LayoutDefinition as z };
@@ -774,4 +774,4 @@ declare const ActivatableToken: Token<Activatable>;
774
774
  */
775
775
  declare const RequestContextToken: Token<RequestContext>;
776
776
 
777
- export { type ActionGuard as A, type Activatable as B, type Core as C, type DefineRepositoryOptions as D, type ExtensionConfig as E, ActivatableToken as F, type GuardDefinition as G, ContainerManagerToken as H, GuardRunnerToken as I, NavigationManagerToken as J, RequestContextToken as K, type LayerDefinition as L, StateCache as M, type NavigationManager as N, type StateParticipant as O, StateRegistry as P, StateRegistryToken as Q, type RequestContext as R, type ServiceDefinition as S, StateSerializerToken as T, type ViewModelDefinition as V, type DefineServiceOptions as a, type DefineViewModelOptions as b, type Definition as c, type RepositoryDefinition as d, type SlotEntry as e, SlotRegistry as f, SlotRegistryToken as g, type LayerConfig as h, type ContainerManager as i, type GuardRunner as j, type Guard as k, type GuardResult as l, type NavigationEntry as m, type NavigationInterceptor as n, type Disposable as o, type LeaveGuardResult as p, type StateSerializer as q, type DefineGuardOptions as r, type DefineExtensionOptions as s, type ExtensionDefinition as t, type DefineActionGuardOptions as u, type ActionGuardDefinition as v, type LayoutConfig as w, type DefineLayoutOptions as x, type LayoutDefinition as y, type DefineLayerOptions as z };
777
+ export { type ActionGuard as A, type DefineLayerOptions as B, type Core as C, type DefineRepositoryOptions as D, type ExtensionConfig as E, type Activatable as F, type GuardDefinition as G, ActivatableToken as H, ContainerManagerToken as I, GuardRunnerToken as J, NavigationManagerToken as K, type LayerDefinition as L, StateCache as M, type NavigationManager as N, type StateParticipant as O, StateRegistry as P, StateRegistryToken as Q, type RequestContext as R, type ServiceDefinition as S, StateSerializerToken as T, type ViewModelDefinition as V, type DefineServiceOptions as a, type DefineViewModelOptions as b, type Definition as c, type RepositoryDefinition as d, type SlotEntry as e, SlotRegistry as f, SlotRegistryToken as g, type LayerConfig as h, RequestContextToken as i, type ContainerManager as j, type GuardRunner as k, type Guard as l, type GuardResult as m, type NavigationEntry as n, type NavigationInterceptor as o, type Disposable as p, type LeaveGuardResult as q, type StateSerializer as r, type DefineGuardOptions as s, type DefineExtensionOptions as t, type ExtensionDefinition as u, type DefineActionGuardOptions as v, type ActionGuardDefinition as w, type LayoutConfig as x, type DefineLayoutOptions as y, type LayoutDefinition as z };
@@ -1,6 +1,6 @@
1
- import { I as IslandDescriptor } from './descriptor-w8oxeIAe.cjs';
1
+ import { I as IslandDescriptor } from './descriptor-C2j6Zz6c.cjs';
2
2
  import { S as ServerRenderResult } from './server-render-CocWXQKC.cjs';
3
- import { L as LayerDefinition, h as LayerConfig } from './types-Dx5qGiwk.cjs';
3
+ import { L as LayerDefinition, h as LayerConfig } from './types-BxMQ-VOd.cjs';
4
4
  import { Container, Token } from '@foxford/ioc';
5
5
 
6
6
  /** Что нужно адаптеру, чтобы отрисовать остров на сервере. */
@@ -1,6 +1,6 @@
1
- import { I as IslandDescriptor } from './descriptor-tWPa9j-x.js';
1
+ import { I as IslandDescriptor } from './descriptor-BSaHM5B4.js';
2
2
  import { S as ServerRenderResult } from './server-render-CocWXQKC.js';
3
- import { L as LayerDefinition, h as LayerConfig } from './types-Dx5qGiwk.js';
3
+ import { L as LayerDefinition, h as LayerConfig } from './types-BxMQ-VOd.js';
4
4
  import { Container, Token } from '@foxford/ioc';
5
5
 
6
6
  /** Что нужно адаптеру, чтобы отрисовать остров на сервере. */