Use standard error types in middleware

This commit is contained in:
Justin Spahr-Summers 2025-02-18 14:18:13 +00:00
commit 57fe3b3fb0
No known key found for this signature in database
2 changed files with 29 additions and 33 deletions

View file

@ -1,4 +1,5 @@
import { RequestHandler } from "express";
import { MethodNotAllowedError } from "../errors.js";
/**
* Middleware to handle unsupported HTTP methods with a 405 Method Not Allowed response.
@ -13,11 +14,9 @@ export function allowedMethods(allowedMethods: string[]): RequestHandler {
return;
}
const error = new MethodNotAllowedError(`The method ${req.method} is not allowed for this endpoint`);
res.status(405)
.set('Allow', allowedMethods.join(', '))
.json({
error: "method_not_allowed",
error_description: `The method ${req.method} is not allowed for this endpoint`
});
.json(error.toResponseObject());
};
}

View file

@ -2,6 +2,7 @@ import { z } from "zod";
import { RequestHandler } from "express";
import { OAuthRegisteredClientsStore } from "../clients.js";
import { OAuthClientInformationFull } from "../../../shared/auth.js";
import { InvalidRequestError, InvalidClientError } from "../errors.js";
export type ClientAuthenticationMiddlewareOptions = {
/**
@ -26,38 +27,34 @@ declare module "express-serve-static-core" {
export function authenticateClient({ clientsStore }: ClientAuthenticationMiddlewareOptions): RequestHandler {
return async (req, res, next) => {
let client_id, client_secret;
try {
const result = ClientAuthenticatedRequestSchema.parse(req.body);
client_id = result.client_id;
client_secret = result.client_secret;
let client_id, client_secret;
try {
const result = ClientAuthenticatedRequestSchema.parse(req.body);
client_id = result.client_id;
client_secret = result.client_secret;
} catch (error) {
throw new InvalidRequestError(String(error));
}
const client = await clientsStore.getClient(client_id);
if (!client) {
throw new InvalidClientError("Invalid client_id");
}
if (client.client_secret !== client_secret) {
throw new InvalidClientError("Invalid client_secret");
}
req.client = client;
next();
} catch (error) {
res.status(400).json({
error: "invalid_request",
error_description: String(error),
});
return;
if (error instanceof InvalidRequestError || error instanceof InvalidClientError) {
res.status(400).json(error.toResponseObject());
} else {
console.error("Unexpected error authenticating client:", error);
res.status(500).end("Internal Server Error");
}
}
const client = await clientsStore.getClient(client_id);
if (!client) {
// TODO: Return 401 with WWW-Authenticate if Authorization header was used
res.status(400).json({
error: "invalid_client",
error_description: "Invalid client_id",
});
return;
}
if (client.client_secret !== client_secret) {
res.status(400).json({
error: "invalid_client",
error_description: "Invalid client_secret",
});
return;
}
req.client = client;
next();
}
}