@docubook/flame 2.0.0-beta.0 → 2.0.0-beta.2
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/.docu/components/ScrollTo.tsx +17 -11
- package/.docu/components/Toc.tsx +32 -7
- package/.docu/lib/build.deno.js +6 -9
- package/.docu/lib/build.deno.js.map +1 -0
- package/.docu/lib/build.impl-BJsi28mD.js +377 -0
- package/.docu/lib/build.impl-BJsi28mD.js.map +1 -0
- package/.docu/lib/build.impl-yVLaa1eQ.js +2 -0
- package/.docu/lib/build.node.js +6 -9
- package/.docu/lib/build.node.js.map +1 -0
- package/.docu/lib/clean.js +25 -25
- package/.docu/lib/clean.js.map +1 -0
- package/.docu/lib/deno-DmEaKggj.js +20 -0
- package/.docu/lib/deno-DmEaKggj.js.map +1 -0
- package/.docu/lib/deploy.deno.js +9 -9
- package/.docu/lib/deploy.deno.js.map +1 -0
- package/.docu/lib/deploy.node.js +8 -8
- package/.docu/lib/deploy.node.js.map +1 -0
- package/.docu/lib/deploy.shared-D3UWafa6.js +295 -0
- package/.docu/lib/deploy.shared-D3UWafa6.js.map +1 -0
- package/.docu/lib/html.shared-DSn-7_6t.js +2467 -0
- package/.docu/lib/html.shared-DSn-7_6t.js.map +1 -0
- package/.docu/lib/logger-CycvLCrQ.js +312 -0
- package/.docu/lib/logger-CycvLCrQ.js.map +1 -0
- package/.docu/lib/node-DPTySdwG.js +80 -0
- package/.docu/lib/node-DPTySdwG.js.map +1 -0
- package/.docu/lib/paths-BtOIPBQ9.js +52 -0
- package/.docu/lib/paths-BtOIPBQ9.js.map +1 -0
- package/.docu/lib/preview.deno.js +7 -11
- package/.docu/lib/preview.deno.js.map +1 -0
- package/.docu/lib/preview.impl-CXJS2tQS.js +77 -0
- package/.docu/lib/preview.impl-CXJS2tQS.js.map +1 -0
- package/.docu/lib/preview.node.js +7 -11
- package/.docu/lib/preview.node.js.map +1 -0
- package/.docu/lib/server.deno.js +7 -12
- package/.docu/lib/server.deno.js.map +1 -0
- package/.docu/lib/server.impl-CJuWimfN.js +358 -0
- package/.docu/lib/server.impl-CJuWimfN.js.map +1 -0
- package/.docu/lib/server.node.js +7 -12
- package/.docu/lib/server.node.js.map +1 -0
- package/.docu/lib/utils-DA17MyQG.js +167 -0
- package/.docu/lib/utils-DA17MyQG.js.map +1 -0
- package/.docu/node/hydrate.node.ts +116 -166
- package/bin/compile-lib.mjs +30 -28
- package/package.json +6 -6
- package/.docu/lib/build.impl-S4DS5XPH.js +0 -12
- package/.docu/lib/chunk-4IQXHHPF.js +0 -62
- package/.docu/lib/chunk-C3RCUTUE.js +0 -470
- package/.docu/lib/chunk-D3QTSBR4.js +0 -434
- package/.docu/lib/chunk-EOK6KATZ.js +0 -191
- package/.docu/lib/chunk-IVM5UM44.js +0 -301
- package/.docu/lib/chunk-JMQI3FKV.js +0 -92
- package/.docu/lib/chunk-LXJLSXQI.js +0 -2691
- package/.docu/lib/chunk-O326MYJE.js +0 -330
- package/.docu/lib/chunk-UISOJ4RW.js +0 -114
|
@@ -1,330 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
DIST_DIR,
|
|
3
|
-
FRAMEWORK_ROOT,
|
|
4
|
-
PROJECT_ROOT
|
|
5
|
-
} from "./chunk-4IQXHHPF.js";
|
|
6
|
-
|
|
7
|
-
// .docu/node/deploy.shared.ts
|
|
8
|
-
import { writeFile, mkdir } from "node:fs/promises";
|
|
9
|
-
import { existsSync, readFileSync } from "node:fs";
|
|
10
|
-
import { join, resolve } from "node:path";
|
|
11
|
-
var FLAME_MAJOR = JSON.parse(
|
|
12
|
-
readFileSync(resolve(FRAMEWORK_ROOT, "package.json"), "utf-8")
|
|
13
|
-
).version.split(".")[0];
|
|
14
|
-
var WORKFLOW_DIR = join(PROJECT_ROOT, ".github/workflows");
|
|
15
|
-
var WORKFLOW_FILE = join(WORKFLOW_DIR, "deploy.yml");
|
|
16
|
-
var NGINX_CONF = `server {
|
|
17
|
-
listen 80;
|
|
18
|
-
server_name _;
|
|
19
|
-
root /usr/share/nginx/html;
|
|
20
|
-
index index.html;
|
|
21
|
-
|
|
22
|
-
gzip on;
|
|
23
|
-
gzip_types text/html text/css application/javascript image/svg+xml;
|
|
24
|
-
|
|
25
|
-
# Security headers (HSTS effective when HTTPS is terminated upstream)
|
|
26
|
-
add_header X-Frame-Options "DENY" always;
|
|
27
|
-
add_header X-Content-Type-Options "nosniff" always;
|
|
28
|
-
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;
|
|
29
|
-
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
|
|
30
|
-
add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always;
|
|
31
|
-
add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; img-src 'self' https: data:; font-src 'self' data:; connect-src 'self' https:; frame-src https://www.youtube-nocookie.com; frame-ancestors 'none'" always;
|
|
32
|
-
|
|
33
|
-
location /assets/ {
|
|
34
|
-
expires 1y;
|
|
35
|
-
add_header Cache-Control "public, immutable";
|
|
36
|
-
add_header X-Frame-Options "DENY" always;
|
|
37
|
-
add_header X-Content-Type-Options "nosniff" always;
|
|
38
|
-
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;
|
|
39
|
-
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
|
|
40
|
-
add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always;
|
|
41
|
-
add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; img-src 'self' https: data:; font-src 'self' data:; connect-src 'self' https:; frame-src https://www.youtube-nocookie.com; frame-ancestors 'none'" always;
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
location /docs/assets/ {
|
|
45
|
-
expires 7d;
|
|
46
|
-
add_header Cache-Control "public";
|
|
47
|
-
add_header X-Frame-Options "DENY" always;
|
|
48
|
-
add_header X-Content-Type-Options "nosniff" always;
|
|
49
|
-
add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;
|
|
50
|
-
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
|
|
51
|
-
add_header Permissions-Policy "camera=(), microphone=(), geolocation=()" always;
|
|
52
|
-
add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; img-src 'self' https: data:; font-src 'self' data:; connect-src 'self' https:; frame-src https://www.youtube-nocookie.com; frame-ancestors 'none'" always;
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
location / {
|
|
56
|
-
try_files $uri $uri.html $uri/ =404;
|
|
57
|
-
}
|
|
58
|
-
}
|
|
59
|
-
`;
|
|
60
|
-
var DOCKERIGNORE = `node_modules
|
|
61
|
-
*.DS_Store
|
|
62
|
-
.docu/dist
|
|
63
|
-
.docu/lib
|
|
64
|
-
.env
|
|
65
|
-
.env.*
|
|
66
|
-
.npmrc
|
|
67
|
-
*.log
|
|
68
|
-
`;
|
|
69
|
-
function detectPkgManager(dir) {
|
|
70
|
-
const bunLockFile = existsSync(join(dir, "bun.lock")) ? "bun.lock" : existsSync(join(dir, "bun.lockb")) ? "bun.lockb" : null;
|
|
71
|
-
if (bunLockFile) {
|
|
72
|
-
return {
|
|
73
|
-
baseImage: "oven/bun:1-debian",
|
|
74
|
-
lockFile: bunLockFile,
|
|
75
|
-
installCmd: "bun install --frozen-lockfile",
|
|
76
|
-
runCmd: "bun",
|
|
77
|
-
cache: "",
|
|
78
|
-
setupAction: "bun"
|
|
79
|
-
};
|
|
80
|
-
}
|
|
81
|
-
if (existsSync(join(dir, "pnpm-lock.yaml"))) {
|
|
82
|
-
return {
|
|
83
|
-
baseImage: "node:22-alpine",
|
|
84
|
-
lockFile: "pnpm-lock.yaml",
|
|
85
|
-
installCmd: "corepack enable && pnpm install --frozen-lockfile",
|
|
86
|
-
runCmd: "pnpm",
|
|
87
|
-
cache: "pnpm",
|
|
88
|
-
setupAction: "pnpm"
|
|
89
|
-
};
|
|
90
|
-
}
|
|
91
|
-
if (existsSync(join(dir, "yarn.lock"))) {
|
|
92
|
-
return {
|
|
93
|
-
baseImage: "node:22-alpine",
|
|
94
|
-
lockFile: "yarn.lock",
|
|
95
|
-
installCmd: "yarn install --frozen-lockfile",
|
|
96
|
-
runCmd: "yarn",
|
|
97
|
-
cache: "yarn",
|
|
98
|
-
setupAction: "node"
|
|
99
|
-
};
|
|
100
|
-
}
|
|
101
|
-
return {
|
|
102
|
-
baseImage: "node:22-alpine",
|
|
103
|
-
lockFile: "package-lock.json",
|
|
104
|
-
installCmd: "npm ci",
|
|
105
|
-
runCmd: "npm",
|
|
106
|
-
cache: "npm",
|
|
107
|
-
setupAction: "node"
|
|
108
|
-
};
|
|
109
|
-
}
|
|
110
|
-
var HEADERS_FILE = `/*
|
|
111
|
-
X-Frame-Options: DENY
|
|
112
|
-
X-Content-Type-Options: nosniff
|
|
113
|
-
Strict-Transport-Security: max-age=63072000; includeSubDomains; preload
|
|
114
|
-
Referrer-Policy: strict-origin-when-cross-origin
|
|
115
|
-
Permissions-Policy: camera=(), microphone=(), geolocation=()
|
|
116
|
-
Content-Security-Policy: default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; img-src 'self' https: data:; font-src 'self' data:; connect-src 'self' https:; frame-src https://www.youtube-nocookie.com; frame-ancestors 'none'
|
|
117
|
-
|
|
118
|
-
/assets/*
|
|
119
|
-
Cache-Control: public, max-age=31536000, immutable
|
|
120
|
-
`;
|
|
121
|
-
var isDocker = !!process.env.FLAME_DEPLOY_DOCKER;
|
|
122
|
-
var isSilent = !!process.env.FLAME_DEPLOY_SILENT;
|
|
123
|
-
var isCi = !!process.env.FLAME_DEPLOY_CI;
|
|
124
|
-
var log = isSilent ? { info: () => {
|
|
125
|
-
}, ok: () => {
|
|
126
|
-
}, created: () => {
|
|
127
|
-
}, out: () => {
|
|
128
|
-
} } : {
|
|
129
|
-
info: (m) => console.log(m),
|
|
130
|
-
ok: () => console.log("\n\u2705 Ready to deploy!"),
|
|
131
|
-
created: (m) => console.log(m),
|
|
132
|
-
out: (m) => console.log(m)
|
|
133
|
-
};
|
|
134
|
-
async function runBuild() {
|
|
135
|
-
process.env.NODE_ENV = "production";
|
|
136
|
-
if (isSilent) {
|
|
137
|
-
process.env.FLAME_BUILD_SILENT = "1";
|
|
138
|
-
process.env.LOG_LEVEL = "error";
|
|
139
|
-
}
|
|
140
|
-
const { runBuildCli } = await import("./build.impl-S4DS5XPH.js");
|
|
141
|
-
await runBuildCli();
|
|
142
|
-
}
|
|
143
|
-
async function writeDockerFiles() {
|
|
144
|
-
const dockerDir = PROJECT_ROOT;
|
|
145
|
-
if (!existsSync(join(dockerDir, "Dockerfile"))) {
|
|
146
|
-
await writeFile(
|
|
147
|
-
join(dockerDir, "Dockerfile"),
|
|
148
|
-
`FROM ghcr.io/docubook/flame:${FLAME_MAJOR} AS builder
|
|
149
|
-
ENV NODE_ENV=production
|
|
150
|
-
WORKDIR /app
|
|
151
|
-
COPY . .
|
|
152
|
-
RUN flame build
|
|
153
|
-
|
|
154
|
-
FROM nginx:alpine
|
|
155
|
-
COPY --from=builder /app/.docu/dist /usr/share/nginx/html
|
|
156
|
-
COPY nginx.conf /etc/nginx/conf.d/default.conf
|
|
157
|
-
EXPOSE 80
|
|
158
|
-
CMD ["nginx", "-g", "daemon off;"]
|
|
159
|
-
`
|
|
160
|
-
);
|
|
161
|
-
log.created("\u{1F4C4} Created Dockerfile");
|
|
162
|
-
}
|
|
163
|
-
if (!existsSync(join(dockerDir, "nginx.conf"))) {
|
|
164
|
-
await writeFile(join(dockerDir, "nginx.conf"), NGINX_CONF);
|
|
165
|
-
log.created("\u{1F4C4} Created nginx.conf");
|
|
166
|
-
}
|
|
167
|
-
if (!existsSync(join(dockerDir, ".dockerignore"))) {
|
|
168
|
-
await writeFile(join(dockerDir, ".dockerignore"), DOCKERIGNORE);
|
|
169
|
-
log.created("\u{1F4C4} Created .dockerignore");
|
|
170
|
-
}
|
|
171
|
-
}
|
|
172
|
-
function generateWorkflowYml() {
|
|
173
|
-
const pm = detectPkgManager(PROJECT_ROOT);
|
|
174
|
-
const setupSteps = [
|
|
175
|
-
" - uses: actions/checkout@v7",
|
|
176
|
-
" with:",
|
|
177
|
-
" fetch-depth: 0",
|
|
178
|
-
""
|
|
179
|
-
];
|
|
180
|
-
if (pm.setupAction === "bun") {
|
|
181
|
-
setupSteps.push(
|
|
182
|
-
" - uses: oven-sh/setup-bun@v2",
|
|
183
|
-
" with:",
|
|
184
|
-
" bun-version: latest",
|
|
185
|
-
""
|
|
186
|
-
);
|
|
187
|
-
} else if (pm.setupAction === "pnpm") {
|
|
188
|
-
setupSteps.push(
|
|
189
|
-
" - uses: pnpm/action-setup@v6",
|
|
190
|
-
"",
|
|
191
|
-
" - uses: actions/setup-node@v6",
|
|
192
|
-
" with:",
|
|
193
|
-
" node-version: 22",
|
|
194
|
-
` cache: ${pm.cache}`,
|
|
195
|
-
""
|
|
196
|
-
);
|
|
197
|
-
} else {
|
|
198
|
-
setupSteps.push(
|
|
199
|
-
" - uses: actions/setup-node@v6",
|
|
200
|
-
" with:",
|
|
201
|
-
" node-version: 22",
|
|
202
|
-
` cache: ${pm.cache}`,
|
|
203
|
-
""
|
|
204
|
-
);
|
|
205
|
-
}
|
|
206
|
-
return [
|
|
207
|
-
`name: Deploy to GitHub Pages`,
|
|
208
|
-
"",
|
|
209
|
-
"on:",
|
|
210
|
-
" push:",
|
|
211
|
-
" branches: [main]",
|
|
212
|
-
" workflow_dispatch:",
|
|
213
|
-
"",
|
|
214
|
-
"permissions:",
|
|
215
|
-
" contents: read",
|
|
216
|
-
" pages: write",
|
|
217
|
-
" id-token: write",
|
|
218
|
-
"",
|
|
219
|
-
"concurrency:",
|
|
220
|
-
' group: "pages"',
|
|
221
|
-
" cancel-in-progress: false",
|
|
222
|
-
"",
|
|
223
|
-
"jobs:",
|
|
224
|
-
" build:",
|
|
225
|
-
" runs-on: ubuntu-latest",
|
|
226
|
-
" steps:",
|
|
227
|
-
...setupSteps,
|
|
228
|
-
` - run: ${pm.installCmd}`,
|
|
229
|
-
"",
|
|
230
|
-
` - run: ${pm.runCmd} run build`,
|
|
231
|
-
"",
|
|
232
|
-
" - name: Add .nojekyll",
|
|
233
|
-
" run: touch .docu/dist/.nojekyll",
|
|
234
|
-
"",
|
|
235
|
-
" - uses: actions/upload-pages-artifact@v3",
|
|
236
|
-
" with:",
|
|
237
|
-
" path: .docu/dist",
|
|
238
|
-
"",
|
|
239
|
-
" deploy:",
|
|
240
|
-
" environment:",
|
|
241
|
-
" name: github-pages",
|
|
242
|
-
" url: ${{ steps.deployment.outputs.page_url }}",
|
|
243
|
-
" runs-on: ubuntu-latest",
|
|
244
|
-
" needs: build",
|
|
245
|
-
" steps:",
|
|
246
|
-
" - id: deployment",
|
|
247
|
-
" uses: actions/deploy-pages@v4"
|
|
248
|
-
].join("\n");
|
|
249
|
-
}
|
|
250
|
-
function generateDockerWorkflowYml() {
|
|
251
|
-
const imageName = "ghcr.io/${{ github.repository }}";
|
|
252
|
-
return [
|
|
253
|
-
`name: Build & Push Docker Image`,
|
|
254
|
-
"",
|
|
255
|
-
"on:",
|
|
256
|
-
" push:",
|
|
257
|
-
" branches: [main]",
|
|
258
|
-
" workflow_dispatch:",
|
|
259
|
-
"",
|
|
260
|
-
"permissions:",
|
|
261
|
-
" contents: read",
|
|
262
|
-
" packages: write",
|
|
263
|
-
"",
|
|
264
|
-
"jobs:",
|
|
265
|
-
" build:",
|
|
266
|
-
" runs-on: ubuntu-latest",
|
|
267
|
-
" steps:",
|
|
268
|
-
" - uses: actions/checkout@v4",
|
|
269
|
-
" with:",
|
|
270
|
-
" fetch-depth: 0",
|
|
271
|
-
"",
|
|
272
|
-
" - name: Log in to GHCR",
|
|
273
|
-
" uses: docker/login-action@v3",
|
|
274
|
-
" with:",
|
|
275
|
-
" registry: ghcr.io",
|
|
276
|
-
" username: ${{ github.actor }}",
|
|
277
|
-
" password: ${{ secrets.GITHUB_TOKEN }}",
|
|
278
|
-
"",
|
|
279
|
-
" - name: Build & push",
|
|
280
|
-
" uses: docker/build-push-action@v5",
|
|
281
|
-
" with:",
|
|
282
|
-
" context: .",
|
|
283
|
-
` tags: ${imageName}:latest`,
|
|
284
|
-
" push: true"
|
|
285
|
-
].join("\n");
|
|
286
|
-
}
|
|
287
|
-
async function writeGhaWorkflow() {
|
|
288
|
-
if (!existsSync(WORKFLOW_FILE)) {
|
|
289
|
-
await mkdir(WORKFLOW_DIR, { recursive: true });
|
|
290
|
-
await writeFile(WORKFLOW_FILE, generateWorkflowYml());
|
|
291
|
-
log.created("\u{1F4C4} Created .github/workflows/deploy.yml");
|
|
292
|
-
}
|
|
293
|
-
}
|
|
294
|
-
var DOCKER_WORKFLOW_FILE = join(WORKFLOW_DIR, "deploy-docker.yml");
|
|
295
|
-
async function writeDockerWorkflow() {
|
|
296
|
-
if (!existsSync(DOCKER_WORKFLOW_FILE)) {
|
|
297
|
-
await mkdir(WORKFLOW_DIR, { recursive: true });
|
|
298
|
-
await writeFile(DOCKER_WORKFLOW_FILE, generateDockerWorkflowYml());
|
|
299
|
-
log.created("\u{1F4C4} Created .github/workflows/deploy-docker.yml");
|
|
300
|
-
}
|
|
301
|
-
}
|
|
302
|
-
async function runDeploy() {
|
|
303
|
-
log.info("\u{1F4E6} Building for production...\n");
|
|
304
|
-
await runBuild();
|
|
305
|
-
await writeFile(join(DIST_DIR, ".nojekyll"), "");
|
|
306
|
-
await writeFile(join(DIST_DIR, "_headers"), HEADERS_FILE);
|
|
307
|
-
if (isDocker) {
|
|
308
|
-
await writeDockerFiles();
|
|
309
|
-
if (isCi) await writeDockerWorkflow();
|
|
310
|
-
} else {
|
|
311
|
-
await writeGhaWorkflow();
|
|
312
|
-
}
|
|
313
|
-
log.ok();
|
|
314
|
-
log.out(" Output: .docu/dist/");
|
|
315
|
-
if (isDocker) {
|
|
316
|
-
log.out(" Build locally: docker build -t my-docs . && docker run -p 80:80 my-docs");
|
|
317
|
-
if (isCi) {
|
|
318
|
-
log.out(" Push to GitHub \u2014 CI will build & push Docker image to GHCR");
|
|
319
|
-
log.out(" Then pull latest image on your hosting platform (Coolify, etc.)");
|
|
320
|
-
} else {
|
|
321
|
-
log.out(" For Coolify: connect repo, set build pack to Dockerfile");
|
|
322
|
-
}
|
|
323
|
-
} else {
|
|
324
|
-
log.out(" Push to GitHub and enable Pages (Settings \u2192 Pages \u2192 Source: GitHub Actions)");
|
|
325
|
-
}
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
export {
|
|
329
|
-
runDeploy
|
|
330
|
-
};
|
|
@@ -1,114 +0,0 @@
|
|
|
1
|
-
// .docu/node/runtime/deno.ts
|
|
2
|
-
var denoAdapter = {
|
|
3
|
-
name: "deno",
|
|
4
|
-
serve(fetch, options) {
|
|
5
|
-
const server = Deno.serve(
|
|
6
|
-
{
|
|
7
|
-
port: options.port,
|
|
8
|
-
hostname: options.hostname,
|
|
9
|
-
onListen: () => {
|
|
10
|
-
}
|
|
11
|
-
},
|
|
12
|
-
fetch
|
|
13
|
-
);
|
|
14
|
-
return {
|
|
15
|
-
port: server.addr.port,
|
|
16
|
-
hostname: server.addr.hostname,
|
|
17
|
-
stop: () => server.shutdown()
|
|
18
|
-
};
|
|
19
|
-
}
|
|
20
|
-
};
|
|
21
|
-
|
|
22
|
-
// .docu/node/runtime/node.ts
|
|
23
|
-
import { createServer } from "node:http";
|
|
24
|
-
function toWebRequest(req, port, hostname) {
|
|
25
|
-
const host = req.headers.host ?? `${hostname}:${port}`;
|
|
26
|
-
const url = `http://${host}${req.url ?? "/"}`;
|
|
27
|
-
const headers = new Headers();
|
|
28
|
-
for (const [key, value] of Object.entries(req.headers)) {
|
|
29
|
-
if (value === void 0) continue;
|
|
30
|
-
if (Array.isArray(value)) {
|
|
31
|
-
for (const v of value) headers.append(key, v);
|
|
32
|
-
} else {
|
|
33
|
-
headers.set(key, value);
|
|
34
|
-
}
|
|
35
|
-
}
|
|
36
|
-
const method = req.method ?? "GET";
|
|
37
|
-
const hasBody = method !== "GET" && method !== "HEAD";
|
|
38
|
-
return new Request(url, {
|
|
39
|
-
method,
|
|
40
|
-
headers,
|
|
41
|
-
// IncomingMessage is an async iterable of Buffer chunks; Request accepts
|
|
42
|
-
// an async iterable body when half-duplex is declared.
|
|
43
|
-
body: hasBody ? req : void 0,
|
|
44
|
-
// @ts-expect-error -- required by undici for streaming request bodies
|
|
45
|
-
duplex: hasBody ? "half" : void 0
|
|
46
|
-
});
|
|
47
|
-
}
|
|
48
|
-
async function writeResponse(response, res) {
|
|
49
|
-
const headers = {};
|
|
50
|
-
const setCookie = response.headers.getSetCookie?.() ?? [];
|
|
51
|
-
response.headers.forEach((value, key) => {
|
|
52
|
-
if (key === "set-cookie") return;
|
|
53
|
-
headers[key] = value;
|
|
54
|
-
});
|
|
55
|
-
if (setCookie.length > 0) headers["set-cookie"] = setCookie;
|
|
56
|
-
res.writeHead(response.status, headers);
|
|
57
|
-
if (!response.body) {
|
|
58
|
-
res.end();
|
|
59
|
-
return;
|
|
60
|
-
}
|
|
61
|
-
const reader = response.body.getReader();
|
|
62
|
-
try {
|
|
63
|
-
for (; ; ) {
|
|
64
|
-
const { done, value } = await reader.read();
|
|
65
|
-
if (done) break;
|
|
66
|
-
const ok = res.write(value);
|
|
67
|
-
if (!ok) await new Promise((resolve) => res.once("drain", resolve));
|
|
68
|
-
}
|
|
69
|
-
res.end();
|
|
70
|
-
} catch {
|
|
71
|
-
await reader.cancel().catch(() => {
|
|
72
|
-
});
|
|
73
|
-
res.destroy();
|
|
74
|
-
}
|
|
75
|
-
}
|
|
76
|
-
var nodeAdapter = {
|
|
77
|
-
name: "node",
|
|
78
|
-
serve(fetch, options) {
|
|
79
|
-
const hostname = options.hostname ?? "localhost";
|
|
80
|
-
const server = createServer((req, res) => {
|
|
81
|
-
Promise.resolve().then(() => fetch(toWebRequest(req, options.port, hostname))).then((response) => writeResponse(response, res)).catch((err) => {
|
|
82
|
-
console.error(err);
|
|
83
|
-
if (!res.headersSent) {
|
|
84
|
-
res.writeHead(500, { "Content-Type": "text/plain" });
|
|
85
|
-
}
|
|
86
|
-
res.end("Internal Server Error");
|
|
87
|
-
});
|
|
88
|
-
});
|
|
89
|
-
if (options.idleTimeout !== void 0) {
|
|
90
|
-
server.timeout = options.idleTimeout * 1e3;
|
|
91
|
-
server.keepAliveTimeout = options.idleTimeout * 1e3;
|
|
92
|
-
}
|
|
93
|
-
return new Promise((resolve, reject) => {
|
|
94
|
-
server.once("error", reject);
|
|
95
|
-
server.listen(options.port, () => {
|
|
96
|
-
const address = server.address();
|
|
97
|
-
const port = typeof address === "object" && address ? address.port : options.port;
|
|
98
|
-
resolve({
|
|
99
|
-
port,
|
|
100
|
-
hostname,
|
|
101
|
-
stop: () => new Promise((res2, rej2) => {
|
|
102
|
-
server.closeAllConnections?.();
|
|
103
|
-
server.close((err) => err ? rej2(err) : res2());
|
|
104
|
-
})
|
|
105
|
-
});
|
|
106
|
-
});
|
|
107
|
-
});
|
|
108
|
-
}
|
|
109
|
-
};
|
|
110
|
-
|
|
111
|
-
export {
|
|
112
|
-
denoAdapter,
|
|
113
|
-
nodeAdapter
|
|
114
|
-
};
|