@tsed/platform-response-filter 7.0.0-beta.8 → 7.0.0-rc.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/coverage.json +6 -0
- package/jest.config.js +9 -0
- package/lib/cjs/errors/TemplateRenderError.js +1 -1
- package/lib/cjs/errors/TemplateRenderError.js.map +1 -1
- package/lib/cjs/services/PlatformResponseFilter.js +24 -12
- package/lib/cjs/services/PlatformResponseFilter.js.map +1 -1
- package/lib/cjs/utils/getContentType.js +4 -8
- package/lib/cjs/utils/getContentType.js.map +1 -1
- package/lib/esm/errors/TemplateRenderError.js +1 -1
- package/lib/esm/errors/TemplateRenderError.js.map +1 -1
- package/lib/esm/services/PlatformResponseFilter.js +24 -12
- package/lib/esm/services/PlatformResponseFilter.js.map +1 -1
- package/lib/esm/utils/getContentType.js +4 -8
- package/lib/esm/utils/getContentType.js.map +1 -1
- package/lib/types/services/PlatformResponseFilter.d.ts +1 -0
- package/package.json +19 -15
- package/readme.md +18 -16
package/coverage.json
ADDED
package/jest.config.js
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
// For a detailed explanation regarding each configuration property, visit:
|
|
2
|
+
// https://jestjs.io/docs/en/configuration.html
|
|
3
|
+
|
|
4
|
+
module.exports = {
|
|
5
|
+
...require("@tsed/jest-config")(__dirname, "platform-response-filter"),
|
|
6
|
+
coverageThreshold: {
|
|
7
|
+
global: require("./coverage.json")
|
|
8
|
+
}
|
|
9
|
+
};
|
|
@@ -7,9 +7,9 @@ const exceptions_1 = require("@tsed/exceptions");
|
|
|
7
7
|
* @private
|
|
8
8
|
*/
|
|
9
9
|
class TemplateRenderError extends exceptions_1.InternalServerError {
|
|
10
|
+
name = "TEMPLATE_RENDER_ERROR";
|
|
10
11
|
constructor(target, method, err) {
|
|
11
12
|
super(TemplateRenderError.buildMessage(target, method, err));
|
|
12
|
-
this.name = "TEMPLATE_RENDER_ERROR";
|
|
13
13
|
}
|
|
14
14
|
/**
|
|
15
15
|
*
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TemplateRenderError.js","sourceRoot":"","sources":["../../../src/errors/TemplateRenderError.ts"],"names":[],"mappings":";;;AAAA,qCAAwC;AACxC,iDAAqD;AAErD;;GAEG;AACH,MAAa,mBAAoB,SAAQ,gCAAmB;
|
|
1
|
+
{"version":3,"file":"TemplateRenderError.js","sourceRoot":"","sources":["../../../src/errors/TemplateRenderError.ts"],"names":[],"mappings":";;;AAAA,qCAAwC;AACxC,iDAAqD;AAErD;;GAEG;AACH,MAAa,mBAAoB,SAAQ,gCAAmB;IAC1D,IAAI,GAAG,uBAAuB,CAAC;IAE/B,YAAY,MAA0B,EAAE,MAAuB,EAAE,GAAU;QACzE,KAAK,CAAC,mBAAmB,CAAC,YAAY,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC;IAC/D,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,YAAY,CAAC,MAA0B,EAAE,MAAuB,EAAE,GAAU;QACjF,OAAO,6BAA6B,IAAA,aAAM,EAAC,MAAM,CAAC,IAAI,MAAM,CAAC,MAAM,CAAC,MAAM,GAAG,GAAG,CAAC;IACnF,CAAC;CACF;AAdD,kDAcC","sourcesContent":["import {nameOf, Type} from \"@tsed/core\";\nimport {InternalServerError} from \"@tsed/exceptions\";\n\n/**\n * @private\n */\nexport class TemplateRenderError extends InternalServerError {\n name = \"TEMPLATE_RENDER_ERROR\";\n\n constructor(target: Type<any> | string, method: string | symbol, err: Error) {\n super(TemplateRenderError.buildMessage(target, method, err));\n }\n\n /**\n *\n * @returns {string}\n */\n static buildMessage(target: Type<any> | string, method: string | symbol, err: Error) {\n return `Template rendering error: ${nameOf(target)}.${String(method)}()\\n` + err;\n }\n}\n"]}
|
|
@@ -3,8 +3,8 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.PlatformResponseFilter = void 0;
|
|
4
4
|
const tslib_1 = require("tslib");
|
|
5
5
|
const core_1 = require("@tsed/core");
|
|
6
|
-
const json_mapper_1 = require("@tsed/json-mapper");
|
|
7
6
|
const di_1 = require("@tsed/di");
|
|
7
|
+
const json_mapper_1 = require("@tsed/json-mapper");
|
|
8
8
|
const ResponseFiltersContainer_1 = require("../domain/ResponseFiltersContainer");
|
|
9
9
|
const getContentType_1 = require("../utils/getContentType");
|
|
10
10
|
const renderView_1 = require("../utils/renderView");
|
|
@@ -12,9 +12,10 @@ const renderView_1 = require("../utils/renderView");
|
|
|
12
12
|
* @platform
|
|
13
13
|
*/
|
|
14
14
|
let PlatformResponseFilter = class PlatformResponseFilter {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
15
|
+
types = new Map();
|
|
16
|
+
injector;
|
|
17
|
+
responseFilters;
|
|
18
|
+
additionalProperties;
|
|
18
19
|
get contentTypes() {
|
|
19
20
|
return [...this.types.keys()];
|
|
20
21
|
}
|
|
@@ -42,13 +43,15 @@ let PlatformResponseFilter = class PlatformResponseFilter {
|
|
|
42
43
|
*/
|
|
43
44
|
async transform(data, ctx) {
|
|
44
45
|
const { response } = ctx;
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
46
|
+
if (ctx.endpoint?.operation) {
|
|
47
|
+
const bestContentType = this.getBestContentType(data, ctx);
|
|
48
|
+
bestContentType && response.contentType(bestContentType);
|
|
49
|
+
if (this.types.has(bestContentType)) {
|
|
50
|
+
return this.types.get(bestContentType).transform(data, ctx);
|
|
51
|
+
}
|
|
52
|
+
if (this.types.has(getContentType_1.ANY_CONTENT_TYPE)) {
|
|
53
|
+
return this.types.get(getContentType_1.ANY_CONTENT_TYPE).transform(data, ctx);
|
|
54
|
+
}
|
|
52
55
|
}
|
|
53
56
|
return data;
|
|
54
57
|
}
|
|
@@ -64,16 +67,25 @@ let PlatformResponseFilter = class PlatformResponseFilter {
|
|
|
64
67
|
data = await (0, renderView_1.renderView)(data, ctx);
|
|
65
68
|
}
|
|
66
69
|
else if ((0, core_1.isSerializable)(data)) {
|
|
70
|
+
const responseOpts = endpoint.getResponseOptions(response.statusCode, {
|
|
71
|
+
includes: this.getIncludes(ctx)
|
|
72
|
+
});
|
|
67
73
|
data = (0, json_mapper_1.serialize)(data, {
|
|
68
74
|
useAlias: true,
|
|
69
75
|
additionalProperties: this.additionalProperties,
|
|
70
|
-
...
|
|
76
|
+
...responseOpts,
|
|
71
77
|
endpoint: true
|
|
72
78
|
});
|
|
73
79
|
}
|
|
74
80
|
}
|
|
75
81
|
return data;
|
|
76
82
|
}
|
|
83
|
+
getIncludes(ctx) {
|
|
84
|
+
if (ctx.request.query.includes) {
|
|
85
|
+
return [].concat(ctx.request.query.includes).flatMap((include) => include.split(","));
|
|
86
|
+
}
|
|
87
|
+
return undefined;
|
|
88
|
+
}
|
|
77
89
|
};
|
|
78
90
|
tslib_1.__decorate([
|
|
79
91
|
(0, di_1.Inject)(),
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"PlatformResponseFilter.js","sourceRoot":"","sources":["../../../src/services/PlatformResponseFilter.ts"],"names":[],"mappings":";;;;AAAA,qCAAgD;AAChD,mDAA4C;AAC5C,
|
|
1
|
+
{"version":3,"file":"PlatformResponseFilter.js","sourceRoot":"","sources":["../../../src/services/PlatformResponseFilter.ts"],"names":[],"mappings":"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","sourcesContent":["import {isSerializable, Type} from \"@tsed/core\";\nimport {BaseContext, Constant, Inject, Injectable, InjectorService} from \"@tsed/di\";\nimport {serialize} from \"@tsed/json-mapper\";\nimport {ResponseFilterKey, ResponseFiltersContainer} from \"../domain/ResponseFiltersContainer\";\nimport {ResponseFilterMethods} from \"../interfaces/ResponseFilterMethods\";\nimport {ANY_CONTENT_TYPE, getContentType} from \"../utils/getContentType\";\nimport {renderView} from \"../utils/renderView\";\n\n/**\n * @platform\n */\n@Injectable()\nexport class PlatformResponseFilter {\n protected types: Map<ResponseFilterKey, ResponseFilterMethods> = new Map();\n\n @Inject()\n protected injector: InjectorService;\n\n @Constant(\"responseFilters\", [])\n protected responseFilters: Type<ResponseFilterMethods>[];\n\n @Constant(\"additionalProperties\")\n protected additionalProperties: boolean;\n\n get contentTypes(): ResponseFilterKey[] {\n return [...this.types.keys()];\n }\n\n $onInit() {\n ResponseFiltersContainer.forEach((token, type) => {\n if (this.responseFilters.includes(token)) {\n this.types.set(type, this.injector.get(token)!);\n }\n });\n }\n\n getBestContentType(data: any, ctx: BaseContext) {\n const contentType = getContentType(data, ctx);\n\n if (ctx.request.get(\"Accept\")) {\n const bestContentType = ctx.request.accepts([contentType].concat(this.contentTypes).filter(Boolean));\n\n if (bestContentType) {\n return [].concat(bestContentType as any).filter((type) => type !== \"*/*\")[0];\n }\n }\n\n return contentType;\n }\n\n /**\n * Call filters to transform data\n * @param data\n * @param ctx\n */\n async transform(data: unknown, ctx: BaseContext) {\n const {response} = ctx;\n\n if (ctx.endpoint?.operation) {\n const bestContentType = this.getBestContentType(data, ctx);\n\n bestContentType && response.contentType(bestContentType);\n\n if (this.types.has(bestContentType)) {\n return this.types.get(bestContentType)!.transform(data, ctx);\n }\n\n if (this.types.has(ANY_CONTENT_TYPE)) {\n return this.types.get(ANY_CONTENT_TYPE)!.transform(data, ctx);\n }\n }\n\n return data;\n }\n\n /**\n * Serialize data before calling filters\n * @param data\n * @param ctx\n */\n async serialize(data: unknown, ctx: BaseContext) {\n const {response, endpoint} = ctx;\n\n if (endpoint) {\n if (endpoint.view) {\n data = await renderView(data, ctx);\n } else if (isSerializable(data)) {\n const responseOpts = endpoint.getResponseOptions(response.statusCode, {\n includes: this.getIncludes(ctx)\n });\n\n data = serialize(data, {\n useAlias: true,\n additionalProperties: this.additionalProperties,\n ...responseOpts,\n endpoint: true\n });\n }\n }\n\n return data;\n }\n\n private getIncludes(ctx: BaseContext) {\n if (ctx.request.query.includes) {\n return [].concat(ctx.request.query.includes).flatMap((include: string) => include.split(\",\"));\n }\n\n return undefined;\n }\n}\n"]}
|
|
@@ -11,16 +11,12 @@ function getContentType(data, ctx) {
|
|
|
11
11
|
const { operation } = endpoint;
|
|
12
12
|
const contentType = response.getContentType() || operation.getContentTypeOf(response.statusCode) || "";
|
|
13
13
|
if (contentType && contentType !== exports.ANY_CONTENT_TYPE) {
|
|
14
|
-
if (contentType === "application/json") {
|
|
15
|
-
|
|
16
|
-
return contentType;
|
|
17
|
-
}
|
|
18
|
-
}
|
|
19
|
-
else {
|
|
20
|
-
return contentType;
|
|
14
|
+
if (contentType === "application/json" && (0, core_1.isObject)(data)) {
|
|
15
|
+
return "application/json";
|
|
21
16
|
}
|
|
17
|
+
return contentType;
|
|
22
18
|
}
|
|
23
|
-
if (
|
|
19
|
+
if (endpoint.view) {
|
|
24
20
|
return "text/html";
|
|
25
21
|
}
|
|
26
22
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"getContentType.js","sourceRoot":"","sources":["../../../src/utils/getContentType.ts"],"names":[],"mappings":";;;AAAA,qCAAoC;
|
|
1
|
+
{"version":3,"file":"getContentType.js","sourceRoot":"","sources":["../../../src/utils/getContentType.ts"],"names":[],"mappings":";;;AAAA,qCAAoC;AAGvB,QAAA,gBAAgB,GAAG,KAAK,CAAC;AAEtC;;GAEG;AACH,SAAgB,cAAc,CAAC,IAAS,EAAE,GAAgB;IACxD,MAAM,EAAC,QAAQ,EAAE,QAAQ,EAAC,GAAG,GAAG,CAAC;IACjC,MAAM,EAAC,SAAS,EAAC,GAAG,QAAQ,CAAC;IAE7B,MAAM,WAAW,GAAG,QAAQ,CAAC,cAAc,EAAE,IAAI,SAAS,CAAC,gBAAgB,CAAC,QAAQ,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC;IAEvG,IAAI,WAAW,IAAI,WAAW,KAAK,wBAAgB,EAAE;QACnD,IAAI,WAAW,KAAK,kBAAkB,IAAI,IAAA,eAAQ,EAAC,IAAI,CAAC,EAAE;YACxD,OAAO,kBAAkB,CAAC;SAC3B;QAED,OAAO,WAAW,CAAC;KACpB;IAED,IAAI,QAAQ,CAAC,IAAI,EAAE;QACjB,OAAO,WAAW,CAAC;KACpB;AACH,CAAC;AAjBD,wCAiBC","sourcesContent":["import {isObject} from \"@tsed/core\";\nimport type {BaseContext} from \"@tsed/di\";\n\nexport const ANY_CONTENT_TYPE = \"*/*\";\n\n/**\n * @ignore\n */\nexport function getContentType(data: any, ctx: BaseContext) {\n const {endpoint, response} = ctx;\n const {operation} = endpoint;\n\n const contentType = response.getContentType() || operation.getContentTypeOf(response.statusCode) || \"\";\n\n if (contentType && contentType !== ANY_CONTENT_TYPE) {\n if (contentType === \"application/json\" && isObject(data)) {\n return \"application/json\";\n }\n\n return contentType;\n }\n\n if (endpoint.view) {\n return \"text/html\";\n }\n}\n"]}
|
|
@@ -4,9 +4,9 @@ import { InternalServerError } from "@tsed/exceptions";
|
|
|
4
4
|
* @private
|
|
5
5
|
*/
|
|
6
6
|
export class TemplateRenderError extends InternalServerError {
|
|
7
|
+
name = "TEMPLATE_RENDER_ERROR";
|
|
7
8
|
constructor(target, method, err) {
|
|
8
9
|
super(TemplateRenderError.buildMessage(target, method, err));
|
|
9
|
-
this.name = "TEMPLATE_RENDER_ERROR";
|
|
10
10
|
}
|
|
11
11
|
/**
|
|
12
12
|
*
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TemplateRenderError.js","sourceRoot":"","sources":["../../../src/errors/TemplateRenderError.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,MAAM,EAAO,MAAM,YAAY,CAAC;AACxC,OAAO,EAAC,mBAAmB,EAAC,MAAM,kBAAkB,CAAC;AAErD;;GAEG;AACH,MAAM,OAAO,mBAAoB,SAAQ,mBAAmB;
|
|
1
|
+
{"version":3,"file":"TemplateRenderError.js","sourceRoot":"","sources":["../../../src/errors/TemplateRenderError.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,MAAM,EAAO,MAAM,YAAY,CAAC;AACxC,OAAO,EAAC,mBAAmB,EAAC,MAAM,kBAAkB,CAAC;AAErD;;GAEG;AACH,MAAM,OAAO,mBAAoB,SAAQ,mBAAmB;IAC1D,IAAI,GAAG,uBAAuB,CAAC;IAE/B,YAAY,MAA0B,EAAE,MAAuB,EAAE,GAAU;QACzE,KAAK,CAAC,mBAAmB,CAAC,YAAY,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC;IAC/D,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,YAAY,CAAC,MAA0B,EAAE,MAAuB,EAAE,GAAU;QACjF,OAAO,6BAA6B,MAAM,CAAC,MAAM,CAAC,IAAI,MAAM,CAAC,MAAM,CAAC,MAAM,GAAG,GAAG,CAAC;IACnF,CAAC;CACF","sourcesContent":["import {nameOf, Type} from \"@tsed/core\";\nimport {InternalServerError} from \"@tsed/exceptions\";\n\n/**\n * @private\n */\nexport class TemplateRenderError extends InternalServerError {\n name = \"TEMPLATE_RENDER_ERROR\";\n\n constructor(target: Type<any> | string, method: string | symbol, err: Error) {\n super(TemplateRenderError.buildMessage(target, method, err));\n }\n\n /**\n *\n * @returns {string}\n */\n static buildMessage(target: Type<any> | string, method: string | symbol, err: Error) {\n return `Template rendering error: ${nameOf(target)}.${String(method)}()\\n` + err;\n }\n}\n"]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { __decorate, __metadata } from "tslib";
|
|
2
2
|
import { isSerializable } from "@tsed/core";
|
|
3
|
-
import { serialize } from "@tsed/json-mapper";
|
|
4
3
|
import { Constant, Inject, Injectable, InjectorService } from "@tsed/di";
|
|
4
|
+
import { serialize } from "@tsed/json-mapper";
|
|
5
5
|
import { ResponseFiltersContainer } from "../domain/ResponseFiltersContainer.js";
|
|
6
6
|
import { ANY_CONTENT_TYPE, getContentType } from "../utils/getContentType.js";
|
|
7
7
|
import { renderView } from "../utils/renderView.js";
|
|
@@ -9,9 +9,10 @@ import { renderView } from "../utils/renderView.js";
|
|
|
9
9
|
* @platform
|
|
10
10
|
*/
|
|
11
11
|
let PlatformResponseFilter = class PlatformResponseFilter {
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
12
|
+
types = new Map();
|
|
13
|
+
injector;
|
|
14
|
+
responseFilters;
|
|
15
|
+
additionalProperties;
|
|
15
16
|
get contentTypes() {
|
|
16
17
|
return [...this.types.keys()];
|
|
17
18
|
}
|
|
@@ -39,13 +40,15 @@ let PlatformResponseFilter = class PlatformResponseFilter {
|
|
|
39
40
|
*/
|
|
40
41
|
async transform(data, ctx) {
|
|
41
42
|
const { response } = ctx;
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
43
|
+
if (ctx.endpoint?.operation) {
|
|
44
|
+
const bestContentType = this.getBestContentType(data, ctx);
|
|
45
|
+
bestContentType && response.contentType(bestContentType);
|
|
46
|
+
if (this.types.has(bestContentType)) {
|
|
47
|
+
return this.types.get(bestContentType).transform(data, ctx);
|
|
48
|
+
}
|
|
49
|
+
if (this.types.has(ANY_CONTENT_TYPE)) {
|
|
50
|
+
return this.types.get(ANY_CONTENT_TYPE).transform(data, ctx);
|
|
51
|
+
}
|
|
49
52
|
}
|
|
50
53
|
return data;
|
|
51
54
|
}
|
|
@@ -61,16 +64,25 @@ let PlatformResponseFilter = class PlatformResponseFilter {
|
|
|
61
64
|
data = await renderView(data, ctx);
|
|
62
65
|
}
|
|
63
66
|
else if (isSerializable(data)) {
|
|
67
|
+
const responseOpts = endpoint.getResponseOptions(response.statusCode, {
|
|
68
|
+
includes: this.getIncludes(ctx)
|
|
69
|
+
});
|
|
64
70
|
data = serialize(data, {
|
|
65
71
|
useAlias: true,
|
|
66
72
|
additionalProperties: this.additionalProperties,
|
|
67
|
-
...
|
|
73
|
+
...responseOpts,
|
|
68
74
|
endpoint: true
|
|
69
75
|
});
|
|
70
76
|
}
|
|
71
77
|
}
|
|
72
78
|
return data;
|
|
73
79
|
}
|
|
80
|
+
getIncludes(ctx) {
|
|
81
|
+
if (ctx.request.query.includes) {
|
|
82
|
+
return [].concat(ctx.request.query.includes).flatMap((include) => include.split(","));
|
|
83
|
+
}
|
|
84
|
+
return undefined;
|
|
85
|
+
}
|
|
74
86
|
};
|
|
75
87
|
__decorate([
|
|
76
88
|
Inject(),
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"PlatformResponseFilter.js","sourceRoot":"","sources":["../../../src/services/PlatformResponseFilter.ts"],"names":[],"mappings":";AAAA,OAAO,EAAC,cAAc,EAAO,MAAM,YAAY,CAAC;AAChD,OAAO,
|
|
1
|
+
{"version":3,"file":"PlatformResponseFilter.js","sourceRoot":"","sources":["../../../src/services/PlatformResponseFilter.ts"],"names":[],"mappings":"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","sourcesContent":["import {isSerializable, Type} from \"@tsed/core\";\nimport {BaseContext, Constant, Inject, Injectable, InjectorService} from \"@tsed/di\";\nimport {serialize} from \"@tsed/json-mapper\";\nimport {ResponseFilterKey, ResponseFiltersContainer} from \"../domain/ResponseFiltersContainer\";\nimport {ResponseFilterMethods} from \"../interfaces/ResponseFilterMethods\";\nimport {ANY_CONTENT_TYPE, getContentType} from \"../utils/getContentType\";\nimport {renderView} from \"../utils/renderView\";\n\n/**\n * @platform\n */\n@Injectable()\nexport class PlatformResponseFilter {\n protected types: Map<ResponseFilterKey, ResponseFilterMethods> = new Map();\n\n @Inject()\n protected injector: InjectorService;\n\n @Constant(\"responseFilters\", [])\n protected responseFilters: Type<ResponseFilterMethods>[];\n\n @Constant(\"additionalProperties\")\n protected additionalProperties: boolean;\n\n get contentTypes(): ResponseFilterKey[] {\n return [...this.types.keys()];\n }\n\n $onInit() {\n ResponseFiltersContainer.forEach((token, type) => {\n if (this.responseFilters.includes(token)) {\n this.types.set(type, this.injector.get(token)!);\n }\n });\n }\n\n getBestContentType(data: any, ctx: BaseContext) {\n const contentType = getContentType(data, ctx);\n\n if (ctx.request.get(\"Accept\")) {\n const bestContentType = ctx.request.accepts([contentType].concat(this.contentTypes).filter(Boolean));\n\n if (bestContentType) {\n return [].concat(bestContentType as any).filter((type) => type !== \"*/*\")[0];\n }\n }\n\n return contentType;\n }\n\n /**\n * Call filters to transform data\n * @param data\n * @param ctx\n */\n async transform(data: unknown, ctx: BaseContext) {\n const {response} = ctx;\n\n if (ctx.endpoint?.operation) {\n const bestContentType = this.getBestContentType(data, ctx);\n\n bestContentType && response.contentType(bestContentType);\n\n if (this.types.has(bestContentType)) {\n return this.types.get(bestContentType)!.transform(data, ctx);\n }\n\n if (this.types.has(ANY_CONTENT_TYPE)) {\n return this.types.get(ANY_CONTENT_TYPE)!.transform(data, ctx);\n }\n }\n\n return data;\n }\n\n /**\n * Serialize data before calling filters\n * @param data\n * @param ctx\n */\n async serialize(data: unknown, ctx: BaseContext) {\n const {response, endpoint} = ctx;\n\n if (endpoint) {\n if (endpoint.view) {\n data = await renderView(data, ctx);\n } else if (isSerializable(data)) {\n const responseOpts = endpoint.getResponseOptions(response.statusCode, {\n includes: this.getIncludes(ctx)\n });\n\n data = serialize(data, {\n useAlias: true,\n additionalProperties: this.additionalProperties,\n ...responseOpts,\n endpoint: true\n });\n }\n }\n\n return data;\n }\n\n private getIncludes(ctx: BaseContext) {\n if (ctx.request.query.includes) {\n return [].concat(ctx.request.query.includes).flatMap((include: string) => include.split(\",\"));\n }\n\n return undefined;\n }\n}\n"]}
|
|
@@ -8,16 +8,12 @@ export function getContentType(data, ctx) {
|
|
|
8
8
|
const { operation } = endpoint;
|
|
9
9
|
const contentType = response.getContentType() || operation.getContentTypeOf(response.statusCode) || "";
|
|
10
10
|
if (contentType && contentType !== ANY_CONTENT_TYPE) {
|
|
11
|
-
if (contentType === "application/json") {
|
|
12
|
-
|
|
13
|
-
return contentType;
|
|
14
|
-
}
|
|
15
|
-
}
|
|
16
|
-
else {
|
|
17
|
-
return contentType;
|
|
11
|
+
if (contentType === "application/json" && isObject(data)) {
|
|
12
|
+
return "application/json";
|
|
18
13
|
}
|
|
14
|
+
return contentType;
|
|
19
15
|
}
|
|
20
|
-
if (
|
|
16
|
+
if (endpoint.view) {
|
|
21
17
|
return "text/html";
|
|
22
18
|
}
|
|
23
19
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"getContentType.js","sourceRoot":"","sources":["../../../src/utils/getContentType.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,QAAQ,EAAC,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"getContentType.js","sourceRoot":"","sources":["../../../src/utils/getContentType.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,QAAQ,EAAC,MAAM,YAAY,CAAC;AAGpC,MAAM,CAAC,MAAM,gBAAgB,GAAG,KAAK,CAAC;AAEtC;;GAEG;AACH,MAAM,UAAU,cAAc,CAAC,IAAS,EAAE,GAAgB;IACxD,MAAM,EAAC,QAAQ,EAAE,QAAQ,EAAC,GAAG,GAAG,CAAC;IACjC,MAAM,EAAC,SAAS,EAAC,GAAG,QAAQ,CAAC;IAE7B,MAAM,WAAW,GAAG,QAAQ,CAAC,cAAc,EAAE,IAAI,SAAS,CAAC,gBAAgB,CAAC,QAAQ,CAAC,UAAU,CAAC,IAAI,EAAE,CAAC;IAEvG,IAAI,WAAW,IAAI,WAAW,KAAK,gBAAgB,EAAE;QACnD,IAAI,WAAW,KAAK,kBAAkB,IAAI,QAAQ,CAAC,IAAI,CAAC,EAAE;YACxD,OAAO,kBAAkB,CAAC;SAC3B;QAED,OAAO,WAAW,CAAC;KACpB;IAED,IAAI,QAAQ,CAAC,IAAI,EAAE;QACjB,OAAO,WAAW,CAAC;KACpB;AACH,CAAC","sourcesContent":["import {isObject} from \"@tsed/core\";\nimport type {BaseContext} from \"@tsed/di\";\n\nexport const ANY_CONTENT_TYPE = \"*/*\";\n\n/**\n * @ignore\n */\nexport function getContentType(data: any, ctx: BaseContext) {\n const {endpoint, response} = ctx;\n const {operation} = endpoint;\n\n const contentType = response.getContentType() || operation.getContentTypeOf(response.statusCode) || \"\";\n\n if (contentType && contentType !== ANY_CONTENT_TYPE) {\n if (contentType === \"application/json\" && isObject(data)) {\n return \"application/json\";\n }\n\n return contentType;\n }\n\n if (endpoint.view) {\n return \"text/html\";\n }\n}\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tsed/platform-response-filter",
|
|
3
|
-
"version": "7.0.0-
|
|
3
|
+
"version": "7.0.0-rc.2",
|
|
4
4
|
"description": "Platform response filter module for Ts.ED Framework",
|
|
5
5
|
"private": false,
|
|
6
6
|
"source": "./src/index.ts",
|
|
@@ -17,24 +17,25 @@
|
|
|
17
17
|
"build": "yarn barrels && yarn run build:esm && yarn run build:cjs",
|
|
18
18
|
"build:cjs": "tsc --build tsconfig.compile.json",
|
|
19
19
|
"build:esm": "tsc --build tsconfig.compile.esm.json",
|
|
20
|
-
"barrels": "yarn barrelsby --delete -d ./src -e \"\\.spec\\.ts\" -e \"__mock__\" -e \".benchmark.ts\""
|
|
20
|
+
"barrels": "yarn barrelsby --delete -d ./src -e \"\\.spec\\.ts\" -e \"__mock__\" -e \".benchmark.ts\"",
|
|
21
|
+
"test": "cross-env NODE_ENV=test yarn jest --max-workers=2"
|
|
21
22
|
},
|
|
22
23
|
"dependencies": {
|
|
23
|
-
"tslib": "2.
|
|
24
|
+
"tslib": "2.4.0"
|
|
24
25
|
},
|
|
25
26
|
"devDependencies": {
|
|
26
|
-
"@tsed/core": "7.0.0-
|
|
27
|
-
"@tsed/di": "7.0.0-
|
|
28
|
-
"@tsed/exceptions": "7.0.0-
|
|
29
|
-
"@tsed/json-mapper": "7.0.0-
|
|
30
|
-
"@tsed/schema": "7.0.0-
|
|
27
|
+
"@tsed/core": "7.0.0-rc.2",
|
|
28
|
+
"@tsed/di": "7.0.0-rc.2",
|
|
29
|
+
"@tsed/exceptions": "7.0.0-rc.2",
|
|
30
|
+
"@tsed/json-mapper": "7.0.0-rc.2",
|
|
31
|
+
"@tsed/schema": "7.0.0-rc.2"
|
|
31
32
|
},
|
|
32
33
|
"peerDependencies": {
|
|
33
|
-
"@tsed/core": "^7.0.0-
|
|
34
|
-
"@tsed/di": "^7.0.0-
|
|
35
|
-
"@tsed/exceptions": "^7.0.0-
|
|
36
|
-
"@tsed/json-mapper": "^7.0.0-
|
|
37
|
-
"@tsed/schema": "^7.0.0-
|
|
34
|
+
"@tsed/core": "^7.0.0-rc.2",
|
|
35
|
+
"@tsed/di": "^7.0.0-rc.2",
|
|
36
|
+
"@tsed/exceptions": "^7.0.0-rc.2",
|
|
37
|
+
"@tsed/json-mapper": "^7.0.0-rc.2",
|
|
38
|
+
"@tsed/schema": "^7.0.0-rc.2"
|
|
38
39
|
},
|
|
39
40
|
"peerDependenciesMeta": {
|
|
40
41
|
"@tsed/core": {
|
|
@@ -57,7 +58,10 @@
|
|
|
57
58
|
"bugs": {
|
|
58
59
|
"url": "https://github.com/tsedio/tsed/issues"
|
|
59
60
|
},
|
|
60
|
-
"homepage": "https://github.com/tsedio/tsed/tree/
|
|
61
|
+
"homepage": "https://github.com/tsedio/tsed/tree/rc/packages/platform/platform-response-filter",
|
|
61
62
|
"author": "Romain Lenzotti",
|
|
62
|
-
"license": "MIT"
|
|
63
|
+
"license": "MIT",
|
|
64
|
+
"publishConfig": {
|
|
65
|
+
"tag": "rc"
|
|
66
|
+
}
|
|
63
67
|
}
|
package/readme.md
CHANGED
|
@@ -11,7 +11,8 @@
|
|
|
11
11
|
[](https://badge.fury.io/js/%40tsed%2Fcommon)
|
|
12
12
|
[](https://github.com/semantic-release/semantic-release)
|
|
13
13
|
[](https://github.com/prettier/prettier)
|
|
14
|
-
[](https://github.com/sponsors/romakita)
|
|
15
|
+
[](https://opencollective.com/tsed)
|
|
15
16
|
|
|
16
17
|
</div>
|
|
17
18
|
|
|
@@ -36,12 +37,13 @@ Transform data returned by a method to a formatted response based on the stored
|
|
|
36
37
|
# Installation
|
|
37
38
|
|
|
38
39
|
```bash
|
|
39
|
-
npm install --save @tsed/di @tsed/platform-views @tsed/schema @tsed/json-schema @tsed/platform-response-filter
|
|
40
|
+
npm install --save @tsed/di @tsed/platform-views @tsed/schema @tsed/json-schema @tsed/platform-response-filter
|
|
40
41
|
```
|
|
41
42
|
|
|
42
43
|
## Usage
|
|
43
44
|
|
|
44
45
|
Define a class that return data:
|
|
46
|
+
|
|
45
47
|
```typescript
|
|
46
48
|
import {Injectable} from "@tsed/di";
|
|
47
49
|
import {Returns} from "@tsed/schema";
|
|
@@ -51,13 +53,13 @@ import {MyModel} from "../models/MyModel";
|
|
|
51
53
|
class MyService {
|
|
52
54
|
@Returns(200, MyModel)
|
|
53
55
|
async getData() {
|
|
54
|
-
return new MyModel({
|
|
56
|
+
return new MyModel({id: "id", test: "test"});
|
|
55
57
|
}
|
|
56
58
|
|
|
57
59
|
@Returns(200, MyModel)
|
|
58
60
|
@View("myview.ejs")
|
|
59
61
|
async getDataView() {
|
|
60
|
-
return new MyModel({
|
|
62
|
+
return new MyModel({id: "id", test: "test"});
|
|
61
63
|
}
|
|
62
64
|
}
|
|
63
65
|
```
|
|
@@ -80,7 +82,7 @@ Then call the service in you module:
|
|
|
80
82
|
```typescript
|
|
81
83
|
import {Module, DIContext} from "@tsed/di";
|
|
82
84
|
import {ResponseFilter} from "@tsed/platform-response-filter";
|
|
83
|
-
import "./filters/WrapperResponseFilter"
|
|
85
|
+
import "./filters/WrapperResponseFilter";
|
|
84
86
|
|
|
85
87
|
@Module()
|
|
86
88
|
class MyModule {
|
|
@@ -95,36 +97,36 @@ class MyModule {
|
|
|
95
97
|
id: uuid.v4(),
|
|
96
98
|
injector: this.injector,
|
|
97
99
|
logger: this.injector.logger
|
|
98
|
-
})
|
|
100
|
+
});
|
|
99
101
|
|
|
100
102
|
// must implement these methods
|
|
101
103
|
context.request = {
|
|
102
104
|
accepts(...args: any[]) {
|
|
103
|
-
return req.accepts(...args)
|
|
105
|
+
return req.accepts(...args);
|
|
104
106
|
},
|
|
105
107
|
get(key: string) {
|
|
106
|
-
return req.get(key)
|
|
108
|
+
return req.get(key);
|
|
107
109
|
}
|
|
108
|
-
}
|
|
110
|
+
};
|
|
109
111
|
context.response = {
|
|
110
112
|
contentType(contentType: string) {
|
|
111
|
-
res.contentType(contentType)
|
|
113
|
+
res.contentType(contentType);
|
|
112
114
|
}
|
|
113
|
-
}
|
|
115
|
+
};
|
|
114
116
|
|
|
115
117
|
const service = this.injector.get<MyService>(MyService);
|
|
116
|
-
let data = await service.getData()
|
|
118
|
+
let data = await service.getData();
|
|
117
119
|
|
|
118
120
|
// serialize data (map Model to Plain object)
|
|
119
121
|
data = await this.responseFilter.serialize(data, context);
|
|
120
122
|
|
|
121
123
|
// call filter based on the right content type
|
|
122
|
-
data = await this.responseFilter.transform(data, context)
|
|
124
|
+
data = await this.responseFilter.transform(data, context);
|
|
123
125
|
|
|
124
126
|
if (isObject(data)) {
|
|
125
|
-
res.json(data)
|
|
127
|
+
res.json(data);
|
|
126
128
|
} else {
|
|
127
|
-
res.send(data)
|
|
129
|
+
res.send(data);
|
|
128
130
|
}
|
|
129
131
|
}
|
|
130
132
|
}
|
|
@@ -165,7 +167,7 @@ website. [[Become a sponsor](https://opencollective.com/tsed#sponsor)]
|
|
|
165
167
|
|
|
166
168
|
The MIT License (MIT)
|
|
167
169
|
|
|
168
|
-
Copyright (c) 2016 -
|
|
170
|
+
Copyright (c) 2016 - 2022 Romain Lenzotti
|
|
169
171
|
|
|
170
172
|
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated
|
|
171
173
|
documentation files (the "Software"), to deal in the Software without restriction, including without limitation the
|