Skip to content

Commit 484473d

Browse files
committed
Added more test, no estimator deprecation warning
1 parent 2de6a00 commit 484473d

File tree

7 files changed

+239
-125
lines changed

7 files changed

+239
-125
lines changed

src/QueryComplexity.ts

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,13 @@ export default class QueryComplexity {
9292
this.context = context;
9393
this.complexity = 0;
9494
this.options = options;
95+
96+
if (!options.estimators) {
97+
console.warn(
98+
'DEPRECATION WARNING: Estimators should be configured in the queryComplexity options.'
99+
);
100+
}
101+
95102
this.estimators = options.estimators || [
96103
legacyEstimator(),
97104
simpleEstimator()
@@ -196,9 +203,11 @@ export default class QueryComplexity {
196203
return false;
197204
});
198205
if (!validScore) {
199-
throw new Error(
200-
`No complexity could be calculated for field ${typeDef.astNode}.${field.name}. ` +
201-
'At least one complexity estimator has to return a complexity score.'
206+
return this.context.reportError(
207+
new GraphQLError(
208+
`No complexity could be calculated for field ${typeDef.astNode}.${field.name}. ` +
209+
'At least one complexity estimator has to return a complexity score.'
210+
)
202211
);
203212
}
204213
break;

src/__tests__/QueryComplexity-test.ts

Lines changed: 105 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -15,58 +15,14 @@ import {expect} from 'chai';
1515
import schema from './fixtures/schema';
1616

1717
import ComplexityVisitor from '../QueryComplexity';
18+
import {
19+
simpleEstimator,
20+
fieldConfigEstimator,
21+
} from '../index';
1822

1923
describe('QueryComplexity analysis', () => {
2024
const typeInfo = new TypeInfo(schema);
2125

22-
it('should consider default scalar cost', () => {
23-
const ast = parse(`
24-
query {
25-
scalar
26-
}
27-
`);
28-
29-
const context = new ValidationContext(schema, ast, typeInfo);
30-
const visitor = new ComplexityVisitor(context, {
31-
maximumComplexity: 100
32-
});
33-
34-
visit(ast, visitWithTypeInfo(typeInfo, visitor));
35-
expect(visitor.complexity).to.equal(1);
36-
});
37-
38-
it('should consider custom scalar cost', () => {
39-
const ast = parse(`
40-
query {
41-
complexScalar
42-
}
43-
`);
44-
45-
const context = new ValidationContext(schema, ast, typeInfo);
46-
const visitor = new ComplexityVisitor(context, {
47-
maximumComplexity: 100
48-
});
49-
50-
visit(ast, visitWithTypeInfo(typeInfo, visitor));
51-
expect(visitor.complexity).to.equal(20);
52-
});
53-
54-
it('should consider variable scalar cost', () => {
55-
const ast = parse(`
56-
query {
57-
variableScalar(count: 100)
58-
}
59-
`);
60-
61-
const context = new ValidationContext(schema, ast, typeInfo);
62-
const visitor = new ComplexityVisitor(context, {
63-
maximumComplexity: 100
64-
});
65-
66-
visit(ast, visitWithTypeInfo(typeInfo, visitor));
67-
expect(visitor.complexity).to.equal(1000);
68-
});
69-
7026
it('should not allow negative cost', () => {
7127
const ast = parse(`
7228
query {
@@ -76,7 +32,10 @@ describe('QueryComplexity analysis', () => {
7632

7733
const context = new ValidationContext(schema, ast, typeInfo);
7834
const visitor = new ComplexityVisitor(context, {
79-
maximumComplexity: 100
35+
maximumComplexity: 100,
36+
estimators: [
37+
simpleEstimator({defaultComplexity: -100})
38+
]
8039
});
8140

8241
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -92,7 +51,13 @@ describe('QueryComplexity analysis', () => {
9251

9352
const context = new ValidationContext(schema, ast, typeInfo);
9453
const visitor = new ComplexityVisitor(context, {
95-
maximumComplexity: 100
54+
maximumComplexity: 100,
55+
estimators: [
56+
fieldConfigEstimator(),
57+
simpleEstimator({
58+
defaultComplexity: 1
59+
})
60+
]
9661
});
9762

9863
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -116,7 +81,13 @@ describe('QueryComplexity analysis', () => {
11681

11782
const context = new ValidationContext(schema, ast, typeInfo);
11883
const visitor = new ComplexityVisitor(context, {
119-
maximumComplexity: 100
84+
maximumComplexity: 100,
85+
estimators: [
86+
fieldConfigEstimator(),
87+
simpleEstimator({
88+
defaultComplexity: 1
89+
})
90+
]
12091
});
12192

12293
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -137,7 +108,13 @@ describe('QueryComplexity analysis', () => {
137108

138109
const context = new ValidationContext(schema, ast, typeInfo);
139110
const visitor = new ComplexityVisitor(context, {
140-
maximumComplexity: 100
111+
maximumComplexity: 100,
112+
estimators: [
113+
fieldConfigEstimator(),
114+
simpleEstimator({
115+
defaultComplexity: 1
116+
})
117+
]
141118
});
142119

143120
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -158,7 +135,13 @@ describe('QueryComplexity analysis', () => {
158135

159136
const context = new ValidationContext(schema, ast, typeInfo);
160137
const visitor = new ComplexityVisitor(context, {
161-
maximumComplexity: 100
138+
maximumComplexity: 100,
139+
estimators: [
140+
fieldConfigEstimator(),
141+
simpleEstimator({
142+
defaultComplexity: 1
143+
})
144+
]
162145
});
163146

164147
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -179,7 +162,13 @@ describe('QueryComplexity analysis', () => {
179162

180163
const context = new ValidationContext(schema, ast, typeInfo);
181164
const visitor = new ComplexityVisitor(context, {
182-
maximumComplexity: 100
165+
maximumComplexity: 100,
166+
estimators: [
167+
fieldConfigEstimator(),
168+
simpleEstimator({
169+
defaultComplexity: 1
170+
})
171+
]
183172
});
184173

185174
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -199,7 +188,13 @@ describe('QueryComplexity analysis', () => {
199188

200189
const context = new ValidationContext(schema, ast, typeInfo);
201190
const visitor = new ComplexityVisitor(context, {
202-
maximumComplexity: 100
191+
maximumComplexity: 100,
192+
estimators: [
193+
fieldConfigEstimator(),
194+
simpleEstimator({
195+
defaultComplexity: 1
196+
})
197+
]
203198
});
204199

205200
visit(ast, visitWithTypeInfo(typeInfo, visitor));
@@ -215,25 +210,77 @@ describe('QueryComplexity analysis', () => {
215210

216211
const context = new ValidationContext(schema, ast, typeInfo);
217212
const visitor = new ComplexityVisitor(context, {
218-
maximumComplexity: 100
213+
maximumComplexity: 100,
214+
estimators: [
215+
fieldConfigEstimator(),
216+
simpleEstimator({
217+
defaultComplexity: 1
218+
})
219+
]
219220
});
220221

221222
visit(ast, visitWithTypeInfo(typeInfo, visitor));
222223
expect(visitor.complexity).to.equal(1);
223224
});
224225

225-
it('should error on a missing non-null argument', () => {
226+
it('should report error on a missing non-null argument', () => {
226227
const ast = parse(`
227228
query {
228229
requiredArgs
229230
}
230231
`);
231232
const context = new ValidationContext(schema, ast, typeInfo);
232233
const visitor = new ComplexityVisitor(context, {
233-
maximumComplexity: 100
234+
maximumComplexity: 100,
235+
estimators: [
236+
fieldConfigEstimator(),
237+
simpleEstimator({
238+
defaultComplexity: 1
239+
})
240+
]
234241
});
235242
visit(ast, visitWithTypeInfo(typeInfo, visitor));
236243
expect(context.getErrors().length).to.equal(1);
237244
expect(context.getErrors()[0].message).to.equal('Argument "count" of required type "Int!" was not provided.');
238245
});
246+
247+
it('should report error when no estimator is configured', () => {
248+
const ast = parse(`
249+
query {
250+
scalar
251+
}
252+
`);
253+
const context = new ValidationContext(schema, ast, typeInfo);
254+
const visitor = new ComplexityVisitor(context, {
255+
maximumComplexity: 100,
256+
estimators: []
257+
});
258+
visit(ast, visitWithTypeInfo(typeInfo, visitor));
259+
expect(context.getErrors().length).to.equal(1);
260+
expect(context.getErrors()[0].message).to.equal(
261+
'No complexity could be calculated for field undefined.scalar. ' +
262+
'At least one complexity estimator has to return a complexity score.'
263+
);
264+
});
265+
266+
it('should report error when no estimator returns value', () => {
267+
const ast = parse(`
268+
query {
269+
scalar
270+
}
271+
`);
272+
const context = new ValidationContext(schema, ast, typeInfo);
273+
const visitor = new ComplexityVisitor(context, {
274+
maximumComplexity: 100,
275+
estimators: [
276+
fieldConfigEstimator()
277+
]
278+
});
279+
visit(ast, visitWithTypeInfo(typeInfo, visitor));
280+
expect(context.getErrors().length).to.equal(1);
281+
expect(context.getErrors()[0].message).to.equal(
282+
'No complexity could be calculated for field undefined.scalar. ' +
283+
'At least one complexity estimator has to return a complexity score.'
284+
);
285+
});
239286
});

src/__tests__/fixtures/schema.ts

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,12 +14,14 @@ import {
1414
GraphQLInterfaceType,
1515
} from 'graphql';
1616

17+
import {ComplexityEstimatorArgs} from '../../QueryComplexity';
18+
1719
const Item: GraphQLObjectType = new GraphQLObjectType({
1820
name: 'Item',
1921
fields: () => ({
2022
variableList: {
2123
type: Item,
22-
complexity: (args: any, childComplexity: number) => childComplexity * (args.count || 10),
24+
complexity: (args: ComplexityEstimatorArgs) => args.childComplexity * (args.args.count || 10),
2325
args: {
2426
count: {
2527
type: GraphQLInt
@@ -30,7 +32,7 @@ const Item: GraphQLObjectType = new GraphQLObjectType({
3032
complexScalar: { type: GraphQLString, complexity: 20 },
3133
variableScalar: {
3234
type: Item,
33-
complexity: (args: {[key: string]: any}) => 10 * (args.count || 10),
35+
complexity: (args: ComplexityEstimatorArgs) => 10 * (args.args.count || 10),
3436
args: {
3537
count: {
3638
type: GraphQLInt
@@ -87,7 +89,7 @@ const Query = new GraphQLObjectType({
8789
name: { type: GraphQLString },
8890
variableList: {
8991
type: Item,
90-
complexity: (args: {[key: string]: any}, childComplexity: number) => childComplexity * (args.count || 10),
92+
complexity: (args: ComplexityEstimatorArgs) => args.childComplexity * (args.args.count || 10),
9193
args: {
9294
count: {
9395
type: GraphQLInt
@@ -101,7 +103,7 @@ const Query = new GraphQLObjectType({
101103
union: { type: Union },
102104
variableScalar: {
103105
type: Item,
104-
complexity: (args: {[key: string]: any}) => 10 * (args.count || 10),
106+
complexity: (args: ComplexityEstimatorArgs) => 10 * (args.args.count || 10),
105107
args: {
106108
count: {
107109
type: GraphQLInt

src/estimators/fieldConfig/__tests__/fieldConfigEstimator-test.ts

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -255,7 +255,13 @@ describe('fieldConfig estimator', () => {
255255

256256
const context = new ValidationContext(schema, ast, typeInfo);
257257
const visitor = new ComplexityVisitor(context, {
258-
maximumComplexity: 100
258+
maximumComplexity: 100,
259+
estimators: [
260+
fieldConfigEstimator(),
261+
simpleEstimator({
262+
defaultComplexity: 1
263+
})
264+
]
259265
});
260266

261267
visit(ast, visitWithTypeInfo(typeInfo, visitor));

0 commit comments

Comments
 (0)