Skip to content

Ignore GraphQLResolveInfo if fields option is defined in in-context sdk #584

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Jun 15, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions packages/handlers/grpc/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,7 @@ const handler: MeshHandlerLibrary<YamlConfig.GrpcHandler> = {
const client = new ServiceClient(config.endpoint, creds);
const methods = nested.methods;
await Promise.all(
Object.keys(methods).map(async methodName => {
Object.keys(methods).map(async (methodName: string) => {
const method = methods[methodName];
let rootFieldName = methodName;
if (name !== config.serviceName) {
Expand Down Expand Up @@ -295,7 +295,7 @@ const handler: MeshHandlerLibrary<YamlConfig.GrpcHandler> = {
});
} else if ('nested' in nested) {
await Promise.all(
Object.keys(nested.nested).map(async key => {
Object.keys(nested.nested).map(async (key: string) => {
const currentNested = nested.nested[key];
await visit(currentNested, key, currentPath ? currentPath + '.' + name : name);
})
Expand Down
8 changes: 4 additions & 4 deletions packages/handlers/mysql/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ const handler: MeshHandlerLibrary<YamlConfig.MySQLHandler> = {
},
extensions: tableForeign,
resolve: async (root, args, { mysqlConnection }, info) => {
const fieldMap = graphqlFields(info);
const fieldMap: Record<string, any> = graphqlFields(info);
const fields = Object.keys(fieldMap).filter(
fieldName => Object.keys(fieldMap[fieldName]).length === 0
);
Expand Down Expand Up @@ -285,7 +285,7 @@ const handler: MeshHandlerLibrary<YamlConfig.MySQLHandler> = {
},
},
resolve: async (root, args, { mysqlConnection }, info) => {
const fieldMap = graphqlFields(info);
const fieldMap: Record<string, any> = graphqlFields(info);
const fields: string[] = [];
await Promise.all(
Object.keys(fieldMap).map(async fieldName => {
Expand Down Expand Up @@ -319,7 +319,7 @@ const handler: MeshHandlerLibrary<YamlConfig.MySQLHandler> = {
},
resolve: async (root, args, { mysqlConnection }, info) => {
const { recordId } = await mysqlConnection.insert(args);
const fieldMap = graphqlFields(info);
const fieldMap: Record<string, any> = graphqlFields(info);
const fields = Object.keys(fieldMap).filter(fieldName => Object.keys(fieldMap[fieldName]).length === 0);
const where: any = {};
await Promise.all(
Expand Down Expand Up @@ -351,7 +351,7 @@ const handler: MeshHandlerLibrary<YamlConfig.MySQLHandler> = {
},
args.where
);
const fieldMap = graphqlFields(info);
const fieldMap: Record<string, any> = graphqlFields(info);
const fields = Object.keys(fieldMap).filter(fieldName => Object.keys(fieldMap[fieldName]).length === 0);
const result = await mysqlConnection.select(tableName, fields, args.where, {});
return result[0];
Expand Down
2 changes: 1 addition & 1 deletion packages/handlers/odata/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@ const handler: MeshHandlerLibrary<YamlConfig.ODataHandler> = {
}

function prepareSearchParams(fragment: ResolveTree, schema: GraphQLSchema) {
const fragmentTypeNames = Object.keys(fragment.fieldsByTypeName);
const fragmentTypeNames = Object.keys(fragment.fieldsByTypeName) as string[];
const returnType = schema.getType(fragmentTypeNames[0]);
const { args, fields } = simplifyParsedResolveInfoFragmentWithType(fragment, returnType);
const searchParams = new URLSearchParams();
Expand Down
4 changes: 2 additions & 2 deletions packages/handlers/openapi/src/openapi-to-graphql/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -362,11 +362,11 @@ async function translateOpenAPIToGraphQL(
queryFields = sortObject(queryFields);
mutationFields = sortObject(mutationFields);
authQueryFields = sortObject(authQueryFields);
Object.keys(authQueryFields).forEach(key => {
Object.keys(authQueryFields).forEach((key: string) => {
authQueryFields[key] = sortObject(authQueryFields[key]);
});
authMutationFields = sortObject(authMutationFields);
Object.keys(authMutationFields).forEach(key => {
Object.keys(authMutationFields).forEach((key: string) => {
authMutationFields[key] = sortObject(authMutationFields[key]);
});

Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
/* eslint-disable no-use-before-define */
// Copyright IBM Corp. 2018. All Rights Reserved.
// Node module: openapi-to-graphql
// This file is licensed under the MIT License.
Expand Down Expand Up @@ -556,7 +557,7 @@ export function getRequestBodyObject(
};
} else {
// Pick first (random) content type
const randomContentType = Object.keys(content)[0];
const randomContentType = Object.keys(content)[0].toString();

return {
payloadContentType: randomContentType,
Expand Down Expand Up @@ -670,7 +671,7 @@ export function getResponseObject(
};
} else {
// Pick first (random) content type
const randomContentType = Object.keys(content)[0];
const randomContentType = Object.keys(content)[0].toString();

return {
responseContentType: randomContentType,
Expand Down Expand Up @@ -772,7 +773,7 @@ export function getResponseStatusCode(path: string, method: string, oas: Oas3, d
const endpoint: OperationObject = oas.paths[path][method];

if (typeof endpoint.responses === 'object') {
const codes = Object.keys(endpoint.responses);
const codes = Object.keys(endpoint.responses) as string[];
const successCodes = codes.filter(code => {
return SUCCESS_STATUS_RX.test(code) || code === 'default';
});
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -424,7 +424,7 @@ export function createDataDef(

const saneLinks = {};
if (typeof links === 'object') {
Object.keys(links).forEach(linkKey => {
Object.keys(links).forEach((linkKey: string) => {
saneLinks[
Oas3Tools.sanitize(
linkKey,
Expand Down Expand Up @@ -1088,7 +1088,7 @@ function createDataDefFromAnyOf({

// Check if any member schema has conflicting properties
anyOfData.allProperties.forEach(properties => {
Object.keys(properties).forEach(propertyName => {
Object.keys(properties).forEach((propertyName: string) => {
if (
!incompatibleProperties.has(propertyName) && // Has not been already identified as a problematic property
typeof allProperties[propertyName] === 'object' &&
Expand All @@ -1115,7 +1115,7 @@ function createDataDefFromAnyOf({
}

anyOfData.allProperties.forEach(properties => {
Object.keys(properties).forEach(propertyName => {
Object.keys(properties).forEach((propertyName: string) => {
if (!incompatibleProperties.has(propertyName)) {
// Dereferenced by processing anyOfData
const propertySchema = properties[propertyName] as SchemaObject;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
/* eslint-disable @typescript-eslint/ban-ts-comment */
/* eslint-disable no-dupe-else-if */
/* eslint-disable no-case-declarations */
// Copyright IBM Corp. 2018. All Rights Reserved.
Expand Down Expand Up @@ -287,7 +288,7 @@ function createOrReuseUnion({ def, operation, data, iteration }: CreateOrReuseCo
description,
types,
resolveType: source => {
const properties = Object.keys(source);
const properties = Object.keys(source) as string[];

// Remove custom _openAPIToGraphQL property used to pass data
const otgIndex = properties.indexOf('_openAPIToGraphQL');
Expand All @@ -307,7 +308,7 @@ function createOrReuseUnion({ def, operation, data, iteration }: CreateOrReuseCo
* of the fields specified in the OAS
*/
return types.find(type => {
const typeFields = Object.keys(type.getFields());
const typeFields = Object.keys(type.getFields()) as string[];

if (properties.length <= typeFields.length) {
for (let i = 0; i < properties.length; i++) {
Expand Down
2 changes: 1 addition & 1 deletion packages/handlers/openapi/src/openapi-to-graphql/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -110,5 +110,5 @@ export function sortObject(o: any) {
export function getCommonPropertyNames(object1: any, object2: any): string[] {
return Object.keys(object1).filter(propertyName => {
return propertyName in object2;
});
}) as string[];
}
51 changes: 40 additions & 11 deletions packages/runtime/src/get-mesh.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,14 @@
/* eslint-disable no-unused-expressions */
import { GraphQLSchema, execute, DocumentNode, GraphQLError } from 'graphql';
import { GraphQLOperation, ExecuteMeshFn, GetMeshOptions, Requester, ResolvedTransform } from './types';
import { GraphQLSchema, execute, DocumentNode, GraphQLError, subscribe } from 'graphql';
import {
GraphQLOperation,
ExecuteMeshFn,
GetMeshOptions,
Requester,
ResolvedTransform,
SubscribeMeshFn,
MeshContext,
} from './types';
import { ensureDocumentNode } from './utils';
import { Hooks, KeyValueCache, RawSourceOutput, MeshTransform } from '@graphql-mesh/types';

Expand All @@ -23,7 +31,7 @@ export function groupTransforms({
}) {
const wrapTransforms: MeshTransform[] = [];
const noWrapTransforms: MeshTransform[] = [];
transforms?.forEach(({ transformCtor: TransformCtor, config }) => {
transforms?.forEach(({ transformLibrary: TransformCtor, config }) => {
const transform = new TransformCtor({
apiName,
config,
Expand All @@ -43,6 +51,7 @@ export async function getMesh(
options: GetMeshOptions
): Promise<{
execute: ExecuteMeshFn;
subscribe: SubscribeMeshFn;
schema: GraphQLSchema;
rawSources: RawSourceOutput[];
sdkRequester: Requester;
Expand Down Expand Up @@ -101,7 +110,7 @@ export async function getMesh(
typeDefs: options.additionalTypeDefs,
resolvers: options.additionalResolvers,
transforms: options.transforms.map(
({ transformCtor: TransformCtor, config }) =>
({ transformLibrary: TransformCtor, config }) =>
new TransformCtor({
config,
cache,
Expand All @@ -114,9 +123,9 @@ export async function getMesh(

unifiedSchema = applyResolversHooksToSchema(unifiedSchema, hooks);

async function buildMeshContext(initialContextValue?: any) {
const context: Record<string, any> = {
...(initialContextValue || {}),
async function buildMeshContext<TAdditionalContext>(initialContextValue?: TAdditionalContext) {
const context: MeshContext & TAdditionalContext = {
...initialContextValue,
[MESH_CONTEXT_SYMBOL]: true,
};

Expand All @@ -131,10 +140,12 @@ export async function getMesh(
}
}

context[rawSource.name] = {
rawSource,
[MESH_API_CONTEXT_SYMBOL]: true,
};
Object.assign(context, {
[rawSource.name]: {
rawSource,
[MESH_API_CONTEXT_SYMBOL]: true,
},
});
})
);

Expand All @@ -158,6 +169,23 @@ export async function getMesh(
});
}

async function meshSubscribe<TVariables = any, TContext = any, TRootValue = any>(
document: GraphQLOperation,
variables?: TVariables,
context?: TContext,
rootValue?: TRootValue
) {
const contextValue = await buildMeshContext(context);

return subscribe({
document: ensureDocumentNode(document),
contextValue,
rootValue: rootValue || {},
variableValues: variables || {},
schema: unifiedSchema,
});
}

const localRequester: Requester = async <R, V>(document: DocumentNode, variables: V, context: any) => {
const executionResult = await meshExecute<V>(document, variables, context);

Expand All @@ -175,6 +203,7 @@ export async function getMesh(

return {
execute: meshExecute,
subscribe: meshSubscribe,
schema: unifiedSchema,
contextBuilder: buildMeshContext,
rawSources,
Expand Down
67 changes: 37 additions & 30 deletions packages/runtime/src/parse-config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,12 @@ import {
import { YamlConfig, getJsonSchema } from '@graphql-mesh/types';
import Ajv from 'ajv';

declare global {
interface ObjectConstructor {
keys<T>(obj: T): Array<keyof T>;
}
}

export type ConfigProcessOptions = {
dir?: string;
ignoreAdditionalResolvers?: boolean;
Expand Down Expand Up @@ -42,43 +48,44 @@ export async function processConfig(config: YamlConfig.Config, options?: ConfigP

const [sources, transforms, additionalTypeDefs, additionalResolvers, cache, merger] = await Promise.all([
Promise.all(
config.sources.map<Promise<MeshResolvedSource>>(
async (source): Promise<MeshResolvedSource> => {
const handlerName = Object.keys(source.handler)[0] as keyof YamlConfig.Handler;
const handlerConfig = source.handler[handlerName];
const [handlerLibrary, transforms] = await Promise.all([
getHandler(handlerName),
Promise.all(
(source.transforms || []).map(async t => {
const transformName = Object.keys(t)[0] as keyof YamlConfig.Transform;
const transformConfig = t[transformName];
const transformCtor = await getPackage<ResolvedTransform['transformCtor']>(transformName, 'transform');

return {
config: transformConfig,
transformCtor,
};
})
),
]);

return {
name: source.name,
handlerConfig,
handlerLibrary,
transforms,
};
}
)
config.sources.map<Promise<MeshResolvedSource>>(async source => {
const handlerName = Object.keys(source.handler)[0];
const handlerConfig = source.handler[handlerName];
const [handlerLibrary, transforms] = await Promise.all([
getHandler(handlerName),
Promise.all(
(source.transforms || []).map(async t => {
const transformName: keyof YamlConfig.Transform = Object.keys(t)[0];
const transformConfig = t[transformName];
const transformLibrary = await getPackage<ResolvedTransform['transformLibrary']>(
transformName,
'transform'
);

return {
config: transformConfig,
transformLibrary,
};
})
),
]);

return {
name: source.name,
handlerConfig,
handlerLibrary,
transforms,
};
})
),
Promise.all(
config.transforms?.map(async t => {
const transformName = Object.keys(t)[0] as keyof YamlConfig.Transform;
const transformConfig = t[transformName];

const TransformLibrary = await getPackage<ResolvedTransform['transformLibrary']>(transformName, 'transform');
return {
config: transformConfig,
transformCtor: await getPackage<ResolvedTransform['transformCtor']>(transformName, 'transform'),
transformLibrary: TransformLibrary,
};
}) || []
),
Expand Down
10 changes: 8 additions & 2 deletions packages/runtime/src/resolvers-hooks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,15 +41,21 @@ function createProxyInfo({
parentType: GraphQLObjectType;
field: GraphQLField<any, any>;
root: any;
args: any;
args: Record<string, any>;
depthLimit?: number;
selectedFields?: SelectedFields;
selectionSet?: string | DocumentNode;
info: GraphQLResolveInfo;
}): any {
const actualReturnType = 'ofType' in info.returnType ? info.returnType.ofType : info.returnType;
const returnType = 'ofType' in field.type ? field.type.ofType : field.type;
if ('name' in actualReturnType && 'name' in returnType && actualReturnType.name === returnType.name) {
if (
!selectedFields &&
!selectionSet &&
'name' in actualReturnType &&
'name' in returnType &&
actualReturnType.name === returnType.name
) {
return {
...info,
returnType,
Expand Down
Loading