From 3897673681b30425debc329ad5d5bb442b3838fe Mon Sep 17 00:00:00 2001 From: doug-martin Date: Thu, 23 Jul 2020 18:17:27 -0500 Subject: [PATCH] fix(graphql,aggregations): Exclude __typename in aggregations --- packages/query-graphql/package.json | 4 +- .../aggregate-query-param.decorator.ts | 38 ++++++++----------- 2 files changed, 18 insertions(+), 24 deletions(-) diff --git a/packages/query-graphql/package.json b/packages/query-graphql/package.json index c7e9edc99..b1cfd5b9f 100644 --- a/packages/query-graphql/package.json +++ b/packages/query-graphql/package.json @@ -42,7 +42,8 @@ "lodash.omit": "^4.5.0", "lower-case-first": "^2.0.1", "pluralize": "^8.0.0", - "upper-case-first": "^2.0.1" + "upper-case-first": "^2.0.1", + "graphql-fields": "^2.0.3" }, "peerDependencies": { "@nestjs/common": "^7.0.0", @@ -63,6 +64,7 @@ "@types/lodash.omit": "4.5.6", "@types/node-fetch": "2.5.7", "@types/pluralize": "0.0.29", + "@types/graphql-fields": "1.3.3", "class-transformer": "0.2.3", "class-validator": "0.12.2", "dataloader": "2.0.0", diff --git a/packages/query-graphql/src/decorators/aggregate-query-param.decorator.ts b/packages/query-graphql/src/decorators/aggregate-query-param.decorator.ts index fdbd15f9c..71f5962f0 100644 --- a/packages/query-graphql/src/decorators/aggregate-query-param.decorator.ts +++ b/packages/query-graphql/src/decorators/aggregate-query-param.decorator.ts @@ -1,30 +1,22 @@ import { AggregateQuery } from '@nestjs-query/core'; -import { GraphQLResolveInfo, SelectionNode, FieldNode, Kind } from 'graphql'; +import { GraphQLResolveInfo } from 'graphql'; import { GqlExecutionContext } from '@nestjs/graphql'; import { createParamDecorator, ExecutionContext } from '@nestjs/common'; +import graphqlFields from 'graphql-fields'; -const isFieldNode = (node: SelectionNode): node is FieldNode => { - return node.kind === Kind.FIELD; -}; - +const EXCLUDED_FIELDS = ['__typename']; +const QUERY_OPERATORS: (keyof AggregateQuery)[] = ['count', 'avg', 'sum', 'min', 'max']; export const AggregateQueryParam = createParamDecorator((data: unknown, ctx: ExecutionContext) => { const info = GqlExecutionContext.create(ctx).getInfo(); - const query = info.fieldNodes.map(({ selectionSet }) => { - return selectionSet?.selections.reduce((aggQuery, selection) => { - if (isFieldNode(selection)) { - const aggType = selection.name.value; - const fields = selection.selectionSet?.selections - .map((s) => { - if (isFieldNode(s)) { - return s.name.value; - } - return undefined; - }) - .filter((f) => !!f); - return { ...aggQuery, [aggType]: fields }; - } - return aggQuery; - }, {} as AggregateQuery); - })[0]; - return query || {}; + const fields = graphqlFields(info, {}, { excludedFields: EXCLUDED_FIELDS }) as Record< + keyof AggregateQuery, + Record + >; + return QUERY_OPERATORS.filter((operator) => !!fields[operator]).reduce((query, operator) => { + const queryFields = Object.keys(fields[operator]) as (keyof DTO)[]; + if (queryFields && queryFields.length) { + return { ...query, [operator]: queryFields }; + } + return query; + }, {} as AggregateQuery); });