-
Notifications
You must be signed in to change notification settings - Fork 2.8k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
test(undici): rm external http reqs from tests (#2459)
* test(undici): rm external http reqs from tests * cleanup(http-test-server): remove finished TODOs * test(undici): fix server type, remove type:module to fix typings in test dir * test(undici): make the typings better * test(undici): fix typo
- Loading branch information
1 parent
5fd406c
commit 732c5e7
Showing
3 changed files
with
208 additions
and
22 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,168 @@ | ||
import { serve } from "bun"; | ||
|
||
// This is obviously incomplete but these are probably the most common status codes + the ones we need for testing | ||
type ValidStatusCode = 200 | 201 | 400 | 404 | 405 | 500; | ||
|
||
const defaultOpts = { | ||
type: "json", | ||
headers: { | ||
"Content-Type": "application/json", | ||
}, | ||
status: 200, | ||
}; | ||
|
||
const defaultResponseBodies = { | ||
200: "OK", | ||
201: "Created", | ||
400: "Bad Request", | ||
404: "Not Found", | ||
405: "Method Not Allowed", | ||
500: "Internal Server Error", | ||
} as Record<ValidStatusCode, string>; | ||
|
||
function getDefaultJSONBody(request: Request) { | ||
return { | ||
url: request.url, | ||
method: request.method, | ||
}; | ||
} | ||
|
||
function makeTestJsonResponse( | ||
request: Request, | ||
opts: ResponseInit & { type?: "plaintext" | "json" } = { status: 200, type: "json" }, | ||
body?: { [k: string | number]: any } | string, | ||
): Response { | ||
const defaultJSONBody = getDefaultJSONBody(request); | ||
|
||
let type = opts.type || "json"; | ||
let resBody; | ||
let headers; | ||
|
||
// Setup headers | ||
|
||
if (!opts.headers) headers = new Headers(); | ||
|
||
if (!(opts.headers instanceof Headers)) headers = new Headers(opts.headers); | ||
else headers = opts.headers; | ||
|
||
switch (type) { | ||
case "json": | ||
if (typeof body === "object" && body !== null) { | ||
resBody = JSON.stringify({ ...defaultJSONBody, ...body }) as string; | ||
} else if (typeof body === "string") { | ||
resBody = JSON.stringify({ ...defaultJSONBody, data: body }) as string; | ||
} else { | ||
resBody = JSON.stringify(defaultJSONBody) as string; | ||
} | ||
// Check to set headers | ||
headers.set("Content-Type", "application/json"); | ||
break; | ||
case "plaintext": | ||
if (typeof body === "object") { | ||
if (body === null) { | ||
resBody = ""; | ||
} else { | ||
resBody = JSON.stringify(body); | ||
} | ||
} | ||
// Check to set headers | ||
headers.set("Content-Type", "text/plain"); | ||
default: | ||
} | ||
|
||
return new Response(resBody as string, { | ||
...defaultOpts, | ||
...opts, | ||
headers: { ...defaultOpts.headers, ...headers }, | ||
}); | ||
} | ||
|
||
export function createServer() { | ||
const server = serve({ | ||
port: 0, | ||
fetch: async req => { | ||
const { pathname, search } = new URL(req.url); | ||
const lowerPath = pathname.toLowerCase(); | ||
|
||
let response: Response; | ||
switch (lowerPath.match(/\/\w+/)?.[0] || "") { | ||
// START HTTP METHOD ROUTES | ||
case "/get": | ||
if (req.method.toUpperCase() !== "GET") { | ||
response = makeTestJsonResponse(req, { status: 405 }); | ||
break; | ||
} | ||
if (search !== "") { | ||
const params = new URLSearchParams(search); | ||
const args = {} as Record<string, string | number>; | ||
params.forEach((v, k) => { | ||
if (!isNaN(parseInt(v))) { | ||
args[k] = parseInt(v); | ||
} else { | ||
args[k] = v; | ||
} | ||
}); | ||
response = makeTestJsonResponse(req, { status: 200 }, { args }); | ||
break; | ||
} | ||
// Normal case | ||
response = makeTestJsonResponse(req); | ||
break; | ||
case "/post": | ||
if (req.method.toUpperCase() !== "POST") { | ||
response = makeTestJsonResponse(req, { status: 405 }); | ||
break; | ||
} | ||
response = makeTestJsonResponse(req, { status: 201, type: "json" }, await req.text()); | ||
break; | ||
case "/head": | ||
if (req.method.toUpperCase() !== "HEAD") { | ||
response = makeTestJsonResponse(req, { status: 405 }); | ||
break; | ||
} | ||
response = makeTestJsonResponse(req, { status: 200 }); | ||
break; | ||
|
||
// END HTTP METHOD ROUTES | ||
|
||
case "/status": | ||
// Parse the status from URL path params: /status/200 | ||
const rawStatus = lowerPath.split("/").filter(Boolean)[1]; | ||
if (rawStatus) { | ||
const status = parseInt(rawStatus); | ||
if (!isNaN(status) && status > 100 && status < 599) { | ||
response = makeTestJsonResponse( | ||
req, | ||
{ status }, | ||
{ data: defaultResponseBodies[(status || 200) as ValidStatusCode] }, | ||
); | ||
break; | ||
} | ||
} | ||
response = makeTestJsonResponse(req, { status: 400 }, { data: "Invalid status" }); | ||
break; | ||
case "/delay": | ||
const rawDelay = lowerPath.split("/").filter(Boolean)[1]; | ||
if (rawDelay) { | ||
const delay = parseInt(rawDelay); | ||
if (!isNaN(delay) && delay >= 0) { | ||
await Bun.sleep(delay * 1000); | ||
response = makeTestJsonResponse(req, { status: 200 }, { data: "Delayed" }); | ||
break; | ||
} | ||
} | ||
response = makeTestJsonResponse(req, { status: 400 }, { data: "Invalid delay" }); | ||
break; | ||
case "/headers": | ||
response = makeTestJsonResponse(req, { status: 200 }, { headers: req.headers }); | ||
break; | ||
default: | ||
response = makeTestJsonResponse(req, { status: 404 }); | ||
} | ||
|
||
return response; | ||
}, | ||
}); | ||
const { port, stop } = server; | ||
return { server, port, stop }; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,5 @@ | ||
{ | ||
"name": "test", | ||
"type": "module", | ||
"devDependencies": {}, | ||
"dependencies": { | ||
"@swc/core": "^1.3.38", | ||
|