fix: Added a content-type parser to HeaderUtil

* fixes #995

* fixed the remarks and added a test for parseContentType

* refactor: remove unnecessary comment

Co-authored-by: woutslabbinck <wout.slabbinck@ugent.com>
This commit is contained in:
Wout Slabbinck 2021-10-15 13:05:26 +02:00 committed by Joachim Van Herwegen
parent 2a48b1f333
commit 54ccbed48d
4 changed files with 30 additions and 3 deletions

View File

@ -1,4 +1,5 @@
import type { HttpRequest } from '../../../server/HttpRequest';
import { parseContentType } from '../../../util/HeaderUtil';
import type { RepresentationMetadata } from '../../representation/RepresentationMetadata';
import { MetadataParser } from './MetadataParser';
@ -10,8 +11,7 @@ export class ContentTypeParser extends MetadataParser {
public async handle(input: { request: HttpRequest; metadata: RepresentationMetadata }): Promise<void> {
const contentType = input.request.headers['content-type'];
if (contentType) {
// Will need to use HeaderUtil once parameters need to be parsed
input.metadata.contentType = /^[^;]*/u.exec(contentType)![0].trim();
input.metadata.contentType = parseContentType(contentType).type;
}
}
}

View File

@ -6,6 +6,7 @@ import { getLoggerFor } from '../logging/LogUtil';
import type { RepresentationConverter } from '../storage/conversion/RepresentationConverter';
import { INTERNAL_QUADS } from './ContentTypes';
import { BadRequestHttpError } from './errors/BadRequestHttpError';
import { parseContentType } from './HeaderUtil';
const logger = getLoggerFor('FetchUtil');
@ -46,9 +47,10 @@ Promise<Representation> {
logger.warn(`Missing content-type header from ${response.url}`);
throw error;
}
const contentTypeValue = parseContentType(contentType).type;
// Try to convert to quads
const representation = new BasicRepresentation(body, contentType);
const representation = new BasicRepresentation(body, contentTypeValue);
const preferences = { type: { [INTERNAL_QUADS]: 1 }};
return converter.handleSafe({ representation, identifier: { path: response.url }, preferences });
}

View File

@ -415,6 +415,18 @@ export function addHeader(response: HttpResponse, name: string, value: string |
response.setHeader(name, allValues.length === 1 ? allValues[0] : allValues);
}
/**
* Parses the Content-Type header.
*
* @param contentType - The media type of the content-type header
*
* @returns The parsed media type of the content-type
*/
export function parseContentType(contentType: string): { type: string } {
const contentTypeValue = /^\s*([^;\s]*)/u.exec(contentType)![1];
return { type: contentTypeValue };
}
/**
* The Forwarded header from RFC7239
*/

View File

@ -6,6 +6,7 @@ import {
parseAcceptDateTime,
parseAcceptEncoding,
parseAcceptLanguage,
parseContentType,
parseForwarded,
} from '../../../src/util/HeaderUtil';
@ -187,6 +188,18 @@ describe('HeaderUtil', (): void => {
});
});
describe('#parseContentType', (): void => {
const contentTypeTurtle = 'text/turtle';
it('handles single content-type parameter (with leading and trailing whitespaces).', (): void => {
expect(parseContentType('text/turtle').type).toEqual(contentTypeTurtle);
expect(parseContentType('text/turtle ').type).toEqual(contentTypeTurtle);
expect(parseContentType(' text/turtle').type).toEqual(contentTypeTurtle);
});
it('handles multiple content-type parameters.', (): void => {
expect(parseContentType('text/turtle; charset=UTF-8').type).toEqual(contentTypeTurtle);
});
});
describe('#parseForwarded', (): void => {
it('handles an empty set of headers.', (): void => {
expect(parseForwarded({})).toEqual({});