wip fix
This commit is contained in:
+38
-8
@@ -1,4 +1,4 @@
|
||||
import { g } from "../utils/global";
|
||||
import { gzipSync } from "bun";
|
||||
|
||||
const parseQueryParams = (ctx: any) => {
|
||||
const pageHref = ctx.req.url;
|
||||
@@ -19,8 +19,8 @@ export const apiContext = (ctx: any) => {
|
||||
req: ctx.req as Request & { params: any; query_parameters: any },
|
||||
res: {
|
||||
...ctx.res,
|
||||
send: (body) => {
|
||||
ctx.res = createResponse(ctx.res, body);
|
||||
send: (body, cache_accept?: string) => {
|
||||
ctx.res = createResponse(ctx.res, body, cache_accept);
|
||||
},
|
||||
sendStatus: (code: number) => {
|
||||
ctx.res._status = code;
|
||||
@@ -29,19 +29,38 @@ export const apiContext = (ctx: any) => {
|
||||
ctx.res.headers.append(key, value);
|
||||
},
|
||||
} as Response & {
|
||||
send: (body?: string | object) => void;
|
||||
send: (body?: string | object, cache_accept?: string) => void;
|
||||
setHeader: (key: string, value: string) => void;
|
||||
sendStatus: (code: number) => void;
|
||||
},
|
||||
};
|
||||
};
|
||||
|
||||
export const createResponse = (existingRes: any, body: any) => {
|
||||
const cache = { gz: {} as Record<string, Uint8Array> };
|
||||
|
||||
export const createResponse = (
|
||||
existingRes: any,
|
||||
body: any,
|
||||
cache_accept?: string
|
||||
) => {
|
||||
const status =
|
||||
typeof existingRes._status === "number" ? existingRes._status : undefined;
|
||||
|
||||
let content: any = typeof body === "string" ? body : JSON.stringify(body);
|
||||
const headers = {} as Record<string, string>;
|
||||
if (cache_accept && cache_accept.toLowerCase().includes("gz")) {
|
||||
const content_hash = simpleHash(content);
|
||||
if (content_hash) {
|
||||
content = cache.gz[content_hash];
|
||||
} else {
|
||||
cache.gz[content_hash] = gzipSync(content);
|
||||
content = cache.gz[content_hash];
|
||||
}
|
||||
headers["content-encoding"] = "gz";
|
||||
}
|
||||
|
||||
let res = new Response(
|
||||
typeof body === "string" ? body : JSON.stringify(body),
|
||||
content,
|
||||
status
|
||||
? {
|
||||
status,
|
||||
@@ -52,11 +71,22 @@ export const createResponse = (existingRes: any, body: any) => {
|
||||
if (typeof body === "object") {
|
||||
res.headers.append("content-type", "application/json");
|
||||
}
|
||||
for (const [k, v] of Object.entries(headers)) {
|
||||
res.headers.append(k, v);
|
||||
}
|
||||
|
||||
const cur = existingRes as Response;
|
||||
for (const [key, value] of cur.headers.entries()) {
|
||||
cur.headers.forEach((value, key) => {
|
||||
res.headers.append(key, value);
|
||||
}
|
||||
});
|
||||
|
||||
return res;
|
||||
};
|
||||
|
||||
function simpleHash(str: string) {
|
||||
let hash = 0;
|
||||
for (let i = 0; i < str.length; i++) {
|
||||
hash = ((hash << 5) - hash + str.charCodeAt(i)) | 0;
|
||||
}
|
||||
return (hash >>> 0).toString(36);
|
||||
}
|
||||
|
||||
+9
-46
@@ -60,56 +60,19 @@ export const createServer = async () => {
|
||||
async fetch(req) {
|
||||
const url = new URL(req.url);
|
||||
|
||||
const web = await serveWeb(url, req);
|
||||
let index = ["", ""];
|
||||
if (web) {
|
||||
if (Array.isArray(web)) index = web;
|
||||
else {
|
||||
return web;
|
||||
}
|
||||
}
|
||||
|
||||
const api = await serveAPI(url, req);
|
||||
if (api) {
|
||||
return api;
|
||||
}
|
||||
|
||||
if (index) {
|
||||
let status: any = {};
|
||||
|
||||
if (!["", "index.html"].includes(trim(url.pathname, " /"))) {
|
||||
status = {
|
||||
status: 404,
|
||||
statusText: "Not Found",
|
||||
};
|
||||
const handle = async (req: Request) => {
|
||||
const api = await serveAPI(url, req);
|
||||
if (api) {
|
||||
return api;
|
||||
}
|
||||
|
||||
const [site_id, body] = index;
|
||||
if (g.web[site_id]) {
|
||||
const router = g.web[site_id].router;
|
||||
if (router) {
|
||||
let found = router.lookup(url.pathname);
|
||||
if (!found) {
|
||||
found = router.lookup(url.pathname + "/");
|
||||
}
|
||||
if (found) {
|
||||
status = {};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return new Response(body, {
|
||||
...status,
|
||||
headers: {
|
||||
"content-type": "text/html",
|
||||
},
|
||||
return new Response(`404 Not Found`, {
|
||||
status: 404,
|
||||
statusText: "Not Found",
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
return new Response(`404 Not Found`, {
|
||||
status: 404,
|
||||
statusText: "Not Found",
|
||||
});
|
||||
return handle(req);
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
+2
-35
@@ -8,15 +8,12 @@ import {
|
||||
removeAsync,
|
||||
writeAsync,
|
||||
} from "fs-jetpack";
|
||||
import { createRouter } from "radix3";
|
||||
import { gunzipSync } from "zlib";
|
||||
import { downloadFile } from "../api/_deploy";
|
||||
import { dir } from "../utils/dir";
|
||||
import { g } from "../utils/global";
|
||||
|
||||
export const loadWeb = async () => {
|
||||
g.web = {};
|
||||
|
||||
await dirAsync(dir(`app/static`));
|
||||
const siteZip = `${
|
||||
g.mode === "dev" ? "http://localhost:4550" : "https://prasi.app"
|
||||
@@ -53,39 +50,14 @@ export const loadWeb = async () => {
|
||||
if (!deploy) {
|
||||
await dirAsync(dir(`app/web/${web.name}/deploys`));
|
||||
}
|
||||
|
||||
g.web[web.name] = {
|
||||
current: parseInt(
|
||||
(await readAsync(dir(`app/web/${web.name}/current`))) || "0"
|
||||
),
|
||||
deploys: deploy ? deploy.children.map((e) => parseInt(e.name)) : [],
|
||||
domains:
|
||||
(await readAsync(dir(`app/web/${web.name}/domains.json`), "json")) ||
|
||||
[],
|
||||
site_id: web.name,
|
||||
deploying: null,
|
||||
cacheKey: 0,
|
||||
router: null,
|
||||
cache: null,
|
||||
};
|
||||
|
||||
const cur = g.web[web.name];
|
||||
|
||||
if (!cur.deploys.includes(cur.current)) {
|
||||
cur.current = 0;
|
||||
}
|
||||
|
||||
if (cur.current) {
|
||||
await loadWebCache(cur.site_id, cur.current);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const decoder = new TextDecoder();
|
||||
export const loadWebCache = async (site_id: string, ts: number | string) => {
|
||||
const web = g.web[site_id];
|
||||
const web = g.web;
|
||||
if (web) {
|
||||
const path = dir(`app/web/${site_id}/deploys/${ts}`);
|
||||
const path = dir(`app/web/deploys/${ts}`);
|
||||
if (await existsAsync(path)) {
|
||||
const fileContent = await readAsync(path, "buffer");
|
||||
if (fileContent) {
|
||||
@@ -94,11 +66,6 @@ export const loadWebCache = async (site_id: string, ts: number | string) => {
|
||||
);
|
||||
|
||||
const res = gunzipSync(fileContent);
|
||||
web.cache = JSON.parse(decoder.decode(res));
|
||||
web.router = createRouter();
|
||||
for (const p of web.cache?.pages || []) {
|
||||
web.router.insert(p.url, p);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
import { statSync } from "fs";
|
||||
import { join } from "path";
|
||||
import { g } from "../utils/global";
|
||||
import { dir } from "utils/dir";
|
||||
|
||||
const index = {
|
||||
@@ -13,28 +12,13 @@ const index = {
|
||||
};
|
||||
|
||||
export const serveWeb = async (url: URL, req: Request) => {
|
||||
const domain = url.hostname;
|
||||
let site_id = "";
|
||||
if (!g.domains) {
|
||||
g.domains = {};
|
||||
for (const web of Object.values(g.web)) {
|
||||
for (const d of web.domains) {
|
||||
const durl = new URL(d);
|
||||
g.domains[durl.hostname] = web.site_id;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (typeof g.domains[domain] === "undefined") {
|
||||
g.domains[domain] = "";
|
||||
}
|
||||
site_id = g.domains[domain];
|
||||
|
||||
if (!site_id) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const base = dir(`app/static/site`);
|
||||
// const base = `/Users/r/Developer/prasi/.output/app/srv/site`;
|
||||
|
||||
let path = join(base, url.pathname);
|
||||
|
||||
@@ -73,7 +57,7 @@ export const serveWeb = async (url: URL, req: Request) => {
|
||||
index.html = generateIndexHtml("", site_id);
|
||||
}
|
||||
|
||||
return [site_id, index.html];
|
||||
return { site_id, index: index.html };
|
||||
};
|
||||
|
||||
export const generateIndexHtml = (base_url: string, site_id: string) => {
|
||||
@@ -95,10 +79,6 @@ export const generateIndexHtml = (base_url: string, site_id: string) => {
|
||||
<div id="root"></div>
|
||||
<script src="${base}/site.js" type="module"></script>
|
||||
<script>window.id_site = "${site_id}";</script>
|
||||
<script
|
||||
src="https://js.sentry-cdn.com/a2dfb8b1128f4018b83bdc9c08d18da2.min.js"
|
||||
crossorigin="anonymous"
|
||||
></script>
|
||||
</body>
|
||||
</html>`;
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user