Skip to content

Commit

Permalink
Add fieldExtensionsEstimator, deprecate fieldConfigEstimator #19
Browse files Browse the repository at this point in the history
  • Loading branch information
ivome committed Sep 23, 2019
1 parent 433b176 commit 0ef07a4
Show file tree
Hide file tree
Showing 8 changed files with 594 additions and 7 deletions.
6 changes: 4 additions & 2 deletions README.md
Expand Up @@ -74,9 +74,11 @@ or write your own:
last estimator in the chain for a default value.
* **[`directiveEstimator`](src/estimators/directive/README.md):** Set the complexity via a directive in your
schema definition (for example via GraphQL SDL)
* **[`fieldConfigEstimator`](src/estimators/fieldConfig/README.md):** The field config estimator lets you set a numeric value or a custom estimator
* **[`fieldExtensionsEstimator`](src/estimators/fieldExtensions/README.md):** The field extensions estimator lets you set a numeric value or a custom estimator
function in the field config extensions of your schema.
* **[`fieldConfigEstimator`](src/estimators/fieldConfig/README.md):** (DEPRECATED) The field config estimator lets you set a numeric value or a custom estimator
function in the field config of your schema.
* **[`legacyEstimator`](src/estimators/legacy/README.md):** The legacy estimator implements the logic of previous versions. Can be used
* **[`legacyEstimator`](src/estimators/legacy/README.md):** (DEPRECATED) The legacy estimator implements the logic of previous versions. Can be used
to gradually migrate your codebase to new estimators.
* PRs welcome...

Expand Down
7 changes: 7 additions & 0 deletions src/estimators/fieldConfig/index.ts
@@ -1,6 +1,13 @@
import {ComplexityEstimator, ComplexityEstimatorArgs} from '../../QueryComplexity';

/**
* @deprecated Use fieldExtensionsEstimator instead
*/
export default function (): ComplexityEstimator {
console.warn(
'DEPRECATION WARNING: fieldConfigEstimator is deprecated. Use fieldExtensionsEstimator instead'
);

return (args: ComplexityEstimatorArgs) => {
// Calculate complexity score
if (typeof args.field.complexity === 'number') {
Expand Down
97 changes: 97 additions & 0 deletions src/estimators/fieldExtensions/README.md
@@ -0,0 +1,97 @@
# Field Extensions Estimator

The `fieldExtensionsEstimator` lets you define a numeric value or a custom estimator
in the field config extensions of your GraphQL schema. If no complexity is set in the field config,
the estimator does not return any value and the next estimator in the chain is executed.

## Usage

```typescript
import queryComplexity, {
fieldExtensionsEstimator,
simpleEstimator
} from 'graphql-query-complexity';

const rule = queryComplexity({
estimators: [
fieldExtensionsEstimator(),

// We use the simpleEstimator as fallback so we only need to
// define the complexity for non 1 values (this is not required...)
simpleEstimator({defaultComplexity: 1})
]
// ... other config
});
```

You can set a custom complexity as a numeric value in the field config:

```javascript
const Post = new GraphQLObjectType({
name: 'Post',
fields: () => ({
title: { type: GraphQLString },
text: {
type: GraphQLString,
extensions: {
complexity: 5
},
},
}),
});
```

**Example Query:**

```graphql
query {
posts(count: 10) {
title
text
}
}
```

This query would result in a complexity of 7.
5 for the `text` field and 1 for each of the other fields.

You can also pass an estimator in the field config to determine a custom complexity.
This function will provide the complexity of the child nodes as well as the field input arguments.

The function signature is the same as for the main estimator which lets you reuse estimators:

```typescript
type ComplexityEstimatorArgs = {
type: GraphQLCompositeType,
field: GraphQLField<any, any>,
args: {[key: string]: any},
childComplexity: number
}

type ComplexityEstimator = (options: ComplexityEstimatorArgs) => number | void;
```

That way you can make a more realistic estimation of individual field complexity values:

```javascript
const Query = new GraphQLObjectType({
name: 'Query',
fields: () => ({
posts: {
type: new GraphQLList(Post),
args: {
count: {
type: GraphQLInt,
defaultValue: 10
}
},
extensions: {
complexity: ({args, childComplexity}) => childComplexity * args.count,
},
},
}),
});
```

This would result in a complexity of 60 since the `childComplexity` of posts (`text` 5, `title` 1) is multiplied by the
number of posts (`args.count`).

0 comments on commit 0ef07a4

Please sign in to comment.