release: WRNexusJS 0.5.10

This commit is contained in:
2026-07-30 13:36:29 +05:30
parent 8fc6f15402
commit d1b0c55b53
159 changed files with 7509 additions and 604 deletions
+40 -8
View File
@@ -10,7 +10,8 @@
*/
import { spawn, type ChildProcess } from "node:child_process";
import { join, resolve } from "node:path";
import { existsSync } from "node:fs";
import { dirname, join, resolve } from "node:path";
import { fileURLToPath } from "node:url";
import { RESTART_EXIT_CODE } from "./restart.ts";
@@ -150,11 +151,15 @@ export function stripInternalError(res: Response): Response {
}
/** Preserve an intentional verifier redirect while keeping other failures opaque. */
export function forwardAuthFailure(res: Response, verifierUrl: string): Response {
export function forwardAuthFailure(
res: Response,
verifierUrl: string,
verifierPublicOrigin = verifierUrl,
): Response {
const location = res.headers.get("location");
if (res.status >= 300 && res.status < 400 && location) {
try {
const redirect = new URL(location, verifierUrl);
const redirect = new URL(location, verifierPublicOrigin);
if (redirect.protocol === "http:" || redirect.protocol === "https:") {
return new Response(null, { status: res.status, headers: { location: redirect.href } });
}
@@ -197,6 +202,7 @@ async function checkAuth(
req: Request,
ip: string,
internalOrigins: Readonly<Record<string, string>>,
publicOrigins: Readonly<Record<string, string>>,
publicOrigin?: string,
): Promise<Response | null> {
if (!auth) return null;
@@ -226,6 +232,10 @@ async function checkAuth(
if (auth.forward) {
const verifyUrl = resolveForwardAuthUrl(auth.forward, internalOrigins);
const verifierPublicOrigin =
typeof auth.forward.app === "string"
? publicOrigins[auth.forward.app]
: new URL(auth.forward.url).origin;
try {
const res = await fetch(verifyUrl, {
@@ -240,7 +250,7 @@ async function checkAuth(
`[wrnexus] forward-auth verifier error: ${req.method} ${requestUrl.pathname} via ${verifyUrl} returned ${res.status}${diagnostic ? `${diagnostic}` : ""}`,
);
}
return forwardAuthFailure(res, verifyUrl);
return forwardAuthFailure(res, verifyUrl, verifierPublicOrigin);
}
} catch (error) {
console.error(
@@ -351,11 +361,21 @@ export async function startGateway(opts: GatewayOptions): Promise<RunningGateway
const hostname = opts.hostname ?? defaultGatewayHostname(mode);
const environment = opts.environment ?? (mode === "production" ? "production" : "development");
const workspaceOrigins = Object.fromEntries(
opts.apps.map((app) => [app.name, app.publicOrigin ?? `http://${app.domains[0]}:${port}`]),
const workspaceOrigins: Readonly<Record<string, string>> = Object.freeze(
Object.fromEntries(
opts.apps.map((app) => [app.name, app.publicOrigin ?? `http://${app.domains[0]}:${port}`]),
),
);
const displayHost = hostname === "0.0.0.0" || hostname === "::" ? "localhost" : hostname;
const serveEntry = fileURLToPath(import.meta.resolve("@wrnexus/dev-server/serve-entry"));
// When the CLI is executed directly from a framework checkout, keep child
// apps on that same source tree. Resolving the package name from an external
// workspace can otherwise select its older installed release on restart.
const sourceServeEntry = fileURLToPath(new URL("./serve-entry.ts", import.meta.url));
const usesSourceServeEntry = existsSync(sourceServeEntry);
const serveEntry = usesSourceServeEntry
? sourceServeEntry
: fileURLToPath(import.meta.resolve("@wrnexus/dev-server/serve-entry"));
const frameworkRoot = resolve(dirname(sourceServeEntry), "../../..");
let stopping = false;
const targets: Target[] = opts.apps.map((app, i) => {
@@ -397,6 +417,11 @@ export async function startGateway(opts: GatewayOptions): Promise<RunningGateway
],
{
stdio: "inherit",
// Bun can otherwise resolve bare @wrnexus imports against the
// external application's node_modules after an HMR restart.
// Keep source-checkout children anchored to the same framework
// checkout as the gateway command.
cwd: usesSourceServeEntry ? frameworkRoot : dir,
env: {
...process.env,
WRNEXUS_ENV: environment,
@@ -496,7 +521,14 @@ export async function startGateway(opts: GatewayOptions): Promise<RunningGateway
}
// Per-app access control (basic auth / IP allowlist / forward-auth).
const denied = await checkAuth(target.auth, req, ip, internalOrigins, target.publicOrigin);
const denied = await checkAuth(
target.auth,
req,
ip,
internalOrigins,
workspaceOrigins,
target.publicOrigin,
);
if (denied) {
if (sec.accessLog)
console.log(