1 | "use strict";
|
2 | Object.defineProperty(exports, "__esModule", { value: true });
|
3 | const errors_1 = require("../errors");
|
4 | const utils_1 = require("./utils");
|
5 | class MetadataStorage {
|
6 | constructor() {
|
7 | this.queries = [];
|
8 | this.mutations = [];
|
9 | this.subscriptions = [];
|
10 | this.fieldResolvers = [];
|
11 | this.objectTypes = [];
|
12 | this.inputTypes = [];
|
13 | this.argumentTypes = [];
|
14 | this.interfaceTypes = [];
|
15 | this.authorizedFields = [];
|
16 | this.enums = [];
|
17 | this.unions = [];
|
18 | this.middlewares = [];
|
19 | this.resolverClasses = [];
|
20 | this.fields = [];
|
21 | this.params = [];
|
22 | utils_1.ensureReflectMetadataExists();
|
23 | }
|
24 | collectQueryHandlerMetadata(definition) {
|
25 | this.queries.push(definition);
|
26 | }
|
27 | collectMutationHandlerMetadata(definition) {
|
28 | this.mutations.push(definition);
|
29 | }
|
30 | collectSubscriptionHandlerMetadata(definition) {
|
31 | this.subscriptions.push(definition);
|
32 | }
|
33 | collectFieldResolverMetadata(definition) {
|
34 | this.fieldResolvers.push(definition);
|
35 | }
|
36 | collectObjectMetadata(definition) {
|
37 | this.objectTypes.push(definition);
|
38 | }
|
39 | collectInputMetadata(definition) {
|
40 | this.inputTypes.push(definition);
|
41 | }
|
42 | collectArgsMetadata(definition) {
|
43 | this.argumentTypes.push(definition);
|
44 | }
|
45 | collectInterfaceMetadata(definition) {
|
46 | this.interfaceTypes.push(definition);
|
47 | }
|
48 | collectAuthorizedFieldMetadata(definition) {
|
49 | this.authorizedFields.push(definition);
|
50 | }
|
51 | collectEnumMetadata(definition) {
|
52 | this.enums.push(definition);
|
53 | }
|
54 | collectUnionMetadata(definition) {
|
55 | const unionSymbol = Symbol(definition.name);
|
56 | this.unions.push(Object.assign({}, definition, { symbol: unionSymbol }));
|
57 | return unionSymbol;
|
58 | }
|
59 | collectMiddlewareMetadata(definition) {
|
60 | this.middlewares.push(definition);
|
61 | }
|
62 | collectResolverClassMetadata(definition) {
|
63 | this.resolverClasses.push(definition);
|
64 | }
|
65 | collectClassFieldMetadata(definition) {
|
66 | this.fields.push(definition);
|
67 | }
|
68 | collectHandlerParamMetadata(definition) {
|
69 | this.params.push(definition);
|
70 | }
|
71 | build() {
|
72 |
|
73 | this.buildClassMetadata(this.objectTypes);
|
74 | this.buildClassMetadata(this.inputTypes);
|
75 | this.buildClassMetadata(this.argumentTypes);
|
76 | this.buildClassMetadata(this.interfaceTypes);
|
77 | this.buildFieldResolverMetadata(this.fieldResolvers);
|
78 | this.buildResolversMetadata(this.queries);
|
79 | this.buildResolversMetadata(this.mutations);
|
80 | this.buildResolversMetadata(this.subscriptions);
|
81 | this.buildExtendedResolversMetadata();
|
82 | }
|
83 | clear() {
|
84 | this.queries = [];
|
85 | this.mutations = [];
|
86 | this.subscriptions = [];
|
87 | this.fieldResolvers = [];
|
88 | this.objectTypes = [];
|
89 | this.inputTypes = [];
|
90 | this.argumentTypes = [];
|
91 | this.interfaceTypes = [];
|
92 | this.authorizedFields = [];
|
93 | this.enums = [];
|
94 | this.unions = [];
|
95 | this.middlewares = [];
|
96 | this.resolverClasses = [];
|
97 | this.fields = [];
|
98 | this.params = [];
|
99 | }
|
100 | buildClassMetadata(definitions) {
|
101 | definitions.forEach(def => {
|
102 | const fields = this.fields.filter(field => field.target === def.target);
|
103 | fields.forEach(field => {
|
104 | field.roles = this.findFieldRoles(field.target, field.name);
|
105 | field.params = this.params.filter(param => param.target === field.target && field.name === param.methodName);
|
106 | field.middlewares = utils_1.mapMiddlewareMetadataToArray(this.middlewares.filter(middleware => middleware.target === field.target && middleware.fieldName === field.name));
|
107 | });
|
108 | def.fields = fields;
|
109 | });
|
110 | }
|
111 | buildResolversMetadata(definitions) {
|
112 | definitions.forEach(def => {
|
113 | const resolverClassMetadata = this.resolverClasses.find(resolver => resolver.target === def.target);
|
114 | def.resolverClassMetadata = resolverClassMetadata;
|
115 | def.params = this.params.filter(param => param.target === def.target && def.methodName === param.methodName);
|
116 | def.roles = this.findFieldRoles(def.target, def.methodName);
|
117 | def.middlewares = utils_1.mapMiddlewareMetadataToArray(this.middlewares.filter(middleware => middleware.target === def.target && def.methodName === middleware.fieldName));
|
118 | });
|
119 | }
|
120 | buildFieldResolverMetadata(definitions) {
|
121 | this.buildResolversMetadata(definitions);
|
122 | definitions.forEach(def => {
|
123 | def.roles = this.findFieldRoles(def.target, def.methodName);
|
124 | def.getObjectType =
|
125 | def.kind === "external"
|
126 | ? this.resolverClasses.find(resolver => resolver.target === def.target).getObjectType
|
127 | : () => def.target;
|
128 | if (def.kind === "external") {
|
129 | const objectTypeCls = this.resolverClasses.find(resolver => resolver.target === def.target)
|
130 | .getObjectType();
|
131 | const objectType = this.objectTypes.find(objTypeDef => objTypeDef.target === objectTypeCls);
|
132 | const objectTypeField = objectType.fields.find(fieldDef => fieldDef.name === def.methodName);
|
133 | if (!objectTypeField) {
|
134 | if (!def.getType || !def.typeOptions) {
|
135 | throw new errors_1.NoExplicitTypeError(def.target.name, def.methodName);
|
136 | }
|
137 | const fieldMetadata = {
|
138 | name: def.methodName,
|
139 | schemaName: def.schemaName,
|
140 | getType: def.getType,
|
141 | target: objectTypeCls,
|
142 | typeOptions: def.typeOptions,
|
143 | deprecationReason: def.deprecationReason,
|
144 | description: def.description,
|
145 | complexity: def.complexity,
|
146 | roles: def.roles,
|
147 | middlewares: def.middlewares,
|
148 | params: def.params,
|
149 | };
|
150 | this.collectClassFieldMetadata(fieldMetadata);
|
151 | objectType.fields.push(fieldMetadata);
|
152 | }
|
153 | else {
|
154 | objectTypeField.complexity = def.complexity;
|
155 | if (objectTypeField.params.length === 0) {
|
156 | objectTypeField.params = def.params;
|
157 | }
|
158 | if (def.roles) {
|
159 | objectTypeField.roles = def.roles;
|
160 | }
|
161 | else if (objectTypeField.roles) {
|
162 | def.roles = objectTypeField.roles;
|
163 | }
|
164 | }
|
165 | }
|
166 | });
|
167 | }
|
168 | buildExtendedResolversMetadata() {
|
169 | this.resolverClasses.forEach(def => {
|
170 | const target = def.target;
|
171 | let superResolver = Object.getPrototypeOf(target);
|
172 |
|
173 | while (superResolver.prototype) {
|
174 | const superResolverMetadata = this.resolverClasses.find(it => it.target === superResolver);
|
175 | if (superResolverMetadata) {
|
176 | this.queries.unshift(...utils_1.mapSuperResolverHandlers(this.queries, superResolver, def));
|
177 | this.mutations.unshift(...utils_1.mapSuperResolverHandlers(this.mutations, superResolver, def));
|
178 | this.subscriptions.unshift(...utils_1.mapSuperResolverHandlers(this.subscriptions, superResolver, def));
|
179 | this.fieldResolvers.unshift(...utils_1.mapSuperFieldResolverHandlers(this.fieldResolvers, superResolver, def));
|
180 | }
|
181 | superResolver = Object.getPrototypeOf(superResolver);
|
182 | }
|
183 | });
|
184 | }
|
185 | findFieldRoles(target, fieldName) {
|
186 | const authorizedField = this.authorizedFields.find(authField => authField.target === target && authField.fieldName === fieldName);
|
187 | if (!authorizedField) {
|
188 | return;
|
189 | }
|
190 | return authorizedField.roles;
|
191 | }
|
192 | }
|
193 | exports.MetadataStorage = MetadataStorage;
|