@lwrjs/core 0.17.2-alpha.2 → 0.17.2-alpha.20

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.
@@ -45,17 +45,17 @@ function createBundleMiddleware(context) {
45
45
  return async (req, res) => {
46
46
  if (!req.validateEnvironmentRequest(appConfig)) {
47
47
  res.status(400);
48
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
48
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
49
49
  return;
50
50
  }
51
51
  if (!req.validateJsonRequest()) {
52
52
  res.status(400);
53
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_JSON());
53
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_JSON());
54
54
  return;
55
55
  }
56
56
  if (!req.validateApiVersion(appConfig)) {
57
57
  res.status(400);
58
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
58
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
59
59
  return;
60
60
  }
61
61
  const {runtimeEnvironment, runtimeParams} = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -92,7 +92,7 @@ function createSourceMapMiddleware(context) {
92
92
  return async (req, res) => {
93
93
  if (!req.validateEnvironmentRequest(appConfig)) {
94
94
  res.status(400);
95
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
95
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
96
96
  return;
97
97
  }
98
98
  const {runtimeEnvironment} = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -41,7 +41,7 @@ function createMappingMiddleware(context) {
41
41
  return async (req, res) => {
42
42
  if (!req.validateEnvironmentRequest(appConfig)) {
43
43
  res.status(400);
44
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
44
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
45
45
  return;
46
46
  }
47
47
  const {runtimeEnvironment, runtimeParams} = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -39,17 +39,17 @@ function createModuleMiddleware(context) {
39
39
  return async (req, res) => {
40
40
  if (!req.validateEnvironmentRequest(appConfig)) {
41
41
  res.status(400);
42
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
42
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
43
43
  return;
44
44
  }
45
45
  if (!req.validateJsonRequest()) {
46
46
  res.status(400);
47
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_JSON());
47
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_JSON());
48
48
  return;
49
49
  }
50
50
  if (!req.validateApiVersion(appConfig)) {
51
51
  res.status(400);
52
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
52
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
53
53
  return;
54
54
  }
55
55
  const {runtimeEnvironment, runtimeParams} = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -28,8 +28,6 @@ __export(exports, {
28
28
  });
29
29
  var import_diagnostics = __toModule(require("@lwrjs/diagnostics"));
30
30
  var import_shared_utils = __toModule(require("@lwrjs/shared-utils"));
31
- var MRT_REQUEST_CLASS = "X-Mobify-Request-Class";
32
- var MRT_REQUEST_CLASS_KEY = MRT_REQUEST_CLASS.toLowerCase();
33
31
  function requestProcessorMiddleware(app, context) {
34
32
  const {basePath} = context.runtimeEnvironment;
35
33
  app.use(async (req, res, next) => {
@@ -44,8 +42,10 @@ function requestProcessorMiddleware(app, context) {
44
42
  });
45
43
  }
46
44
  }
47
- requestClass = req.headers[MRT_REQUEST_CLASS_KEY];
45
+ requestClass = req.headers[import_shared_utils.MRT_REQUEST_CLASS];
48
46
  requestDepth = (0, import_shared_utils.parseRequestDepth)(req.headers, req.query);
47
+ const trueClientIP = req.headers[import_shared_utils.TRUE_CLIENT_IP];
48
+ const correlationID = req.headers[import_shared_utils.CORRELATION_ID];
49
49
  const forwarded = req.headers["forwarded"];
50
50
  const host = req.headers["host"];
51
51
  const forwardedProto = req.headers["x-forwarded-proto"];
@@ -53,7 +53,7 @@ function requestProcessorMiddleware(app, context) {
53
53
  if ((0, import_shared_utils.isLambdaEnv)()) {
54
54
  import_diagnostics.logger.info({
55
55
  label: `request-processor-middleware`,
56
- message: `Original Url: ${req.originalUrl}, Forwarded: ${forwarded}, X-Forwarded-Proto: ${forwardedProto}, Host: ${host}, Protocol: ${protocol}, ${MRT_REQUEST_CLASS}: ${requestClass}, ${import_shared_utils.REQUEST_DEPTH_HEADER}: ${requestDepth}`
56
+ message: `Original Url: ${req.originalUrl}, Forwarded: ${forwarded}, X-Forwarded-Proto: ${forwardedProto}, Host: ${host}, Protocol: ${protocol}, ${import_shared_utils.MRT_REQUEST_CLASS}: ${requestClass}, ${import_shared_utils.TRUE_CLIENT_IP}: ${trueClientIP}, ${import_shared_utils.CORRELATION_ID}: ${correlationID}, ${import_shared_utils.REQUEST_DEPTH_HEADER}: ${requestDepth}`
57
57
  });
58
58
  }
59
59
  }
@@ -89,7 +89,7 @@ function requestProcessorMiddleware(app, context) {
89
89
  } else {
90
90
  import_diagnostics.logger.debug({
91
91
  label: `request-processor-middleware`,
92
- message: `${MRT_REQUEST_CLASS_KEY} ignored ${req.headers ? req.headers[MRT_REQUEST_CLASS_KEY] : "no-headers"}`
92
+ message: `${import_shared_utils.MRT_REQUEST_CLASS} ignored ${req.headers ? req.headers[import_shared_utils.MRT_REQUEST_CLASS] : "no-headers"}`
93
93
  });
94
94
  req.basePath = basePath;
95
95
  }
@@ -33,7 +33,7 @@ function createResourceMiddleware(context) {
33
33
  const {appConfig, resourceRegistry, runtimeEnvironment: defaultRuntimeEnvironment} = context;
34
34
  return async (req, res) => {
35
35
  if (!req.validateEnvironmentRequest(appConfig)) {
36
- res.status(400).send(import_diagnostics.descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
36
+ res.status(400).send(import_diagnostics.descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
37
37
  return;
38
38
  }
39
39
  const {runtimeEnvironment, runtimeParams} = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -28,16 +28,43 @@ __export(exports, {
28
28
  });
29
29
  var import_diagnostics = __toModule(require("@lwrjs/diagnostics"));
30
30
  var import_diagnostics2 = __toModule(require("@lwrjs/diagnostics"));
31
- function createReturnStatus(error, url) {
32
- if (error instanceof import_diagnostics.LwrApplicationError) {
33
- return {status: 400, message: error.message};
31
+ var import_shared_utils = __toModule(require("@lwrjs/shared-utils"));
32
+ function addRedirectQueryParam(redirectUrl, depth) {
33
+ const fakeOrigin = "http://parse.com";
34
+ const url = (0, import_shared_utils.isURL)(redirectUrl) ? new URL(redirectUrl) : new URL(`${fakeOrigin}${redirectUrl}`);
35
+ url.searchParams.set(import_shared_utils.REQUEST_DEPTH_HEADER, String(depth + 1));
36
+ return url.toString().replace(fakeOrigin, "");
37
+ }
38
+ function createReturnStatus(error, req, debug) {
39
+ let status = 500, body = error.message || "";
40
+ const headers = {};
41
+ if (error instanceof import_diagnostics.LwrStatusError) {
42
+ status = error.status;
43
+ const rawHeaders = error.headers || {};
44
+ Object.entries(rawHeaders).forEach(([key, value]) => headers[key.toLowerCase()] = value);
45
+ if (status === 301 || status === 302) {
46
+ const location = headers.location;
47
+ if (location && (0, import_shared_utils.isURL)(location) || location?.startsWith("/")) {
48
+ headers.location = addRedirectQueryParam(location, (0, import_shared_utils.parseRequestDepth)(req.headers, req.query));
49
+ } else {
50
+ import_diagnostics2.logger.warn(`[error-middleware] Invalid location header for HTTP status ${status}: "${location}"`);
51
+ }
52
+ }
53
+ }
54
+ if (error instanceof import_diagnostics.LwrInvalidError) {
55
+ status = 400;
56
+ } else if (error instanceof import_diagnostics.LwrUnresolvableError) {
57
+ status = 404;
58
+ } else {
59
+ body = error instanceof import_diagnostics.LwrError ? body : `${import_diagnostics.descriptions.SERVER.SERVER_ERROR(req.originalUrl)}: ${body}`;
34
60
  }
35
- if (error instanceof import_diagnostics.LwrUnresolvableError) {
36
- return {status: 404, message: error.message};
61
+ if (debug) {
62
+ body = `<div style="font-family:sans-serif;margin:50px;"><h1>${status}: Document generation failed</h1><p>${body.replace(/</g, "&lt;").replace(/>/g, "&gt;")}</p></div>`;
63
+ status = 200;
37
64
  }
38
- return {status: 500, message: `${import_diagnostics.descriptions.SERVER.SERVER_ERROR(url)}: ${error.message}`};
65
+ return {status, body, headers: Object.keys(headers).length > 0 ? headers : void 0};
39
66
  }
40
- function handleErrors(middleware) {
67
+ function handleErrors(middleware, isBaseDoc = false) {
41
68
  return async (req, res, next) => {
42
69
  try {
43
70
  await middleware(req, res, next);
@@ -49,9 +76,9 @@ function handleErrors(middleware) {
49
76
  } else {
50
77
  import_diagnostics2.logger.error(err);
51
78
  }
52
- const {status, message} = createReturnStatus(err, req.originalUrl);
53
- res.status(status);
54
- res.send(message);
79
+ const {status, body, headers} = createReturnStatus(err, req, req.query.debug !== void 0 && isBaseDoc);
80
+ headers && res.set(headers);
81
+ res.status(status).send(body);
55
82
  }
56
83
  };
57
84
  }
@@ -37,7 +37,7 @@ function validateSpecifier(specifer) {
37
37
  function getModuleIdentity(req, importer) {
38
38
  const {specifier, signature} = req.params;
39
39
  if (validateSpecifier(specifier) === false) {
40
- throw new import_diagnostics.LwrApplicationError(import_diagnostics.descriptions.APPLICATION.INVALID_SPECIFIER(specifier));
40
+ throw new import_diagnostics.LwrInvalidError(import_diagnostics.descriptions.INVALID.INVALID_SPECIFIER(specifier));
41
41
  }
42
42
  const moduleId = (0, import_shared_utils.explodeSpecifier)(specifier);
43
43
  return {
@@ -61,7 +61,7 @@ function getMappingIdentity(req) {
61
61
  function getResourceIdentity(req) {
62
62
  const {specifier, signature = import_shared_utils.LATEST_SIGNATURE} = req.params;
63
63
  if (validateSpecifier(specifier) === false) {
64
- throw new import_diagnostics.LwrApplicationError(import_diagnostics.descriptions.APPLICATION.INVALID_SPECIFIER(specifier));
64
+ throw new import_diagnostics.LwrInvalidError(import_diagnostics.descriptions.INVALID.INVALID_SPECIFIER(specifier));
65
65
  }
66
66
  const resourceId = (0, import_shared_utils.explodeSpecifier)(specifier);
67
67
  return {
@@ -73,7 +73,7 @@ function getAssetIdentity(req) {
73
73
  const {signature, immutable, assetType: type} = req.params;
74
74
  const specifier = type ? process.platform === "win32" ? req.params[0] : "/" + req.params[0] : req.originalUrl.split("?")[0];
75
75
  if (validateSpecifier(specifier) === false) {
76
- throw new import_diagnostics.LwrApplicationError(import_diagnostics.descriptions.APPLICATION.INVALID_SPECIFIER(specifier));
76
+ throw new import_diagnostics.LwrInvalidError(import_diagnostics.descriptions.INVALID.INVALID_SPECIFIER(specifier));
77
77
  }
78
78
  return {
79
79
  immutable,
@@ -26,17 +26,16 @@ __markAsModule(exports);
26
26
  __export(exports, {
27
27
  viewMiddleware: () => viewMiddleware
28
28
  });
29
- var import_util = __toModule(require("util"));
30
29
  var import_url = __toModule(require("url"));
30
+ var import_util = __toModule(require("util"));
31
+ var import_zlib = __toModule(require("zlib"));
31
32
  var import_diagnostics = __toModule(require("@lwrjs/diagnostics"));
33
+ var import_instrumentation = __toModule(require("@lwrjs/instrumentation"));
32
34
  var import_router = __toModule(require("@lwrjs/router"));
33
35
  var import_shared_utils = __toModule(require("@lwrjs/shared-utils"));
34
- var import_instrumentation = __toModule(require("@lwrjs/instrumentation"));
35
- var import_error_handling = __toModule(require("./utils/error-handling.cjs"));
36
36
  var import_view_registry = __toModule(require("@lwrjs/view-registry"));
37
- var import_instrumentation2 = __toModule(require("@lwrjs/instrumentation"));
38
- var import_zlib = __toModule(require("zlib"));
39
37
  var import_compression = __toModule(require("./utils/compression.cjs"));
38
+ var import_error_handling = __toModule(require("./utils/error-handling.cjs"));
40
39
  function createViewMiddleware(route, errorRoutes, context, viewHandler) {
41
40
  const errorRoute = errorRoutes.find((route2) => route2.status === 500);
42
41
  const appConfig = context.appConfig;
@@ -45,12 +44,12 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
45
44
  return async (req, res) => {
46
45
  if (!req.validateEnvironmentRequest(appConfig)) {
47
46
  res.status(400);
48
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
47
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
49
48
  return;
50
49
  }
51
50
  if (!req.validateJsonRequest()) {
52
51
  res.status(400);
53
- res.send(import_diagnostics.descriptions.APPLICATION.INVALID_JSON());
52
+ res.send(import_diagnostics.descriptions.INVALID.INVALID_JSON());
54
53
  return;
55
54
  }
56
55
  const {runtimeEnvironment, runtimeParams: defaultRuntimeParams} = req.getRuntimeContext(context.runtimeEnvironment);
@@ -69,13 +68,15 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
69
68
  params: viewRequest.params,
70
69
  query: viewRequest.query,
71
70
  cookie: req.headers?.cookie,
72
- trueClientIP: req.headers && req.headers["true-client-ip"],
71
+ trueClientIP: req.headers?.[import_shared_utils.TRUE_CLIENT_IP],
72
+ correlationID: req.headers?.[import_shared_utils.CORRELATION_ID],
73
73
  coreProxy: req.getCoreProxy(appConfig.coreProxy ?? void 0, route.bootstrap?.proxyForSSR)
74
74
  };
75
75
  const resolve = req.isJsonRequest() ? viewHandler.getViewJson : viewHandler.getViewContent;
76
76
  let viewResponse;
77
77
  let resolvedRoute;
78
78
  let traceId;
79
+ let headers = {};
79
80
  try {
80
81
  viewResponse = await (0, import_instrumentation.getTracer)().trace({
81
82
  name: import_instrumentation.RequestHandlerSpan.GetView,
@@ -87,7 +88,9 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
87
88
  locale: runtimeParams.locale
88
89
  }
89
90
  }, async (span) => {
91
+ runtimeParams.viewSpanID = span.spanId;
90
92
  traceId = span.traceId;
93
+ headers = (0, import_shared_utils.getTraceHeaders)(runtimeParams, span);
91
94
  const res2 = await resolve.call(viewHandler, viewRequest, route, runtimeEnvironment, runtimeParams);
92
95
  span.setAttributes({
93
96
  size: byteSize(res2.body)
@@ -96,7 +99,7 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
96
99
  });
97
100
  resolvedRoute = route;
98
101
  } catch (err) {
99
- if (!errorRoute) {
102
+ if (!errorRoute || runtimeEnvironment.debug) {
100
103
  throw err;
101
104
  }
102
105
  import_diagnostics.logger.error(`[view-middleware] Route Error ${req.originalUrl}`);
@@ -111,12 +114,13 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
111
114
  });
112
115
  resolvedRoute = errorRoute;
113
116
  } finally {
117
+ if (Object.keys(headers).length)
118
+ res.set(headers);
114
119
  if (traceId?.length) {
115
- res.setHeader("x-trace-id", traceId);
116
120
  res.set({
117
- "Server-Timing": (0, import_instrumentation2.getTraceCollector)().getSpansInTrace(traceId)
121
+ "Server-Timing": (0, import_instrumentation.getTraceCollector)().getSpansInTrace(traceId)
118
122
  });
119
- (0, import_instrumentation2.getTraceCollector)().dropTrace(traceId);
123
+ (0, import_instrumentation.getTraceCollector)().dropTrace(traceId);
120
124
  }
121
125
  }
122
126
  if (req.isSiteGeneration()) {
@@ -136,24 +140,8 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
136
140
  }
137
141
  }
138
142
  let status = resolvedRoute.status || viewResponse.status || 200;
139
- const viewDefinitionStatus = viewResponse.metadata?.viewDefinition?.status;
140
143
  if (viewResponse.status === 301 || viewResponse.status === 302) {
141
144
  status = viewResponse.status;
142
- } else if (viewDefinitionStatus && viewDefinitionStatus.code) {
143
- const origStatus = status;
144
- const {code, location} = viewDefinitionStatus;
145
- const isRedirect = code === 301 || code === 302;
146
- status = code;
147
- if (isRedirect) {
148
- if (location && (0, import_shared_utils.isURL)(location) || location?.startsWith("/")) {
149
- res.set({
150
- location: addRedirectQueryParam(location, (0, import_shared_utils.parseRequestDepth)(req.headers, req.query))
151
- });
152
- } else {
153
- status = origStatus;
154
- import_diagnostics.logger.warn(`[view-middleware] Ignoring invalid location header: "${location}"`);
155
- }
156
- }
157
145
  }
158
146
  res.status(status);
159
147
  const viewResponseBody = viewResponse.body;
@@ -264,7 +252,7 @@ function viewMiddleware(app, context) {
264
252
  }
265
253
  }
266
254
  import_diagnostics.logger.debug({label: `view-middleware`, message: `Add view paths ${paths}`});
267
- app.get(paths, (0, import_error_handling.handleErrors)(createViewMiddleware(route, errorRoutes, context, viewHandler)));
255
+ app.get(paths, (0, import_error_handling.handleErrors)(createViewMiddleware(route, errorRoutes, context, viewHandler), true));
268
256
  }
269
257
  app.get((0, import_shared_utils.getClientBootstrapConfigurationRoutes)(), (0, import_error_handling.handleErrors)(createConfigMiddleware(routes, context, viewHandler)));
270
258
  app.get("/" + app.getRegexWildcard(), (0, import_error_handling.handleErrors)(createNotFoundMiddleware(errorRoutes, context, viewHandler)));
@@ -299,12 +287,6 @@ function addDefaultLocaleRedirects(defaultLocale, defaultLocalePaths, defaultRed
299
287
  return res.sendStatus(301);
300
288
  });
301
289
  }
302
- function addRedirectQueryParam(redirectUrl, depth) {
303
- const fakeOrigin = "http://parse.com";
304
- const url = (0, import_shared_utils.isURL)(redirectUrl) ? new URL(redirectUrl) : new URL(`${fakeOrigin}${redirectUrl}`);
305
- url.searchParams.set(import_shared_utils.REQUEST_DEPTH_KEY, String(depth + 1));
306
- return url.toString().replace(fakeOrigin, "");
307
- }
308
290
  function byteSize(body) {
309
291
  if (Buffer.isBuffer(body)) {
310
292
  return body.length;
@@ -12,17 +12,17 @@ function createBundleMiddleware(context) {
12
12
  return async (req, res) => {
13
13
  if (!req.validateEnvironmentRequest(appConfig)) {
14
14
  res.status(400);
15
- res.send(descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
15
+ res.send(descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
16
16
  return;
17
17
  }
18
18
  if (!req.validateJsonRequest()) {
19
19
  res.status(400);
20
- res.send(descriptions.APPLICATION.INVALID_JSON());
20
+ res.send(descriptions.INVALID.INVALID_JSON());
21
21
  return;
22
22
  }
23
23
  if (!req.validateApiVersion(appConfig)) {
24
24
  res.status(400);
25
- res.send(descriptions.APPLICATION.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
25
+ res.send(descriptions.INVALID.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
26
26
  return;
27
27
  }
28
28
  const { runtimeEnvironment, runtimeParams } = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -65,7 +65,7 @@ function createSourceMapMiddleware(context) {
65
65
  return async (req, res) => {
66
66
  if (!req.validateEnvironmentRequest(appConfig)) {
67
67
  res.status(400);
68
- res.send(descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
68
+ res.send(descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
69
69
  return;
70
70
  }
71
71
  const { runtimeEnvironment } = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -8,7 +8,7 @@ function createMappingMiddleware(context) {
8
8
  return async (req, res) => {
9
9
  if (!req.validateEnvironmentRequest(appConfig)) {
10
10
  res.status(400);
11
- res.send(descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
11
+ res.send(descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
12
12
  return;
13
13
  }
14
14
  const { runtimeEnvironment, runtimeParams } = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -11,17 +11,17 @@ function createModuleMiddleware(context) {
11
11
  return async (req, res) => {
12
12
  if (!req.validateEnvironmentRequest(appConfig)) {
13
13
  res.status(400);
14
- res.send(descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
14
+ res.send(descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
15
15
  return;
16
16
  }
17
17
  if (!req.validateJsonRequest()) {
18
18
  res.status(400);
19
- res.send(descriptions.APPLICATION.INVALID_JSON());
19
+ res.send(descriptions.INVALID.INVALID_JSON());
20
20
  return;
21
21
  }
22
22
  if (!req.validateApiVersion(appConfig)) {
23
23
  res.status(400);
24
- res.send(descriptions.APPLICATION.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
24
+ res.send(descriptions.INVALID.INVALID_API_VERSION(req.params.apiVersion, appConfig.apiVersion));
25
25
  return;
26
26
  }
27
27
  const { runtimeEnvironment, runtimeParams } = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -1,15 +1,5 @@
1
- /**
2
- * Parse passed to us via the X-Mobify-Request-Class.
3
- *
4
- * basePath: The dynamic base path
5
- * '' or undefined -> LWR basePath ''
6
- * token or /token -> LWR basePath '/token'
7
- *
8
- */
9
1
  import { logger } from '@lwrjs/diagnostics';
10
- import { REQUEST_DEPTH_HEADER, isLambdaEnv, parseRequestDepth } from '@lwrjs/shared-utils';
11
- const MRT_REQUEST_CLASS = 'X-Mobify-Request-Class';
12
- const MRT_REQUEST_CLASS_KEY = MRT_REQUEST_CLASS.toLowerCase();
2
+ import { CORRELATION_ID, MRT_REQUEST_CLASS, REQUEST_DEPTH_HEADER, TRUE_CLIENT_IP, isLambdaEnv, parseRequestDepth, } from '@lwrjs/shared-utils';
13
3
  export function requestProcessorMiddleware(app, context) {
14
4
  const { basePath } = context.runtimeEnvironment;
15
5
  app.use(async (req, res, next) => {
@@ -26,8 +16,10 @@ export function requestProcessorMiddleware(app, context) {
26
16
  });
27
17
  }
28
18
  }
29
- requestClass = req.headers[MRT_REQUEST_CLASS_KEY];
19
+ requestClass = req.headers[MRT_REQUEST_CLASS];
30
20
  requestDepth = parseRequestDepth(req.headers, req.query);
21
+ const trueClientIP = req.headers[TRUE_CLIENT_IP];
22
+ const correlationID = req.headers[CORRELATION_ID];
31
23
  const forwarded = req.headers['forwarded'];
32
24
  const host = req.headers['host'];
33
25
  const forwardedProto = req.headers['x-forwarded-proto'];
@@ -36,7 +28,7 @@ export function requestProcessorMiddleware(app, context) {
36
28
  if (isLambdaEnv()) {
37
29
  logger.info({
38
30
  label: `request-processor-middleware`,
39
- message: `Original Url: ${req.originalUrl}, Forwarded: ${forwarded}, X-Forwarded-Proto: ${forwardedProto}, Host: ${host}, Protocol: ${protocol}, ${MRT_REQUEST_CLASS}: ${requestClass}, ${REQUEST_DEPTH_HEADER}: ${requestDepth}`,
31
+ message: `Original Url: ${req.originalUrl}, Forwarded: ${forwarded}, X-Forwarded-Proto: ${forwardedProto}, Host: ${host}, Protocol: ${protocol}, ${MRT_REQUEST_CLASS}: ${requestClass}, ${TRUE_CLIENT_IP}: ${trueClientIP}, ${CORRELATION_ID}: ${correlationID}, ${REQUEST_DEPTH_HEADER}: ${requestDepth}`,
40
32
  });
41
33
  }
42
34
  }
@@ -81,7 +73,7 @@ export function requestProcessorMiddleware(app, context) {
81
73
  else {
82
74
  logger.debug({
83
75
  label: `request-processor-middleware`,
84
- message: `${MRT_REQUEST_CLASS_KEY} ignored ${req.headers ? req.headers[MRT_REQUEST_CLASS_KEY] : 'no-headers'}`,
76
+ message: `${MRT_REQUEST_CLASS} ignored ${req.headers ? req.headers[MRT_REQUEST_CLASS] : 'no-headers'}`,
85
77
  });
86
78
  req.basePath = basePath;
87
79
  }
@@ -89,12 +81,21 @@ export function requestProcessorMiddleware(app, context) {
89
81
  await next();
90
82
  });
91
83
  }
84
+ /**
85
+ * Parse the basePath passed via the X-Mobify-Request-Class header.
86
+ * Example: basePath=/token
87
+ *
88
+ * basePath: The dynamic base path
89
+ * '' or undefined -> LWR basePath ''
90
+ * token or /token -> LWR basePath '/token'
91
+ *
92
+ */
92
93
  function parseRequestClass(requestClass) {
93
94
  // If there is no requestClass do not bother parsing
94
95
  if (!requestClass) {
95
96
  return {};
96
97
  }
97
- // Split the Forwarded header into individual key-value pairs
98
+ // Split the header into individual key-value pairs
98
99
  const keyValuePairs = requestClass.split(';');
99
100
  // Create an object to store the parsed values
100
101
  const parsed = {};
@@ -5,7 +5,7 @@ function createResourceMiddleware(context) {
5
5
  const { appConfig, resourceRegistry, runtimeEnvironment: defaultRuntimeEnvironment } = context;
6
6
  return async (req, res) => {
7
7
  if (!req.validateEnvironmentRequest(appConfig)) {
8
- res.status(400).send(descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
8
+ res.status(400).send(descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
9
9
  return;
10
10
  }
11
11
  const { runtimeEnvironment, runtimeParams } = req.getRuntimeContext(defaultRuntimeEnvironment);
@@ -1,3 +1,3 @@
1
1
  import type { MiddlewareFunction } from '@lwrjs/types';
2
- export declare function handleErrors(middleware: MiddlewareFunction): MiddlewareFunction;
2
+ export declare function handleErrors(middleware: MiddlewareFunction, isBaseDoc?: boolean): MiddlewareFunction;
3
3
  //# sourceMappingURL=error-handling.d.ts.map
@@ -1,16 +1,54 @@
1
- import { descriptions, DiagnosticsError, LwrApplicationError, LwrUnresolvableError, } from '@lwrjs/diagnostics';
1
+ import { descriptions, DiagnosticsError, LwrError, LwrInvalidError, LwrStatusError, LwrUnresolvableError, } from '@lwrjs/diagnostics';
2
2
  import { logger } from '@lwrjs/diagnostics';
3
- function createReturnStatus(error, url) {
4
- if (error instanceof LwrApplicationError) {
5
- return { status: 400, message: error.message };
3
+ import { isURL, parseRequestDepth, REQUEST_DEPTH_HEADER } from '@lwrjs/shared-utils';
4
+ function addRedirectQueryParam(redirectUrl, depth) {
5
+ // add a request depth query param to the URL
6
+ // the depth header cannot be used since headers cannot be added to a redirect
7
+ const fakeOrigin = 'http://parse.com';
8
+ const url = isURL(redirectUrl) ? new URL(redirectUrl) : new URL(`${fakeOrigin}${redirectUrl}`);
9
+ url.searchParams.set(REQUEST_DEPTH_HEADER, String(depth + 1));
10
+ return url.toString().replace(fakeOrigin, '');
11
+ }
12
+ function createReturnStatus(error, req, debug) {
13
+ let status = 500, body = error.message || '';
14
+ const headers = {};
15
+ if (error instanceof LwrStatusError) {
16
+ // handle special HTTP statuses, eg: 301, 302, 429, 503
17
+ status = error.status;
18
+ const rawHeaders = error.headers || {};
19
+ Object.entries(rawHeaders).forEach(([key, value]) => (headers[key.toLowerCase()] = value));
20
+ if (status === 301 || status === 302) {
21
+ // handle redirect
22
+ const location = headers.location;
23
+ if ((location && isURL(location)) || location?.startsWith('/')) {
24
+ headers.location = addRedirectQueryParam(location, parseRequestDepth(req.headers, req.query));
25
+ }
26
+ else {
27
+ logger.warn(`[error-middleware] Invalid location header for HTTP status ${status}: "${location}"`);
28
+ }
29
+ }
30
+ }
31
+ if (error instanceof LwrInvalidError) {
32
+ status = 400;
33
+ }
34
+ else if (error instanceof LwrUnresolvableError) {
35
+ status = 404;
36
+ }
37
+ else {
38
+ // catchall: likely a LwrServerError
39
+ body =
40
+ error instanceof LwrError
41
+ ? body
42
+ : `${descriptions.SERVER.SERVER_ERROR(req.originalUrl)}: ${body}`;
6
43
  }
7
- if (error instanceof LwrUnresolvableError) {
8
- return { status: 404, message: error.message };
44
+ if (debug) {
45
+ // return a debug base doc and a 200 response code if debug mode is on
46
+ body = `<div style="font-family:sans-serif;margin:50px;"><h1>${status}: Document generation failed</h1><p>${body.replace(/</g, '&lt;').replace(/>/g, '&gt;')}</p></div>`;
47
+ status = 200;
9
48
  }
10
- // catchall: likely a LwrServerError
11
- return { status: 500, message: `${descriptions.SERVER.SERVER_ERROR(url)}: ${error.message}` };
49
+ return { status, body, headers: Object.keys(headers).length > 0 ? headers : undefined };
12
50
  }
13
- export function handleErrors(middleware) {
51
+ export function handleErrors(middleware, isBaseDoc = false) {
14
52
  return async (req, res, next) => {
15
53
  try {
16
54
  await middleware(req, res, next);
@@ -24,9 +62,11 @@ export function handleErrors(middleware) {
24
62
  else {
25
63
  logger.error(err);
26
64
  }
27
- const { status, message } = createReturnStatus(err, req.originalUrl);
28
- res.status(status);
29
- res.send(message);
65
+ const { status, body, headers } = createReturnStatus(err, req,
66
+ // only return HTML error screen for base doc requests in debug mode
67
+ req.query.debug !== undefined && isBaseDoc);
68
+ headers && res.set(headers);
69
+ res.status(status).send(body);
30
70
  }
31
71
  };
32
72
  }
@@ -1,12 +1,12 @@
1
1
  import { explodeSpecifier, explodeSpecifiers, LATEST_SIGNATURE } from '@lwrjs/shared-utils';
2
- import { descriptions, LwrApplicationError } from '@lwrjs/diagnostics';
2
+ import { descriptions, LwrInvalidError } from '@lwrjs/diagnostics';
3
3
  function validateSpecifier(specifer) {
4
4
  return specifer.indexOf('../') < 0;
5
5
  }
6
6
  export function getModuleIdentity(req, importer) {
7
7
  const { specifier, signature } = req.params;
8
8
  if (validateSpecifier(specifier) === false) {
9
- throw new LwrApplicationError(descriptions.APPLICATION.INVALID_SPECIFIER(specifier));
9
+ throw new LwrInvalidError(descriptions.INVALID.INVALID_SPECIFIER(specifier));
10
10
  }
11
11
  const moduleId = explodeSpecifier(specifier);
12
12
  return {
@@ -30,7 +30,7 @@ export function getMappingIdentity(req) {
30
30
  export function getResourceIdentity(req) {
31
31
  const { specifier, signature = LATEST_SIGNATURE } = req.params;
32
32
  if (validateSpecifier(specifier) === false) {
33
- throw new LwrApplicationError(descriptions.APPLICATION.INVALID_SPECIFIER(specifier));
33
+ throw new LwrInvalidError(descriptions.INVALID.INVALID_SPECIFIER(specifier));
34
34
  }
35
35
  const resourceId = explodeSpecifier(specifier);
36
36
  return {
@@ -46,7 +46,7 @@ export function getAssetIdentity(req) {
46
46
  : '/' + req.params[0]
47
47
  : req.originalUrl.split('?')[0];
48
48
  if (validateSpecifier(specifier) === false) {
49
- throw new LwrApplicationError(descriptions.APPLICATION.INVALID_SPECIFIER(specifier));
49
+ throw new LwrInvalidError(descriptions.INVALID.INVALID_SPECIFIER(specifier));
50
50
  }
51
51
  return {
52
52
  immutable,
@@ -1,14 +1,13 @@
1
- import { TextEncoder } from 'util';
2
1
  import { URLSearchParams } from 'url';
2
+ import { TextEncoder } from 'util';
3
+ import { brotliCompressSync, gzipSync } from 'zlib';
3
4
  import { descriptions, logger } from '@lwrjs/diagnostics';
5
+ import { RequestHandlerSpan, getTraceCollector, getTracer } from '@lwrjs/instrumentation';
4
6
  import { getClientRoutes } from '@lwrjs/router';
5
- import { decodeViewPath, extractRequestParams, getClientBootstrapConfigurationRoutes, isURL, parseRequestDepth, REQUEST_DEPTH_KEY, isLocalDev, shortestTtl, isLambdaEnv, } from '@lwrjs/shared-utils';
6
- import { RequestHandlerSpan, getTracer } from '@lwrjs/instrumentation';
7
- import { handleErrors } from './utils/error-handling.js';
7
+ import { CORRELATION_ID, TRUE_CLIENT_IP, decodeViewPath, extractRequestParams, getClientBootstrapConfigurationRoutes, getTraceHeaders, isLambdaEnv, isLocalDev, shortestTtl, } from '@lwrjs/shared-utils';
8
8
  import { LwrViewHandler } from '@lwrjs/view-registry';
9
- import { getTraceCollector } from '@lwrjs/instrumentation';
10
- import { brotliCompressSync, gzipSync } from 'zlib';
11
9
  import { getMrtCompressionThreshold } from './utils/compression.js';
10
+ import { handleErrors } from './utils/error-handling.js';
12
11
  function createViewMiddleware(route, errorRoutes, context, viewHandler) {
13
12
  const errorRoute = errorRoutes.find((route) => route.status === 500);
14
13
  const appConfig = context.appConfig;
@@ -17,12 +16,12 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
17
16
  return async (req, res) => {
18
17
  if (!req.validateEnvironmentRequest(appConfig)) {
19
18
  res.status(400);
20
- res.send(descriptions.APPLICATION.INVALID_ENVIRONMENT(req.params.environment));
19
+ res.send(descriptions.INVALID.INVALID_ENVIRONMENT(req.params.environment));
21
20
  return;
22
21
  }
23
22
  if (!req.validateJsonRequest()) {
24
23
  res.status(400);
25
- res.send(descriptions.APPLICATION.INVALID_JSON());
24
+ res.send(descriptions.INVALID.INVALID_JSON());
26
25
  return;
27
26
  }
28
27
  const { runtimeEnvironment, runtimeParams: defaultRuntimeParams } = req.getRuntimeContext(context.runtimeEnvironment);
@@ -43,13 +42,15 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
43
42
  params: viewRequest.params,
44
43
  query: viewRequest.query,
45
44
  cookie: req.headers?.cookie,
46
- trueClientIP: req.headers && req.headers['true-client-ip'],
45
+ trueClientIP: req.headers?.[TRUE_CLIENT_IP],
46
+ correlationID: req.headers?.[CORRELATION_ID],
47
47
  coreProxy: req.getCoreProxy(appConfig.coreProxy ?? undefined, route.bootstrap?.proxyForSSR),
48
48
  };
49
49
  const resolve = req.isJsonRequest() ? viewHandler.getViewJson : viewHandler.getViewContent;
50
50
  let viewResponse;
51
51
  let resolvedRoute;
52
52
  let traceId;
53
+ let headers = {};
53
54
  try {
54
55
  viewResponse = await getTracer().trace({
55
56
  name: RequestHandlerSpan.GetView,
@@ -61,7 +62,9 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
61
62
  locale: runtimeParams.locale,
62
63
  },
63
64
  }, async (span) => {
65
+ runtimeParams.viewSpanID = span.spanId;
64
66
  traceId = span.traceId;
67
+ headers = getTraceHeaders(runtimeParams, span);
65
68
  const res = await resolve.call(viewHandler, viewRequest, route, runtimeEnvironment, runtimeParams);
66
69
  // Add the view size metric
67
70
  span.setAttributes({
@@ -72,7 +75,9 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
72
75
  resolvedRoute = route;
73
76
  }
74
77
  catch (err) {
75
- if (!errorRoute) {
78
+ if (!errorRoute || runtimeEnvironment.debug) {
79
+ // this is handled by the error middleware
80
+ // when debug mode is on, always show the error screen
76
81
  throw err;
77
82
  }
78
83
  // Log Unexpected Routing Errors
@@ -89,8 +94,9 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
89
94
  resolvedRoute = errorRoute;
90
95
  }
91
96
  finally {
97
+ if (Object.keys(headers).length)
98
+ res.set(headers);
92
99
  if (traceId?.length) {
93
- res.setHeader('x-trace-id', traceId);
94
100
  res.set({
95
101
  'Server-Timing': getTraceCollector().getSpansInTrace(traceId),
96
102
  });
@@ -119,29 +125,10 @@ function createViewMiddleware(route, errorRoutes, context, viewHandler) {
119
125
  }
120
126
  }
121
127
  let status = resolvedRoute.status || viewResponse.status || 200;
122
- const viewDefinitionStatus = viewResponse.metadata?.viewDefinition?.status;
123
128
  if (viewResponse.status === 301 || viewResponse.status === 302) {
124
129
  // route handle redirect status takes precedence
125
130
  status = viewResponse.status;
126
131
  }
127
- else if (viewDefinitionStatus && viewDefinitionStatus.code) {
128
- const origStatus = status;
129
- const { code, location } = viewDefinitionStatus;
130
- const isRedirect = code === 301 || code === 302;
131
- status = code;
132
- if (isRedirect) {
133
- if ((location && isURL(location)) || location?.startsWith('/')) {
134
- res.set({
135
- location: addRedirectQueryParam(location, parseRequestDepth(req.headers, req.query)),
136
- });
137
- }
138
- else {
139
- // reset the status in the event of an invalid location when redirecting
140
- status = origStatus;
141
- logger.warn(`[view-middleware] Ignoring invalid location header: "${location}"`);
142
- }
143
- }
144
- }
145
132
  res.status(status);
146
133
  // LWR@MRT 254 temporary safeguard for "dupe styles" issue causing huge base docs
147
134
  // Re-evaluate for removal once we determine it is no longer needed: W-17201070
@@ -272,7 +259,7 @@ export function viewMiddleware(app, context) {
272
259
  }
273
260
  }
274
261
  logger.debug({ label: `view-middleware`, message: `Add view paths ${paths}` });
275
- app.get(paths, handleErrors(createViewMiddleware(route, errorRoutes, context, viewHandler)));
262
+ app.get(paths, handleErrors(createViewMiddleware(route, errorRoutes, context, viewHandler), true));
276
263
  }
277
264
  // create and attach middleware for bootstrap configurations
278
265
  app.get(getClientBootstrapConfigurationRoutes(), handleErrors(createConfigMiddleware(routes, context, viewHandler)));
@@ -325,14 +312,6 @@ function addDefaultLocaleRedirects(defaultLocale, defaultLocalePaths, defaultRed
325
312
  return res.sendStatus(301);
326
313
  });
327
314
  }
328
- function addRedirectQueryParam(redirectUrl, depth) {
329
- // add a request depth query param to the URL
330
- // the depth header cannot be used since headers cannot be added to a redirect
331
- const fakeOrigin = 'http://parse.com';
332
- const url = isURL(redirectUrl) ? new URL(redirectUrl) : new URL(`${fakeOrigin}${redirectUrl}`);
333
- url.searchParams.set(REQUEST_DEPTH_KEY, String(depth + 1));
334
- return url.toString().replace(fakeOrigin, '');
335
- }
336
315
  // Get number of bytes from a string. Different char encodings can effect size per char.
337
316
  function byteSize(body) {
338
317
  if (Buffer.isBuffer(body)) {
package/package.json CHANGED
@@ -4,7 +4,7 @@
4
4
  "publishConfig": {
5
5
  "access": "public"
6
6
  },
7
- "version": "0.17.2-alpha.2",
7
+ "version": "0.17.2-alpha.20",
8
8
  "homepage": "https://developer.salesforce.com/docs/platform/lwr/overview",
9
9
  "repository": {
10
10
  "type": "git",
@@ -43,34 +43,34 @@
43
43
  "build": "tsc -b"
44
44
  },
45
45
  "dependencies": {
46
- "@lwrjs/app-service": "0.17.2-alpha.2",
47
- "@lwrjs/asset-registry": "0.17.2-alpha.2",
48
- "@lwrjs/asset-transformer": "0.17.2-alpha.2",
49
- "@lwrjs/base-view-provider": "0.17.2-alpha.2",
50
- "@lwrjs/base-view-transformer": "0.17.2-alpha.2",
51
- "@lwrjs/client-modules": "0.17.2-alpha.2",
52
- "@lwrjs/config": "0.17.2-alpha.2",
53
- "@lwrjs/diagnostics": "0.17.2-alpha.2",
54
- "@lwrjs/esbuild": "0.17.2-alpha.2",
55
- "@lwrjs/fs-asset-provider": "0.17.2-alpha.2",
56
- "@lwrjs/fs-watch": "0.17.2-alpha.2",
57
- "@lwrjs/html-view-provider": "0.17.2-alpha.2",
58
- "@lwrjs/instrumentation": "0.17.2-alpha.2",
59
- "@lwrjs/loader": "0.17.2-alpha.2",
60
- "@lwrjs/lwc-module-provider": "0.17.2-alpha.2",
61
- "@lwrjs/lwc-ssr": "0.17.2-alpha.2",
62
- "@lwrjs/markdown-view-provider": "0.17.2-alpha.2",
63
- "@lwrjs/module-bundler": "0.17.2-alpha.2",
64
- "@lwrjs/module-registry": "0.17.2-alpha.2",
65
- "@lwrjs/npm-module-provider": "0.17.2-alpha.2",
66
- "@lwrjs/nunjucks-view-provider": "0.17.2-alpha.2",
67
- "@lwrjs/o11y": "0.17.2-alpha.2",
68
- "@lwrjs/resource-registry": "0.17.2-alpha.2",
69
- "@lwrjs/router": "0.17.2-alpha.2",
70
- "@lwrjs/server": "0.17.2-alpha.2",
71
- "@lwrjs/shared-utils": "0.17.2-alpha.2",
72
- "@lwrjs/static": "0.17.2-alpha.2",
73
- "@lwrjs/view-registry": "0.17.2-alpha.2",
46
+ "@lwrjs/app-service": "0.17.2-alpha.20",
47
+ "@lwrjs/asset-registry": "0.17.2-alpha.20",
48
+ "@lwrjs/asset-transformer": "0.17.2-alpha.20",
49
+ "@lwrjs/base-view-provider": "0.17.2-alpha.20",
50
+ "@lwrjs/base-view-transformer": "0.17.2-alpha.20",
51
+ "@lwrjs/client-modules": "0.17.2-alpha.20",
52
+ "@lwrjs/config": "0.17.2-alpha.20",
53
+ "@lwrjs/diagnostics": "0.17.2-alpha.20",
54
+ "@lwrjs/esbuild": "0.17.2-alpha.20",
55
+ "@lwrjs/fs-asset-provider": "0.17.2-alpha.20",
56
+ "@lwrjs/fs-watch": "0.17.2-alpha.20",
57
+ "@lwrjs/html-view-provider": "0.17.2-alpha.20",
58
+ "@lwrjs/instrumentation": "0.17.2-alpha.20",
59
+ "@lwrjs/loader": "0.17.2-alpha.20",
60
+ "@lwrjs/lwc-module-provider": "0.17.2-alpha.20",
61
+ "@lwrjs/lwc-ssr": "0.17.2-alpha.20",
62
+ "@lwrjs/markdown-view-provider": "0.17.2-alpha.20",
63
+ "@lwrjs/module-bundler": "0.17.2-alpha.20",
64
+ "@lwrjs/module-registry": "0.17.2-alpha.20",
65
+ "@lwrjs/npm-module-provider": "0.17.2-alpha.20",
66
+ "@lwrjs/nunjucks-view-provider": "0.17.2-alpha.20",
67
+ "@lwrjs/o11y": "0.17.2-alpha.20",
68
+ "@lwrjs/resource-registry": "0.17.2-alpha.20",
69
+ "@lwrjs/router": "0.17.2-alpha.20",
70
+ "@lwrjs/server": "0.17.2-alpha.20",
71
+ "@lwrjs/shared-utils": "0.17.2-alpha.20",
72
+ "@lwrjs/static": "0.17.2-alpha.20",
73
+ "@lwrjs/view-registry": "0.17.2-alpha.20",
74
74
  "chokidar": "^3.6.0",
75
75
  "esbuild": "^0.9.7",
76
76
  "fs-extra": "^11.2.0",
@@ -80,7 +80,7 @@
80
80
  "ws": "^8.18.0"
81
81
  },
82
82
  "devDependencies": {
83
- "@lwrjs/types": "0.17.2-alpha.2",
83
+ "@lwrjs/types": "0.17.2-alpha.20",
84
84
  "@types/ws": "^8.5.12",
85
85
  "memfs": "^4.13.0"
86
86
  },
@@ -88,10 +88,10 @@
88
88
  "lwc": ">= 2.x"
89
89
  },
90
90
  "engines": {
91
- "node": ">=18.0.0"
91
+ "node": ">=20.0.0"
92
92
  },
93
93
  "volta": {
94
94
  "extends": "../../../package.json"
95
95
  },
96
- "gitHead": "739b237f5d7f2c1989142cb505a56cc763f21976"
96
+ "gitHead": "871213620dec8ff886be421339f1e90e86dbee96"
97
97
  }