@loopback/openapi-v3 1.10.1 → 1.12.0
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/CHANGELOG.md +40 -0
- package/dist/controller-spec.js +62 -31
- package/dist/controller-spec.js.map +1 -1
- package/dist/decorators/api.decorator.js +2 -2
- package/dist/decorators/api.decorator.js.map +1 -1
- package/dist/decorators/operation.decorator.js +2 -2
- package/dist/decorators/operation.decorator.js.map +1 -1
- package/dist/decorators/parameter.decorator.js +5 -4
- package/dist/decorators/parameter.decorator.js.map +1 -1
- package/dist/decorators/request-body.decorator.js +12 -8
- package/dist/decorators/request-body.decorator.js.map +1 -1
- package/dist/enhancers/index.d.ts +3 -0
- package/dist/enhancers/index.js +13 -0
- package/dist/enhancers/index.js.map +1 -0
- package/dist/enhancers/keys.d.ts +6 -0
- package/dist/enhancers/keys.js +12 -0
- package/dist/enhancers/keys.js.map +1 -0
- package/dist/enhancers/spec-enhancer.service.d.ts +73 -0
- package/dist/enhancers/spec-enhancer.service.js +135 -0
- package/dist/enhancers/spec-enhancer.service.js.map +1 -0
- package/dist/enhancers/types.d.ts +18 -0
- package/dist/enhancers/types.js +20 -0
- package/dist/enhancers/types.js.map +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/json-to-schema.js +16 -11
- package/dist/json-to-schema.js.map +1 -1
- package/dist/keys.d.ts +1 -1
- package/dist/keys.js +6 -10
- package/dist/keys.js.map +1 -1
- package/package.json +12 -11
- package/src/controller-spec.ts +53 -21
- package/src/decorators/api.decorator.ts +1 -1
- package/src/decorators/operation.decorator.ts +1 -1
- package/src/decorators/parameter.decorator.ts +2 -2
- package/src/decorators/request-body.decorator.ts +4 -4
- package/src/enhancers/index.ts +8 -0
- package/src/enhancers/keys.ts +14 -0
- package/src/enhancers/spec-enhancer.service.ts +121 -0
- package/src/enhancers/types.ts +30 -0
- package/src/index.ts +1 -0
- package/src/json-to-schema.ts +14 -8
- package/src/keys.ts +1 -6
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// Copyright IBM Corp. 2019. All Rights Reserved.
|
|
3
|
+
// Node module: @loopback/openapi-v3
|
|
4
|
+
// This file is licensed under the MIT License.
|
|
5
|
+
// License text available at https://opensource.org/licenses/MIT
|
|
6
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
7
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
8
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
9
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
10
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
11
|
+
};
|
|
12
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
13
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
14
|
+
};
|
|
15
|
+
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
16
|
+
return function (target, key) { decorator(target, key, paramIndex); }
|
|
17
|
+
};
|
|
18
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
19
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
20
|
+
};
|
|
21
|
+
var __importStar = (this && this.__importStar) || function (mod) {
|
|
22
|
+
if (mod && mod.__esModule) return mod;
|
|
23
|
+
var result = {};
|
|
24
|
+
if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k];
|
|
25
|
+
result["default"] = mod;
|
|
26
|
+
return result;
|
|
27
|
+
};
|
|
28
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
29
|
+
const core_1 = require("@loopback/core");
|
|
30
|
+
const debug_1 = __importDefault(require("debug"));
|
|
31
|
+
const _ = __importStar(require("lodash"));
|
|
32
|
+
const util_1 = require("util");
|
|
33
|
+
const types_1 = require("./types");
|
|
34
|
+
const jsonmergepatch = require('json-merge-patch');
|
|
35
|
+
const debug = debug_1.default('loopback:openapi:spec-enhancer');
|
|
36
|
+
/**
|
|
37
|
+
* An extension point for OpenAPI Spec enhancement
|
|
38
|
+
* This service is used for enhancing an OpenAPI spec by loading and applying one or more
|
|
39
|
+
* registered enhancers.
|
|
40
|
+
*
|
|
41
|
+
* A typical use of it would be generating the OpenAPI spec for the endpoints on a server
|
|
42
|
+
* in the `@loopback/rest` module.
|
|
43
|
+
*/
|
|
44
|
+
let OASEnhancerService = class OASEnhancerService {
|
|
45
|
+
constructor(
|
|
46
|
+
/**
|
|
47
|
+
* Inject a getter function to fetch spec enhancers
|
|
48
|
+
*/
|
|
49
|
+
getEnhancers,
|
|
50
|
+
/**
|
|
51
|
+
* An extension point should be able to receive its options via dependency
|
|
52
|
+
* injection.
|
|
53
|
+
*/
|
|
54
|
+
options) {
|
|
55
|
+
this.getEnhancers = getEnhancers;
|
|
56
|
+
this.options = options;
|
|
57
|
+
this._spec = {
|
|
58
|
+
openapi: '3.0.0',
|
|
59
|
+
info: {
|
|
60
|
+
title: 'LoopBack Application',
|
|
61
|
+
version: '1.0.0',
|
|
62
|
+
},
|
|
63
|
+
paths: {},
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Getter for `_spec`
|
|
68
|
+
*/
|
|
69
|
+
get spec() {
|
|
70
|
+
return this._spec;
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Setter for `_spec`
|
|
74
|
+
*/
|
|
75
|
+
set spec(value) {
|
|
76
|
+
this._spec = value;
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Find an enhancer by its name
|
|
80
|
+
* @param name The name of the enhancer you want to find
|
|
81
|
+
*/
|
|
82
|
+
async getEnhancerByName(name) {
|
|
83
|
+
// Get the latest list of enhancers
|
|
84
|
+
const enhancers = await this.getEnhancers();
|
|
85
|
+
return enhancers.find(e => e.name === name);
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Apply a given enhancer's merge function. Return the latest _spec.
|
|
89
|
+
* @param name The name of the enhancer you want to apply
|
|
90
|
+
*/
|
|
91
|
+
async applyEnhancerByName(name) {
|
|
92
|
+
const enhancer = await this.getEnhancerByName(name);
|
|
93
|
+
if (enhancer)
|
|
94
|
+
this._spec = enhancer.modifySpec(this._spec);
|
|
95
|
+
return this._spec;
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* Generate OpenAPI spec by applying ALL registered enhancers
|
|
99
|
+
* TBD: load enhancers by group names
|
|
100
|
+
*/
|
|
101
|
+
async applyAllEnhancers(options = {}) {
|
|
102
|
+
const enhancers = await this.getEnhancers();
|
|
103
|
+
if (_.isEmpty(enhancers))
|
|
104
|
+
return this._spec;
|
|
105
|
+
for (const e of enhancers) {
|
|
106
|
+
this._spec = e.modifySpec(this._spec);
|
|
107
|
+
}
|
|
108
|
+
debug(`Spec enhancer service, generated spec: ${util_1.inspect(this._spec)}`);
|
|
109
|
+
return this._spec;
|
|
110
|
+
}
|
|
111
|
+
};
|
|
112
|
+
OASEnhancerService = __decorate([
|
|
113
|
+
core_1.extensionPoint(types_1.OAS_ENHANCER_EXTENSION_POINT_NAME),
|
|
114
|
+
__param(0, core_1.extensions()),
|
|
115
|
+
__param(1, core_1.config()),
|
|
116
|
+
__metadata("design:paramtypes", [Function, Object])
|
|
117
|
+
], OASEnhancerService);
|
|
118
|
+
exports.OASEnhancerService = OASEnhancerService;
|
|
119
|
+
/**
|
|
120
|
+
* The default merge function to patch the current OpenAPI spec.
|
|
121
|
+
* It leverages module `json-merge-patch`'s merge API to merge two json objects.
|
|
122
|
+
* It returns a new merged object without modifying the original one.
|
|
123
|
+
*
|
|
124
|
+
* A list of merging rules can be found in test file:
|
|
125
|
+
* https://github.com/pierreinglebert/json-merge-patch/blob/master/test/lib/merge.js
|
|
126
|
+
*
|
|
127
|
+
* @param currentSpec The original spec
|
|
128
|
+
* @param patchSpec The patch spec to be merged into the original spec
|
|
129
|
+
*/
|
|
130
|
+
function mergeOpenAPISpec(currentSpec, patchSpec) {
|
|
131
|
+
const mergedSpec = jsonmergepatch.merge(currentSpec, patchSpec);
|
|
132
|
+
return mergedSpec;
|
|
133
|
+
}
|
|
134
|
+
exports.mergeOpenAPISpec = mergeOpenAPISpec;
|
|
135
|
+
//# sourceMappingURL=spec-enhancer.service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"spec-enhancer.service.js","sourceRoot":"","sources":["../../src/enhancers/spec-enhancer.service.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE;;;;;;;;;;;;;;;;;;;;;;;;AAEhE,yCAA0E;AAC1E,kDAAgC;AAChC,0CAA4B;AAC5B,+BAA6B;AAE7B,mCAAuE;AACvE,MAAM,cAAc,GAAG,OAAO,CAAC,kBAAkB,CAAC,CAAC;AAEnD,MAAM,KAAK,GAAG,eAAW,CAAC,gCAAgC,CAAC,CAAC;AAS5D;;;;;;;GAOG;AAEH,IAAa,kBAAkB,GAA/B,MAAa,kBAAkB;IAC7B;IACE;;OAEG;IAEK,YAAmC;IAC3C;;;OAGG;IAEa,OAAmC;QAN3C,iBAAY,GAAZ,YAAY,CAAuB;QAM3B,YAAO,GAAP,OAAO,CAA4B;QAG7C,UAAK,GAAgB;YAC3B,OAAO,EAAE,OAAO;YAChB,IAAI,EAAE;gBACJ,KAAK,EAAE,sBAAsB;gBAC7B,OAAO,EAAE,OAAO;aACjB;YACD,KAAK,EAAE,EAAE;SACV,CAAC;IATC,CAAC;IAWJ;;OAEG;IACH,IAAI,IAAI;QACN,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;IACD;;OAEG;IACH,IAAI,IAAI,CAAC,KAAkB;QACzB,IAAI,CAAC,KAAK,GAAG,KAAK,CAAC;IACrB,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,iBAAiB,CAAC,IAAY;QAClC,mCAAmC;QACnC,MAAM,SAAS,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;QAC5C,OAAO,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,IAAI,CAAC,CAAC;IAC9C,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,mBAAmB,CAAC,IAAY;QACpC,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,iBAAiB,CAAC,IAAI,CAAC,CAAC;QACpD,IAAI,QAAQ;YAAE,IAAI,CAAC,KAAK,GAAG,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC3D,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,iBAAiB,CAAC,OAAO,GAAG,EAAE;QAClC,MAAM,SAAS,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;QAC5C,IAAI,CAAC,CAAC,OAAO,CAAC,SAAS,CAAC;YAAE,OAAO,IAAI,CAAC,KAAK,CAAC;QAC5C,KAAK,MAAM,CAAC,IAAI,SAAS,EAAE;YACzB,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,UAAU,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;SACvC;QACD,KAAK,CAAC,0CAA0C,cAAO,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;QACvE,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;CACF,CAAA;AAtEY,kBAAkB;IAD9B,qBAAc,CAAC,yCAAiC,CAAC;IAM7C,WAAA,iBAAU,EAAE,CAAA;IAMZ,WAAA,aAAM,EAAE,CAAA;;GAXA,kBAAkB,CAsE9B;AAtEY,gDAAkB;AAwE/B;;;;;;;;;;GAUG;AACH,SAAgB,gBAAgB,CAC9B,WAAiC,EACjC,SAA+B;IAE/B,MAAM,UAAU,GAAG,cAAc,CAAC,KAAK,CAAC,WAAW,EAAE,SAAS,CAAC,CAAC;IAChE,OAAO,UAAU,CAAC;AACpB,CAAC;AAND,4CAMC"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { BindingTemplate } from '@loopback/core';
|
|
2
|
+
import { OpenApiSpec } from '../types';
|
|
3
|
+
/**
|
|
4
|
+
* Typically an extension point defines an interface as the contract for
|
|
5
|
+
* extensions to implement
|
|
6
|
+
*/
|
|
7
|
+
export interface OASEnhancer {
|
|
8
|
+
name: string;
|
|
9
|
+
modifySpec(spec: OpenApiSpec): OpenApiSpec;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Name/id of the OAS enhancer extension point
|
|
13
|
+
*/
|
|
14
|
+
export declare const OAS_ENHANCER_EXTENSION_POINT_NAME = "oas-enhancer";
|
|
15
|
+
/**
|
|
16
|
+
* A binding template for spec contributor extensions
|
|
17
|
+
*/
|
|
18
|
+
export declare const asSpecEnhancer: BindingTemplate;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// Copyright IBM Corp. 2019. All Rights Reserved.
|
|
3
|
+
// Node module: @loopback/openapi-v3
|
|
4
|
+
// This file is licensed under the MIT License.
|
|
5
|
+
// License text available at https://opensource.org/licenses/MIT
|
|
6
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
+
const core_1 = require("@loopback/core");
|
|
8
|
+
/**
|
|
9
|
+
* Name/id of the OAS enhancer extension point
|
|
10
|
+
*/
|
|
11
|
+
exports.OAS_ENHANCER_EXTENSION_POINT_NAME = 'oas-enhancer';
|
|
12
|
+
/**
|
|
13
|
+
* A binding template for spec contributor extensions
|
|
14
|
+
*/
|
|
15
|
+
exports.asSpecEnhancer = binding => {
|
|
16
|
+
core_1.extensionFor(exports.OAS_ENHANCER_EXTENSION_POINT_NAME)(binding);
|
|
17
|
+
// is it ok to have a different namespace than the extension point name?
|
|
18
|
+
binding.tag({ namespace: 'oas-enhancer' });
|
|
19
|
+
};
|
|
20
|
+
//# sourceMappingURL=types.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/enhancers/types.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE;;AAEhE,yCAA6D;AAY7D;;GAEG;AACU,QAAA,iCAAiC,GAAG,cAAc,CAAC;AAEhE;;GAEG;AACU,QAAA,cAAc,GAAoB,OAAO,CAAC,EAAE;IACvD,mBAAY,CAAC,yCAAiC,CAAC,CAAC,OAAO,CAAC,CAAC;IACzD,wEAAwE;IACxE,OAAO,CAAC,GAAG,CAAC,EAAC,SAAS,EAAE,cAAc,EAAC,CAAC,CAAC;AAC3C,CAAC,CAAC"}
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -10,6 +10,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
10
10
|
__export(require("@loopback/repository-json-schema"));
|
|
11
11
|
__export(require("./controller-spec"));
|
|
12
12
|
__export(require("./decorators"));
|
|
13
|
+
__export(require("./enhancers"));
|
|
13
14
|
__export(require("./filter-schema"));
|
|
14
15
|
__export(require("./json-to-schema"));
|
|
15
16
|
__export(require("./types"));
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE;;;;;AAEhE,sDAAiD;AACjD,uCAAkC;AAClC,kCAA6B;AAC7B,qCAAgC;AAChC,sCAAiC;AACjC,6BAAwB"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE;;;;;AAEhE,sDAAiD;AACjD,uCAAkC;AAClC,kCAA6B;AAC7B,iCAA4B;AAC5B,qCAAgC;AAChC,sCAAiC;AACjC,6BAAwB"}
|
package/dist/json-to-schema.js
CHANGED
|
@@ -3,8 +3,11 @@
|
|
|
3
3
|
// Node module: @loopback/openapi-v3
|
|
4
4
|
// This file is licensed under the MIT License.
|
|
5
5
|
// License text available at https://opensource.org/licenses/MIT
|
|
6
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
7
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
8
|
+
};
|
|
6
9
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
-
const
|
|
10
|
+
const lodash_1 = __importDefault(require("lodash"));
|
|
8
11
|
const types_1 = require("./types");
|
|
9
12
|
/**
|
|
10
13
|
* Converts JSON Schemas into a SchemaObject
|
|
@@ -25,13 +28,7 @@ function jsonToSchemaObject(json, visited = new Map()) {
|
|
|
25
28
|
[converted]: false,
|
|
26
29
|
};
|
|
27
30
|
visited.set(json, result);
|
|
28
|
-
const propsToIgnore = [
|
|
29
|
-
'anyOf',
|
|
30
|
-
'oneOf',
|
|
31
|
-
'additionalItems',
|
|
32
|
-
'defaultProperties',
|
|
33
|
-
'typeof',
|
|
34
|
-
];
|
|
31
|
+
const propsToIgnore = ['additionalItems', 'defaultProperties', 'typeof'];
|
|
35
32
|
for (const property in json) {
|
|
36
33
|
if (propsToIgnore.includes(property)) {
|
|
37
34
|
continue;
|
|
@@ -45,15 +42,23 @@ function jsonToSchemaObject(json, visited = new Map()) {
|
|
|
45
42
|
break;
|
|
46
43
|
}
|
|
47
44
|
case 'allOf': {
|
|
48
|
-
result.allOf =
|
|
45
|
+
result.allOf = lodash_1.default.map(json.allOf, item => jsonToSchemaObject(item, visited));
|
|
46
|
+
break;
|
|
47
|
+
}
|
|
48
|
+
case 'anyOf': {
|
|
49
|
+
result.anyOf = lodash_1.default.map(json.anyOf, item => jsonToSchemaObject(item, visited));
|
|
50
|
+
break;
|
|
51
|
+
}
|
|
52
|
+
case 'oneOf': {
|
|
53
|
+
result.oneOf = lodash_1.default.map(json.oneOf, item => jsonToSchemaObject(item, visited));
|
|
49
54
|
break;
|
|
50
55
|
}
|
|
51
56
|
case 'definitions': {
|
|
52
|
-
result.definitions =
|
|
57
|
+
result.definitions = lodash_1.default.mapValues(json.definitions, def => jsonToSchemaObject(jsonOrBooleanToJSON(def), visited));
|
|
53
58
|
break;
|
|
54
59
|
}
|
|
55
60
|
case 'properties': {
|
|
56
|
-
result.properties =
|
|
61
|
+
result.properties = lodash_1.default.mapValues(json.properties, item => jsonToSchemaObject(jsonOrBooleanToJSON(item), visited));
|
|
57
62
|
break;
|
|
58
63
|
}
|
|
59
64
|
case 'additionalProperties': {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"json-to-schema.js","sourceRoot":"","sources":["../src/json-to-schema.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE
|
|
1
|
+
{"version":3,"file":"json-to-schema.js","sourceRoot":"","sources":["../src/json-to-schema.ts"],"names":[],"mappings":"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"}
|
package/dist/keys.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { MetadataAccessor } from '@loopback/
|
|
1
|
+
import { MetadataAccessor } from '@loopback/core';
|
|
2
2
|
import { ControllerSpec, RestEndpoint } from './controller-spec';
|
|
3
3
|
import { ParameterObject, RequestBodyObject } from './types';
|
|
4
4
|
export declare namespace OAI3Keys {
|
package/dist/keys.js
CHANGED
|
@@ -4,32 +4,28 @@
|
|
|
4
4
|
// This file is licensed under the MIT License.
|
|
5
5
|
// License text available at https://opensource.org/licenses/MIT
|
|
6
6
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
-
const
|
|
8
|
-
// Copyright IBM Corp. 2018. All Rights Reserved.
|
|
9
|
-
// Node module: @loopback/openapi-v3
|
|
10
|
-
// This file is licensed under the MIT License.
|
|
11
|
-
// License text available at https://opensource.org/licenses/MIT
|
|
7
|
+
const core_1 = require("@loopback/core");
|
|
12
8
|
var OAI3Keys;
|
|
13
9
|
(function (OAI3Keys) {
|
|
14
10
|
/**
|
|
15
11
|
* Metadata key used to set or retrieve `@operation` metadata.
|
|
16
12
|
*/
|
|
17
|
-
OAI3Keys.METHODS_KEY =
|
|
13
|
+
OAI3Keys.METHODS_KEY = core_1.MetadataAccessor.create('openapi-v3:methods');
|
|
18
14
|
/**
|
|
19
15
|
* Metadata key used to set or retrieve `param` decorator metadata
|
|
20
16
|
*/
|
|
21
|
-
OAI3Keys.PARAMETERS_KEY =
|
|
17
|
+
OAI3Keys.PARAMETERS_KEY = core_1.MetadataAccessor.create('openapi-v3:parameters');
|
|
22
18
|
/**
|
|
23
19
|
* Metadata key used to set or retrieve `@api` metadata
|
|
24
20
|
*/
|
|
25
|
-
OAI3Keys.CLASS_KEY =
|
|
21
|
+
OAI3Keys.CLASS_KEY = core_1.MetadataAccessor.create('openapi-v3:class');
|
|
26
22
|
/**
|
|
27
23
|
* Metadata key used to set or retrieve a controller spec
|
|
28
24
|
*/
|
|
29
|
-
OAI3Keys.CONTROLLER_SPEC_KEY =
|
|
25
|
+
OAI3Keys.CONTROLLER_SPEC_KEY = core_1.MetadataAccessor.create('openapi-v3:controller-spec');
|
|
30
26
|
/**
|
|
31
27
|
* Metadata key used to set or retrieve `@requestBody` metadata
|
|
32
28
|
*/
|
|
33
|
-
OAI3Keys.REQUEST_BODY_KEY =
|
|
29
|
+
OAI3Keys.REQUEST_BODY_KEY = core_1.MetadataAccessor.create('openapi-v3:request-body');
|
|
34
30
|
})(OAI3Keys = exports.OAI3Keys || (exports.OAI3Keys = {}));
|
|
35
31
|
//# sourceMappingURL=keys.js.map
|
package/dist/keys.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"keys.js","sourceRoot":"","sources":["../src/keys.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE;;AAEhE
|
|
1
|
+
{"version":3,"file":"keys.js","sourceRoot":"","sources":["../src/keys.ts"],"names":[],"mappings":";AAAA,iDAAiD;AACjD,oCAAoC;AACpC,+CAA+C;AAC/C,gEAAgE;;AAEhE,yCAAgD;AAIhD,IAAiB,QAAQ,CAwCxB;AAxCD,WAAiB,QAAQ;IACvB;;OAEG;IACU,oBAAW,GAAG,uBAAgB,CAAC,MAAM,CAGhD,oBAAoB,CAAC,CAAC;IAExB;;OAEG;IACU,uBAAc,GAAG,uBAAgB,CAAC,MAAM,CAGnD,uBAAuB,CAAC,CAAC;IAE3B;;OAEG;IACU,kBAAS,GAAG,uBAAgB,CAAC,MAAM,CAG9C,kBAAkB,CAAC,CAAC;IAEtB;;OAEG;IACU,4BAAmB,GAAG,uBAAgB,CAAC,MAAM,CAGxD,4BAA4B,CAAC,CAAC;IAEhC;;OAEG;IACU,yBAAgB,GAAG,uBAAgB,CAAC,MAAM,CAGrD,yBAAyB,CAAC,CAAC;AAC/B,CAAC,EAxCgB,QAAQ,GAAR,gBAAQ,KAAR,gBAAQ,QAwCxB"}
|
package/package.json
CHANGED
|
@@ -1,26 +1,27 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@loopback/openapi-v3",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.12.0",
|
|
4
4
|
"description": "Processes openapi v3 related metadata",
|
|
5
5
|
"engines": {
|
|
6
6
|
"node": ">=8.9"
|
|
7
7
|
},
|
|
8
8
|
"dependencies": {
|
|
9
|
-
"@loopback/
|
|
10
|
-
"@loopback/repository-json-schema": "^1.
|
|
9
|
+
"@loopback/core": "^1.12.2",
|
|
10
|
+
"@loopback/repository-json-schema": "^1.12.0",
|
|
11
11
|
"debug": "^4.1.1",
|
|
12
|
+
"json-merge-patch": "^0.2.3",
|
|
12
13
|
"lodash": "^4.17.15",
|
|
13
14
|
"openapi3-ts": "^1.3.0"
|
|
14
15
|
},
|
|
15
16
|
"devDependencies": {
|
|
16
|
-
"@loopback/build": "^
|
|
17
|
-
"@loopback/eslint-config": "^
|
|
18
|
-
"@loopback/openapi-spec-builder": "^1.
|
|
19
|
-
"@loopback/repository": "^1.
|
|
20
|
-
"@loopback/testlab": "^1.
|
|
17
|
+
"@loopback/build": "^3.1.0",
|
|
18
|
+
"@loopback/eslint-config": "^5.0.2",
|
|
19
|
+
"@loopback/openapi-spec-builder": "^1.3.0",
|
|
20
|
+
"@loopback/repository": "^1.18.0",
|
|
21
|
+
"@loopback/testlab": "^1.10.2",
|
|
21
22
|
"@types/debug": "^4.1.5",
|
|
22
|
-
"@types/lodash": "^4.14.
|
|
23
|
-
"@types/node": "^10.17.
|
|
23
|
+
"@types/lodash": "^4.14.149",
|
|
24
|
+
"@types/node": "^10.17.13"
|
|
24
25
|
},
|
|
25
26
|
"scripts": {
|
|
26
27
|
"build": "lb-tsc",
|
|
@@ -55,5 +56,5 @@
|
|
|
55
56
|
"url": "https://github.com/strongloop/loopback-next.git",
|
|
56
57
|
"directory": "packages/openapi-v3"
|
|
57
58
|
},
|
|
58
|
-
"gitHead": "
|
|
59
|
+
"gitHead": "d08f135a0d1040edc61497739a8d86a866e4e29a"
|
|
59
60
|
}
|
package/src/controller-spec.ts
CHANGED
|
@@ -3,13 +3,13 @@
|
|
|
3
3
|
// This file is licensed under the MIT License.
|
|
4
4
|
// License text available at https://opensource.org/licenses/MIT
|
|
5
5
|
|
|
6
|
-
import {DecoratorFactory, MetadataInspector} from '@loopback/
|
|
6
|
+
import {DecoratorFactory, MetadataInspector} from '@loopback/core';
|
|
7
7
|
import {
|
|
8
8
|
getJsonSchema,
|
|
9
9
|
getJsonSchemaRef,
|
|
10
10
|
JsonSchemaOptions,
|
|
11
11
|
} from '@loopback/repository-json-schema';
|
|
12
|
-
import
|
|
12
|
+
import {includes} from 'lodash';
|
|
13
13
|
import {resolveSchema} from './generate-schema';
|
|
14
14
|
import {jsonToSchemaObject, SchemaRef} from './json-to-schema';
|
|
15
15
|
import {OAI3Keys} from './keys';
|
|
@@ -81,7 +81,7 @@ function resolveControllerSpec(constructor: Function): ControllerSpec {
|
|
|
81
81
|
MetadataInspector.getAllMethodMetadata<RestEndpoint>(
|
|
82
82
|
OAI3Keys.METHODS_KEY,
|
|
83
83
|
constructor.prototype,
|
|
84
|
-
)
|
|
84
|
+
) ?? {};
|
|
85
85
|
|
|
86
86
|
endpoints = DecoratorFactory.cloneDeep(endpoints);
|
|
87
87
|
for (const op in endpoints) {
|
|
@@ -121,7 +121,7 @@ function resolveControllerSpec(constructor: Function): ControllerSpec {
|
|
|
121
121
|
const responseObject: ResponseObject | ReferenceObject =
|
|
122
122
|
operationSpec.responses[code];
|
|
123
123
|
if (isReferenceObject(responseObject)) continue;
|
|
124
|
-
const content = responseObject.content
|
|
124
|
+
const content = responseObject.content ?? {};
|
|
125
125
|
for (const c in content) {
|
|
126
126
|
debug(' processing response code %s with content-type %', code, c);
|
|
127
127
|
processSchemaExtensions(spec, content[c].schema);
|
|
@@ -178,9 +178,11 @@ function resolveControllerSpec(constructor: Function): ControllerSpec {
|
|
|
178
178
|
|
|
179
179
|
requestBody = requestBodies[0];
|
|
180
180
|
debug(' requestBody for method %s: %j', op, requestBody);
|
|
181
|
+
/* istanbul ignore else */
|
|
181
182
|
if (requestBody) {
|
|
182
183
|
operationSpec.requestBody = requestBody;
|
|
183
184
|
|
|
185
|
+
/* istanbul ignore else */
|
|
184
186
|
const content = requestBody.content || {};
|
|
185
187
|
for (const mediaType in content) {
|
|
186
188
|
processSchemaExtensions(spec, content[mediaType].schema);
|
|
@@ -222,7 +224,7 @@ function resolveControllerSpec(constructor: Function): ControllerSpec {
|
|
|
222
224
|
const paramTypes = opMetadata.parameterTypes;
|
|
223
225
|
|
|
224
226
|
const isComplexType = (ctor: Function) =>
|
|
225
|
-
!
|
|
227
|
+
!includes([String, Number, Boolean, Array, Object], ctor);
|
|
226
228
|
|
|
227
229
|
for (const p of paramTypes) {
|
|
228
230
|
if (isComplexType(p)) {
|
|
@@ -233,6 +235,9 @@ function resolveControllerSpec(constructor: Function): ControllerSpec {
|
|
|
233
235
|
return spec;
|
|
234
236
|
}
|
|
235
237
|
|
|
238
|
+
declare type MixKey = 'allOf' | 'anyOf' | 'oneOf';
|
|
239
|
+
const SCHEMA_ARR_KEYS: MixKey[] = ['allOf', 'anyOf', 'oneOf'];
|
|
240
|
+
|
|
236
241
|
/**
|
|
237
242
|
* Resolve the x-ts-type in the schema object
|
|
238
243
|
* @param spec - Controller spec
|
|
@@ -248,24 +253,51 @@ function processSchemaExtensions(
|
|
|
248
253
|
assignRelatedSchemas(spec, schema.definitions);
|
|
249
254
|
delete schema.definitions;
|
|
250
255
|
|
|
251
|
-
|
|
256
|
+
/**
|
|
257
|
+
* check if we have been provided a `not`
|
|
258
|
+
* `not` is valid in many cases- here we're checking for
|
|
259
|
+
* `not: { schema: {'x-ts-type': SomeModel }}
|
|
260
|
+
*/
|
|
261
|
+
if (schema.not) {
|
|
262
|
+
processSchemaExtensions(spec, schema.not);
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
/**
|
|
266
|
+
* check for schema.allOf, schema.oneOf, schema.anyOf arrays first.
|
|
267
|
+
* You cannot provide BOTH a defnintion AND one of these keywords.
|
|
268
|
+
*/
|
|
269
|
+
/* istanbul ignore else */
|
|
270
|
+
const hasOwn = (prop: string) => schema?.hasOwnProperty(prop);
|
|
271
|
+
|
|
272
|
+
if (SCHEMA_ARR_KEYS.some(k => hasOwn(k))) {
|
|
273
|
+
SCHEMA_ARR_KEYS.forEach((k: MixKey) => {
|
|
274
|
+
/* istanbul ignore else */
|
|
275
|
+
if (schema?.[k] && Array.isArray(schema[k])) {
|
|
276
|
+
schema[k].forEach((r: (SchemaObject | ReferenceObject)[]) => {
|
|
277
|
+
processSchemaExtensions(spec, r);
|
|
278
|
+
});
|
|
279
|
+
}
|
|
280
|
+
});
|
|
281
|
+
} else {
|
|
282
|
+
if (isReferenceObject(schema)) return;
|
|
252
283
|
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
284
|
+
const tsType = schema[TS_TYPE_KEY];
|
|
285
|
+
debug(' %s => %o', TS_TYPE_KEY, tsType);
|
|
286
|
+
if (tsType) {
|
|
287
|
+
schema = resolveSchema(tsType, schema);
|
|
288
|
+
if (schema.$ref) generateOpenAPISchema(spec, tsType);
|
|
258
289
|
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
290
|
+
// We don't want a Function type in the final spec.
|
|
291
|
+
delete schema[TS_TYPE_KEY];
|
|
292
|
+
return;
|
|
293
|
+
}
|
|
294
|
+
if (schema.type === 'array') {
|
|
295
|
+
processSchemaExtensions(spec, schema.items);
|
|
296
|
+
} else if (schema.type === 'object') {
|
|
297
|
+
if (schema.properties) {
|
|
298
|
+
for (const p in schema.properties) {
|
|
299
|
+
processSchemaExtensions(spec, schema.properties[p]);
|
|
300
|
+
}
|
|
269
301
|
}
|
|
270
302
|
}
|
|
271
303
|
}
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
// This file is licensed under the MIT License.
|
|
4
4
|
// License text available at https://opensource.org/licenses/MIT
|
|
5
5
|
|
|
6
|
-
import {ClassDecoratorFactory} from '@loopback/
|
|
6
|
+
import {ClassDecoratorFactory} from '@loopback/core';
|
|
7
7
|
import {ControllerSpec} from '../controller-spec';
|
|
8
8
|
import {OAI3Keys} from '../keys';
|
|
9
9
|
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
// This file is licensed under the MIT License.
|
|
4
4
|
// License text available at https://opensource.org/licenses/MIT
|
|
5
5
|
|
|
6
|
-
import {MethodDecoratorFactory} from '@loopback/
|
|
6
|
+
import {MethodDecoratorFactory} from '@loopback/core';
|
|
7
7
|
import {RestEndpoint} from '../controller-spec';
|
|
8
8
|
import {OAI3Keys} from '../keys';
|
|
9
9
|
import {OperationObject} from '../types';
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
// This file is licensed under the MIT License.
|
|
4
4
|
// License text available at https://opensource.org/licenses/MIT
|
|
5
5
|
|
|
6
|
-
import {MetadataInspector, ParameterDecoratorFactory} from '@loopback/
|
|
6
|
+
import {MetadataInspector, ParameterDecoratorFactory} from '@loopback/core';
|
|
7
7
|
import {resolveSchema} from '../generate-schema';
|
|
8
8
|
import {OAI3Keys} from '../keys';
|
|
9
9
|
import {
|
|
@@ -37,7 +37,7 @@ export function param(paramSpec: ParameterObject) {
|
|
|
37
37
|
paramSpec = paramSpec || {};
|
|
38
38
|
// Get the design time method parameter metadata
|
|
39
39
|
const methodSig = MetadataInspector.getDesignTypeForMethod(target, member);
|
|
40
|
-
const paramTypes =
|
|
40
|
+
const paramTypes = methodSig?.parameterTypes || [];
|
|
41
41
|
|
|
42
42
|
// Map design-time parameter type to the OpenAPI param type
|
|
43
43
|
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
// This file is licensed under the MIT License.
|
|
4
4
|
// License text available at https://opensource.org/licenses/MIT
|
|
5
5
|
|
|
6
|
-
import {MetadataInspector, ParameterDecoratorFactory} from '@loopback/
|
|
7
|
-
import
|
|
6
|
+
import {MetadataInspector, ParameterDecoratorFactory} from '@loopback/core';
|
|
7
|
+
import _ from 'lodash';
|
|
8
8
|
import {inspect} from 'util';
|
|
9
9
|
import {resolveSchema} from '../generate-schema';
|
|
10
10
|
import {OAI3Keys} from '../keys';
|
|
@@ -86,14 +86,14 @@ export function requestBody(requestBodySpec?: Partial<RequestBodyObject>) {
|
|
|
86
86
|
debug(' options: %s', inspect(requestBodySpec, {depth: null}));
|
|
87
87
|
|
|
88
88
|
// Use 'application/json' as default content if `requestBody` is undefined
|
|
89
|
-
requestBodySpec = requestBodySpec
|
|
89
|
+
requestBodySpec = requestBodySpec ?? {content: {}};
|
|
90
90
|
|
|
91
91
|
if (_.isEmpty(requestBodySpec.content))
|
|
92
92
|
requestBodySpec.content = {'application/json': {}};
|
|
93
93
|
|
|
94
94
|
// Get the design time method parameter metadata
|
|
95
95
|
const methodSig = MetadataInspector.getDesignTypeForMethod(target, member);
|
|
96
|
-
const paramTypes =
|
|
96
|
+
const paramTypes = methodSig?.parameterTypes || [];
|
|
97
97
|
|
|
98
98
|
const paramType = paramTypes[index];
|
|
99
99
|
const schema = resolveSchema(paramType);
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
// Copyright IBM Corp. 2019. All Rights Reserved.
|
|
2
|
+
// Node module: @loopback/openapi-v3
|
|
3
|
+
// This file is licensed under the MIT License.
|
|
4
|
+
// License text available at https://opensource.org/licenses/MIT
|
|
5
|
+
|
|
6
|
+
export * from './keys';
|
|
7
|
+
export * from './spec-enhancer.service';
|
|
8
|
+
export * from './types';
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
// Copyright IBM Corp. 2019. All Rights Reserved.
|
|
2
|
+
// Node module: @loopback/openapi-v3
|
|
3
|
+
// This file is licensed under the MIT License.
|
|
4
|
+
// License text available at https://opensource.org/licenses/MIT
|
|
5
|
+
|
|
6
|
+
import {BindingKey} from '@loopback/core';
|
|
7
|
+
import {OASEnhancerService} from './spec-enhancer.service';
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* Strongly-typed binding key for SpecService
|
|
11
|
+
*/
|
|
12
|
+
export const OAS_ENHANCER_SERVICE = BindingKey.create<OASEnhancerService>(
|
|
13
|
+
'services.SpecService',
|
|
14
|
+
);
|