mirror of
https://github.com/CommunitySolidServer/CommunitySolidServer.git
synced 2024-10-03 14:55:10 +00:00
feat: Parse Accept headers as early as possible
This commit is contained in:
@@ -3,12 +3,13 @@ import type { OperationMetadataCollector } from '../http/ldp/metadata/OperationM
|
||||
import type { ErrorHandler } from '../http/output/error/ErrorHandler';
|
||||
import type { ResponseDescription } from '../http/output/response/ResponseDescription';
|
||||
import type { ResponseWriter } from '../http/output/ResponseWriter';
|
||||
import type { RepresentationPreferences } from '../http/representation/RepresentationPreferences';
|
||||
import { getLoggerFor } from '../logging/LogUtil';
|
||||
import { assertError } from '../util/errors/ErrorUtil';
|
||||
import { HttpError } from '../util/errors/HttpError';
|
||||
import type { HttpHandlerInput } from './HttpHandler';
|
||||
import { HttpHandler } from './HttpHandler';
|
||||
import type { HttpRequest } from './HttpRequest';
|
||||
import type { HttpResponse } from './HttpResponse';
|
||||
import type { OperationHttpHandler } from './OperationHttpHandler';
|
||||
|
||||
export interface ParsingHttpHandlerArgs {
|
||||
@@ -35,9 +36,9 @@ export interface ParsingHttpHandlerArgs {
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses requests and sends the resulting Operation to wrapped operationHandler.
|
||||
* Errors are caught and handled by the Errorhandler.
|
||||
* In case the operationHandler returns a result it will be sent to the ResponseWriter.
|
||||
* Parses requests and sends the resulting {@link Operation} to the wrapped {@link OperationHttpHandler}.
|
||||
* Errors are caught and handled by the {@link ErrorHandler}.
|
||||
* In case the {@link OperationHttpHandler} returns a result it will be sent to the {@link ResponseWriter}.
|
||||
*/
|
||||
export class ParsingHttpHandler extends HttpHandler {
|
||||
private readonly logger = getLoggerFor(this);
|
||||
@@ -58,30 +59,45 @@ export class ParsingHttpHandler extends HttpHandler {
|
||||
}
|
||||
|
||||
public async handle({ request, response }: HttpHandlerInput): Promise<void> {
|
||||
let result: ResponseDescription | undefined;
|
||||
let preferences: RepresentationPreferences = { type: { 'text/plain': 1 }};
|
||||
let result: ResponseDescription;
|
||||
|
||||
try {
|
||||
const operation = await this.requestParser.handleSafe(request);
|
||||
({ preferences } = operation);
|
||||
result = await this.operationHandler.handleSafe({ operation, request, response });
|
||||
|
||||
if (result?.metadata) {
|
||||
await this.metadataCollector.handleSafe({ operation, metadata: result.metadata });
|
||||
}
|
||||
|
||||
this.logger.verbose(`Parsed ${operation.method} operation on ${operation.target.path}`);
|
||||
result = await this.handleRequest(request, response);
|
||||
} catch (error: unknown) {
|
||||
assertError(error);
|
||||
result = await this.errorHandler.handleSafe({ error, preferences });
|
||||
if (HttpError.isInstance(error) && result.metadata) {
|
||||
const quads = error.generateMetadata(result.metadata.identifier);
|
||||
result.metadata.addQuads(quads);
|
||||
}
|
||||
result = await this.handleError(error, request);
|
||||
}
|
||||
|
||||
if (result) {
|
||||
await this.responseWriter.handleSafe({ response, result });
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Interprets the request and passes the generated Operation object to the stored OperationHttpHandler.
|
||||
*/
|
||||
protected async handleRequest(request: HttpRequest, response: HttpResponse):
|
||||
Promise<ResponseDescription> {
|
||||
const operation = await this.requestParser.handleSafe(request);
|
||||
const result = await this.operationHandler.handleSafe({ operation, request, response });
|
||||
|
||||
if (result?.metadata) {
|
||||
await this.metadataCollector.handleSafe({ operation, metadata: result.metadata });
|
||||
}
|
||||
|
||||
this.logger.verbose(`Parsed ${operation.method} operation on ${operation.target.path}`);
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles the error output correctly based on the preferences.
|
||||
*/
|
||||
protected async handleError(error: unknown, request: HttpRequest): Promise<ResponseDescription> {
|
||||
assertError(error);
|
||||
const result = await this.errorHandler.handleSafe({ error, request });
|
||||
if (HttpError.isInstance(error) && result.metadata) {
|
||||
const quads = error.generateMetadata(result.metadata.identifier);
|
||||
result.metadata.addQuads(quads);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user