bun-dev-server 0.0.4 → 0.0.6
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.md +6 -0
- package/bunManifest.ts +18 -0
- package/bunServeConfig.ts +2 -0
- package/index.ts +32 -10
- package/indexHTMLTemplate.ejs +3 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
```
|
|
4
4
|
//devserver.ts
|
|
5
5
|
import {startBunDevServer} from "bun-dev-server"
|
|
6
|
+
import { file } from "bun"
|
|
6
7
|
|
|
7
8
|
startBunDevServer({
|
|
8
9
|
buildConfig: {
|
|
@@ -14,6 +15,11 @@ startBunDevServer({
|
|
|
14
15
|
chunk: "chunks/[name]-[hash].[ext]",
|
|
15
16
|
}
|
|
16
17
|
},
|
|
18
|
+
tls: {
|
|
19
|
+
cert: file("./serve_cert.pem"),
|
|
20
|
+
key: file("./serve_key.pem"),
|
|
21
|
+
},
|
|
22
|
+
writeManifest: true,
|
|
17
23
|
cleanServePath: true,
|
|
18
24
|
port: 4567,
|
|
19
25
|
enableTypeScriptWatch: true,
|
package/bunManifest.ts
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { type BuildOutput, write, pathToFileURL } from "bun";
|
|
2
|
+
export function writeManifest(output: BuildOutput, outdir: string, manifestName = "manifest.txt") {
|
|
3
|
+
const entryPoints = output.outputs.filter(o => o.kind === "entry-point");
|
|
4
|
+
const epTable = [];
|
|
5
|
+
for (const ep of entryPoints) {
|
|
6
|
+
const basePathUrl = pathToFileURL(outdir);
|
|
7
|
+
const epUrl = pathToFileURL(ep.path);
|
|
8
|
+
const relativePath = epUrl.href.replace(`${basePathUrl.href}/`, "");
|
|
9
|
+
const nameNoJs = relativePath.replace(".js", "");
|
|
10
|
+
const hashedImport = `${relativePath}?${ep.hash}`;
|
|
11
|
+
epTable.push({ name: nameNoJs, path: hashedImport });
|
|
12
|
+
}
|
|
13
|
+
const outObj = {};
|
|
14
|
+
for (const element of epTable) {
|
|
15
|
+
Object.assign(outObj, { [element.name]: { js: [`${element.path}`] } });
|
|
16
|
+
}
|
|
17
|
+
write(`${outdir}/${manifestName}`, JSON.stringify(outObj));
|
|
18
|
+
}
|
package/bunServeConfig.ts
CHANGED
|
@@ -5,6 +5,8 @@ export interface BunDevServerConfig extends Partial<BunDevServerSocketConfig> {
|
|
|
5
5
|
buildConfig: BuildConfig;
|
|
6
6
|
watchDir?: string;
|
|
7
7
|
enableTypeScriptWatch?: boolean;
|
|
8
|
+
writeManifest?: boolean;
|
|
9
|
+
manifestName?: string;
|
|
8
10
|
/**
|
|
9
11
|
* The path to the directory to serve files from.
|
|
10
12
|
* Takes precedence over `buildConfig.outdir`.
|
package/index.ts
CHANGED
|
@@ -8,6 +8,7 @@ import { type FileChangeInfo } from "fs/promises";
|
|
|
8
8
|
import { startTSWatcher } from "./bunTSWatcher";
|
|
9
9
|
import { getBunHMRFooter } from "./bunHmrPlugin";
|
|
10
10
|
import { type BunDevServerConfig } from "./bunServeConfig";
|
|
11
|
+
import { writeManifest } from "./bunManifest";
|
|
11
12
|
|
|
12
13
|
|
|
13
14
|
|
|
@@ -49,14 +50,15 @@ export async function startBunDevServer(serverConfig: BunDevServerConfig) {
|
|
|
49
50
|
development: true,
|
|
50
51
|
tls: finalConfig.tls,
|
|
51
52
|
async fetch(req, server) {
|
|
52
|
-
if(req.method === "OPTIONS") {
|
|
53
|
+
if (req.method === "OPTIONS") {
|
|
53
54
|
const response = new Response("", { status: 200 });
|
|
54
|
-
response
|
|
55
|
-
response.headers.set("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
|
|
55
|
+
augumentHeaders(response);
|
|
56
56
|
return response;
|
|
57
57
|
}
|
|
58
58
|
if (req.url.toLowerCase().endsWith("/favicon.ico")) {
|
|
59
|
-
|
|
59
|
+
const response = new Response("", { status: 404 });
|
|
60
|
+
augumentHeaders(response);
|
|
61
|
+
return response;
|
|
60
62
|
}
|
|
61
63
|
if (req.url.toLowerCase().endsWith(finalConfig.websocketPath)) {
|
|
62
64
|
if (server.upgrade(req)) {
|
|
@@ -81,7 +83,9 @@ export async function startBunDevServer(serverConfig: BunDevServerConfig) {
|
|
|
81
83
|
|
|
82
84
|
if (!isDirectory) {
|
|
83
85
|
const fl = Bun.file(dst + requestPath);
|
|
84
|
-
|
|
86
|
+
const response = new Response(fl);
|
|
87
|
+
augumentHeaders(response);
|
|
88
|
+
return response;
|
|
85
89
|
}
|
|
86
90
|
try {
|
|
87
91
|
const allEntries = await readdir(dst + requestPath, {
|
|
@@ -104,9 +108,13 @@ export async function startBunDevServer(serverConfig: BunDevServerConfig) {
|
|
|
104
108
|
};
|
|
105
109
|
});
|
|
106
110
|
const rnd = render(finalConfig.serveOutputEjs, { dirs, files });
|
|
107
|
-
|
|
111
|
+
const response = new Response(rnd, { headers: { "Content-Type": "text/html" } });
|
|
112
|
+
augumentHeaders(response);
|
|
113
|
+
return response;
|
|
108
114
|
} catch {
|
|
109
|
-
|
|
115
|
+
const response = new Response("Not Found", { status: 404 });
|
|
116
|
+
augumentHeaders(response);
|
|
117
|
+
return response;
|
|
110
118
|
}
|
|
111
119
|
},
|
|
112
120
|
|
|
@@ -125,6 +133,9 @@ export async function startBunDevServer(serverConfig: BunDevServerConfig) {
|
|
|
125
133
|
const output = await Bun.build(buildCfg);
|
|
126
134
|
publishOutputLogs(output, { filename: "Initial", eventType: "change" });
|
|
127
135
|
publishIndexHTML(output, { filename: "Initial", eventType: "change" });
|
|
136
|
+
if (finalConfig.writeManifest) {
|
|
137
|
+
writeManifest(output, dst, finalConfig.manifestName);
|
|
138
|
+
}
|
|
128
139
|
// $`tsc --watch`.then((tsc) => {
|
|
129
140
|
// console.log("ASDASD");
|
|
130
141
|
// });
|
|
@@ -144,6 +155,10 @@ export async function startBunDevServer(serverConfig: BunDevServerConfig) {
|
|
|
144
155
|
const output = await Bun.build(buildCfg);
|
|
145
156
|
publishOutputLogs(output, event);
|
|
146
157
|
publishIndexHTML(output, event);
|
|
158
|
+
if (finalConfig.writeManifest) {
|
|
159
|
+
writeManifest(output, dst, finalConfig.manifestName);
|
|
160
|
+
}
|
|
161
|
+
|
|
147
162
|
}
|
|
148
163
|
|
|
149
164
|
function publishOutputLogs(output: Bun.BuildOutput, event: FileChangeInfo<string>) {
|
|
@@ -163,17 +178,24 @@ export async function startBunDevServer(serverConfig: BunDevServerConfig) {
|
|
|
163
178
|
}
|
|
164
179
|
|
|
165
180
|
function publishIndexHTML(output: Bun.BuildOutput, event: FileChangeInfo<string>) {
|
|
166
|
-
const
|
|
167
|
-
|
|
181
|
+
const eps = output.outputs.filter(o => o.kind === "entry-point");
|
|
182
|
+
const hashedImports: string[] = [];
|
|
183
|
+
for (const ep of eps) {
|
|
168
184
|
const basePathUrl = Bun.pathToFileURL(dst);
|
|
169
185
|
const epUrl = Bun.pathToFileURL(ep.path);
|
|
170
186
|
const hashedImport = `${epUrl.href.replace(basePathUrl.href, "")}?${ep.hash}`;
|
|
171
|
-
|
|
187
|
+
hashedImports.push(hashedImport);
|
|
172
188
|
}
|
|
189
|
+
Bun.write(dst + "/index.html", render(finalConfig.serveOutputHtml, { hashedImports }));
|
|
173
190
|
}
|
|
174
191
|
|
|
175
192
|
}
|
|
176
193
|
|
|
194
|
+
function augumentHeaders(response: Response) {
|
|
195
|
+
response.headers.set("Access-Control-Allow-Origin", "*");
|
|
196
|
+
response.headers.set("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
|
|
197
|
+
}
|
|
198
|
+
|
|
177
199
|
async function cleanDirectory(dst: string) {
|
|
178
200
|
const { stderr, exitCode } = await $`rm -rf ${dst}/*`.nothrow();
|
|
179
201
|
if (exitCode !== 0) {
|
package/indexHTMLTemplate.ejs
CHANGED
|
@@ -4,7 +4,9 @@
|
|
|
4
4
|
<meta charset="UTF-8" />
|
|
5
5
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
6
6
|
<title>Bun HTML File</title>
|
|
7
|
-
|
|
7
|
+
<% for (const hashedJs of hashedImports) { %>
|
|
8
|
+
<script type="module" src="<%= hashedJs %>"></script>
|
|
9
|
+
<% } %>
|
|
8
10
|
</head>
|
|
9
11
|
|
|
10
12
|
<body>
|