@jsenv/server 16.0.6 → 16.0.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/client/default_body_4xx_5xx/4xx.html +8 -1
- package/dist/client/route_inspector/route_inspector.html +8 -1
- package/dist/jsenv_server.js +29 -10
- package/package.json +7 -5
- package/src/services/autoreload_on_server_restart/client/autoreload_on_server_restart.js +8 -1
- package/src/services/error_handler/jsenv_service_error_handler.js +2 -8
|
@@ -121,6 +121,9 @@
|
|
|
121
121
|
};
|
|
122
122
|
|
|
123
123
|
const initialWebSocket = await connect();
|
|
124
|
+
if (!initialWebSocket) {
|
|
125
|
+
return;
|
|
126
|
+
}
|
|
124
127
|
initialWebSocket.onclose = async () => {
|
|
125
128
|
console.info("connection to server lost, trying to reconnect");
|
|
126
129
|
const retry = async () => {
|
|
@@ -165,12 +168,16 @@
|
|
|
165
168
|
);
|
|
166
169
|
}
|
|
167
170
|
|
|
171
|
+
const websocketEndpoint =
|
|
172
|
+
document.currentScript.getAttribute("data-ws-endpoint") ||
|
|
173
|
+
"/.internal/alive.websocket";
|
|
174
|
+
|
|
168
175
|
const jsenvAutoreloadOnServerRestartElement =
|
|
169
176
|
new JsenvAutoreloadOnServerRestart({
|
|
170
177
|
url: (() => {
|
|
171
178
|
const websocketScheme =
|
|
172
179
|
self.location.protocol === "https:" ? "wss" : "ws";
|
|
173
|
-
const websocketUrl = `${websocketScheme}://${self.location.host}
|
|
180
|
+
const websocketUrl = `${websocketScheme}://${self.location.host}${websocketEndpoint}`;
|
|
174
181
|
return websocketUrl;
|
|
175
182
|
})(),
|
|
176
183
|
});
|
|
@@ -278,6 +278,9 @@
|
|
|
278
278
|
};
|
|
279
279
|
|
|
280
280
|
const initialWebSocket = await connect();
|
|
281
|
+
if (!initialWebSocket) {
|
|
282
|
+
return;
|
|
283
|
+
}
|
|
281
284
|
initialWebSocket.onclose = async () => {
|
|
282
285
|
console.info("connection to server lost, trying to reconnect");
|
|
283
286
|
const retry = async () => {
|
|
@@ -322,12 +325,16 @@
|
|
|
322
325
|
);
|
|
323
326
|
}
|
|
324
327
|
|
|
328
|
+
const websocketEndpoint =
|
|
329
|
+
document.currentScript.getAttribute("data-ws-endpoint") ||
|
|
330
|
+
"/.internal/alive.websocket";
|
|
331
|
+
|
|
325
332
|
const jsenvAutoreloadOnServerRestartElement =
|
|
326
333
|
new JsenvAutoreloadOnServerRestart({
|
|
327
334
|
url: (() => {
|
|
328
335
|
const websocketScheme =
|
|
329
336
|
self.location.protocol === "https:" ? "wss" : "ws";
|
|
330
|
-
const websocketUrl = `${websocketScheme}://${self.location.host}
|
|
337
|
+
const websocketUrl = `${websocketScheme}://${self.location.host}${websocketEndpoint}`;
|
|
331
338
|
return websocketUrl;
|
|
332
339
|
})(),
|
|
333
340
|
});
|
package/dist/jsenv_server.js
CHANGED
|
@@ -551,6 +551,29 @@ ${
|
|
|
551
551
|
return text;
|
|
552
552
|
};
|
|
553
553
|
|
|
554
|
+
const errorToHTML = (error) => {
|
|
555
|
+
const errorIsAPrimitive =
|
|
556
|
+
error === null ||
|
|
557
|
+
(typeof error !== "object" && typeof error !== "function");
|
|
558
|
+
|
|
559
|
+
if (errorIsAPrimitive) {
|
|
560
|
+
if (typeof error === "string") {
|
|
561
|
+
return `<pre>${escapeHtml(error)}</pre>`;
|
|
562
|
+
}
|
|
563
|
+
return `<pre>${JSON.stringify(error, null, " ")}</pre>`;
|
|
564
|
+
}
|
|
565
|
+
return `<pre>${escapeHtml(error.stack)}</pre>`;
|
|
566
|
+
};
|
|
567
|
+
|
|
568
|
+
const escapeHtml = (string) => {
|
|
569
|
+
return string
|
|
570
|
+
.replace(/&/g, "&")
|
|
571
|
+
.replace(/</g, "<")
|
|
572
|
+
.replace(/>/g, ">")
|
|
573
|
+
.replace(/"/g, """)
|
|
574
|
+
.replace(/'/g, "'");
|
|
575
|
+
};
|
|
576
|
+
|
|
554
577
|
const LOG_LEVEL_OFF = "off";
|
|
555
578
|
|
|
556
579
|
const LOG_LEVEL_DEBUG = "debug";
|
|
@@ -3166,8 +3189,11 @@ const getParentDirectoryUrl = (url) => {
|
|
|
3166
3189
|
return new URL(url.endsWith("/") ? "../" : "./", url).href;
|
|
3167
3190
|
};
|
|
3168
3191
|
|
|
3169
|
-
const
|
|
3192
|
+
const findSelfOrAncestorDirectoryUrl = (url, callback) => {
|
|
3170
3193
|
url = String(url);
|
|
3194
|
+
if (!url.endsWith("/")) {
|
|
3195
|
+
url = new URL("./", url).href;
|
|
3196
|
+
}
|
|
3171
3197
|
while (url !== "file:///") {
|
|
3172
3198
|
if (callback(url)) {
|
|
3173
3199
|
return url;
|
|
@@ -3178,7 +3204,7 @@ const findAncestorDirectoryUrl = (url, callback) => {
|
|
|
3178
3204
|
};
|
|
3179
3205
|
|
|
3180
3206
|
const lookupPackageDirectory = (currentUrl) => {
|
|
3181
|
-
return
|
|
3207
|
+
return findSelfOrAncestorDirectoryUrl(currentUrl, (ancestorDirectoryUrl) => {
|
|
3182
3208
|
const potentialPackageJsonFileUrl = `${ancestorDirectoryUrl}package.json`;
|
|
3183
3209
|
return existsSync(new URL(potentialPackageJsonFileUrl));
|
|
3184
3210
|
});
|
|
@@ -7477,14 +7503,7 @@ const jsenvServiceErrorHandler = ({ sendErrorDetails = false } = {}) => {
|
|
|
7477
7503
|
return `<p>Details not available: to enable them use jsenvServiceErrorHandler({ sendErrorDetails: true }).</p>`;
|
|
7478
7504
|
};
|
|
7479
7505
|
const renderHtmlForErrorWithDetails = () => {
|
|
7480
|
-
|
|
7481
|
-
return `<pre>${JSON.stringify(
|
|
7482
|
-
serverInternalError,
|
|
7483
|
-
null,
|
|
7484
|
-
" ",
|
|
7485
|
-
)}</pre>`;
|
|
7486
|
-
}
|
|
7487
|
-
return `<pre>${serverInternalError.stack}</pre>`;
|
|
7506
|
+
return errorToHTML(serverInternalError);
|
|
7488
7507
|
};
|
|
7489
7508
|
|
|
7490
7509
|
const internalErrorHtmlTemplate = readFileSync(
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jsenv/server",
|
|
3
|
-
"version": "16.0.
|
|
3
|
+
"version": "16.0.8",
|
|
4
4
|
"description": "A modern Node.js HTTP server with declarative routing, content negotiation, and WebSocket support",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": {
|
|
@@ -33,7 +33,9 @@
|
|
|
33
33
|
"/dist/",
|
|
34
34
|
"/src/"
|
|
35
35
|
],
|
|
36
|
-
"sideEffects":
|
|
36
|
+
"sideEffects": [
|
|
37
|
+
"./dist/jsenv_server_node_modules.js"
|
|
38
|
+
],
|
|
37
39
|
"scripts": {
|
|
38
40
|
"build": "node --experimental-import-meta-resolve ./scripts/build.mjs",
|
|
39
41
|
"prepublishOnly": "npm run build"
|
|
@@ -41,14 +43,14 @@
|
|
|
41
43
|
"dependencies": {
|
|
42
44
|
"launch-editor": "2.10.0",
|
|
43
45
|
"@jsenv/abort": "4.3.1",
|
|
44
|
-
"@jsenv/humanize": "1.
|
|
46
|
+
"@jsenv/humanize": "1.5.0",
|
|
45
47
|
"@jsenv/url-meta": "8.5.6",
|
|
46
48
|
"@jsenv/utils": "2.3.0",
|
|
47
49
|
"ws": "8.18.1",
|
|
48
50
|
"formidable": "3.5.2"
|
|
49
51
|
},
|
|
50
52
|
"devDependencies": {
|
|
51
|
-
"eventsource": "3.0.
|
|
52
|
-
"undici": "7.
|
|
53
|
+
"eventsource": "3.0.6",
|
|
54
|
+
"undici": "7.8.0"
|
|
53
55
|
}
|
|
54
56
|
}
|
|
@@ -53,6 +53,9 @@ class JsenvAutoreloadOnServerRestart extends HTMLElement {
|
|
|
53
53
|
};
|
|
54
54
|
|
|
55
55
|
const initialWebSocket = await connect();
|
|
56
|
+
if (!initialWebSocket) {
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
56
59
|
initialWebSocket.onclose = async () => {
|
|
57
60
|
console.info("connection to server lost, trying to reconnect");
|
|
58
61
|
const retry = async () => {
|
|
@@ -97,12 +100,16 @@ if (!customElements.get("jsenv-autoreload-on-server-restart")) {
|
|
|
97
100
|
);
|
|
98
101
|
}
|
|
99
102
|
|
|
103
|
+
const websocketEndpoint =
|
|
104
|
+
document.currentScript.getAttribute("data-ws-endpoint") ||
|
|
105
|
+
"/.internal/alive.websocket";
|
|
106
|
+
|
|
100
107
|
const jsenvAutoreloadOnServerRestartElement =
|
|
101
108
|
new JsenvAutoreloadOnServerRestart({
|
|
102
109
|
url: (() => {
|
|
103
110
|
const websocketScheme =
|
|
104
111
|
self.location.protocol === "https:" ? "wss" : "ws";
|
|
105
|
-
const websocketUrl = `${websocketScheme}://${self.location.host}
|
|
112
|
+
const websocketUrl = `${websocketScheme}://${self.location.host}${websocketEndpoint}`;
|
|
106
113
|
return websocketUrl;
|
|
107
114
|
})(),
|
|
108
115
|
});
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { errorToHTML } from "@jsenv/humanize";
|
|
1
2
|
import { readFileSync } from "node:fs";
|
|
2
3
|
import { pickContentType } from "../../content_negotiation/pick_content_type.js";
|
|
3
4
|
import { replacePlaceholdersInHtml } from "../../replace_placeholder_in_html.js";
|
|
@@ -36,14 +37,7 @@ export const jsenvServiceErrorHandler = ({ sendErrorDetails = false } = {}) => {
|
|
|
36
37
|
return `<p>Details not available: to enable them use jsenvServiceErrorHandler({ sendErrorDetails: true }).</p>`;
|
|
37
38
|
};
|
|
38
39
|
const renderHtmlForErrorWithDetails = () => {
|
|
39
|
-
|
|
40
|
-
return `<pre>${JSON.stringify(
|
|
41
|
-
serverInternalError,
|
|
42
|
-
null,
|
|
43
|
-
" ",
|
|
44
|
-
)}</pre>`;
|
|
45
|
-
}
|
|
46
|
-
return `<pre>${serverInternalError.stack}</pre>`;
|
|
40
|
+
return errorToHTML(serverInternalError);
|
|
47
41
|
};
|
|
48
42
|
|
|
49
43
|
const internalErrorHtmlTemplate = readFileSync(
|