All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.infomaximum.cluster.graphql.executor.builder.GraphQLExecutorBuilder Maven / Gradle / Ivy

The newest version!
package com.infomaximum.cluster.graphql.executor.builder;

import com.infomaximum.cluster.graphql.exception.GraphQLExecutorException;
import com.infomaximum.cluster.graphql.executor.GraphQLExecutor;
import com.infomaximum.cluster.graphql.executor.GraphQLExecutorImpl;
import com.infomaximum.cluster.graphql.executor.GraphQLExecutorPrepareImpl;
import com.infomaximum.cluster.graphql.executor.component.GraphQLComponentExecutor;
import com.infomaximum.cluster.graphql.executor.subscription.GraphQLSubscribeEngineImpl;
import com.infomaximum.cluster.graphql.remote.graphql.executor.RControllerGraphQLExecutor;
import com.infomaximum.cluster.graphql.schema.GraphQLSchemaType;
import com.infomaximum.cluster.graphql.schema.build.MergeGraphQLTypeOutObject;
import com.infomaximum.cluster.graphql.schema.build.MergeGraphQLTypeOutObjectInterface;
import com.infomaximum.cluster.graphql.schema.build.graphqltype.TypeGraphQLFieldConfigurationBuilder;
import com.infomaximum.cluster.graphql.schema.datafetcher.ComponentDataFetcher;
import com.infomaximum.cluster.graphql.schema.datafetcher.ExtPropertyDataFetcher;
import com.infomaximum.cluster.graphql.schema.scalartype.GraphQLTypeScalar;
import com.infomaximum.cluster.graphql.schema.struct.RGraphQLType;
import com.infomaximum.cluster.graphql.schema.struct.RGraphQLTypeEnum;
import com.infomaximum.cluster.graphql.schema.struct.in.RGraphQLInputObjectTypeField;
import com.infomaximum.cluster.graphql.schema.struct.in.RGraphQLTypeInObject;
import com.infomaximum.cluster.graphql.schema.struct.out.RGraphQLObjectTypeField;
import com.infomaximum.cluster.graphql.schema.struct.out.RGraphQLObjectTypeMethodArgument;
import com.infomaximum.cluster.graphql.schema.struct.out.RGraphQLTypeOutObject;
import com.infomaximum.cluster.graphql.schema.struct.out.RGraphQLTypeOutObjectInterface;
import com.infomaximum.cluster.graphql.utils.Utils;
import com.infomaximum.cluster.struct.Component;
import graphql.GraphQL;
import graphql.TypeResolutionEnvironment;
import graphql.execution.AsyncExecutionStrategy;
import graphql.execution.AsyncSerialExecutionStrategy;
import graphql.execution.DataFetcherExceptionHandler;
import graphql.execution.SubscriptionExecutionStrategy;
import graphql.schema.*;

import java.lang.reflect.Constructor;
import java.util.*;

import static graphql.schema.GraphQLSchema.newSchema;

public class GraphQLExecutorBuilder {

    private final Component component;
    private final String sdkPackagePath;
    private final Constructor customRemoteDataFetcher;

    private final TypeGraphQLFieldConfigurationBuilder fieldConfigurationBuilder;
    private final GraphQLSchemaType graphQLSchemaType;
    private final GraphQLSubscribeEngineImpl subscribeEngine;
    private final DataFetcherExceptionHandler dataFetcherExceptionHandler;

    private GraphQLComponentExecutor sdkGraphQLItemExecutor;

    public GraphQLExecutorBuilder(
            Component component,
            String sdkPackagePath,
            Constructor customRemoteDataFetcher,
            TypeGraphQLFieldConfigurationBuilder fieldConfigurationBuilder,
            GraphQLSchemaType graphQLSchemaType,
            GraphQLSubscribeEngineImpl subscribeEngine,
            DataFetcherExceptionHandler dataFetcherExceptionHandler
    ) {
        this.component = component;
        this.sdkPackagePath = sdkPackagePath;
        this.customRemoteDataFetcher = customRemoteDataFetcher;
        this.fieldConfigurationBuilder = fieldConfigurationBuilder;
        this.graphQLSchemaType = graphQLSchemaType;
        this.subscribeEngine = subscribeEngine;
        this.dataFetcherExceptionHandler = dataFetcherExceptionHandler;
    }

    public GraphQLExecutor build() throws GraphQLExecutorException {
        try {

            //Собираем какие типы у нас вообще есть
            List buildGraphQLTypeEnums = new ArrayList();
            Map buildGraphQLTypeOutObjects = new HashMap();
            Map buildGraphQLTypeOutObjectUnions = new HashMap();
            Map> buildGraphQLTypeInObjects = new HashMap>();

            //Собираем встроенные
            if (sdkPackagePath != null) {
                sdkGraphQLItemExecutor = new GraphQLComponentExecutor(
                        sdkPackagePath, fieldConfigurationBuilder, graphQLSchemaType
                );
                for (RGraphQLType rGraphQLType : sdkGraphQLItemExecutor.getGraphQLTypes()) {
                    mergeGraphQLType(
                            buildGraphQLTypeEnums,
                            buildGraphQLTypeOutObjects,
                            buildGraphQLTypeOutObjectUnions,
                            buildGraphQLTypeInObjects,
                            rGraphQLType
                    );
                }
            }

            //Запрашиваем только у локальных подсистем
            UUID localNodeRuntimeId = component.getTransport().getCluster().node.getRuntimeId();
            Collection rControllerGraphQLExecutors = component.getRemotes().getControllers(RControllerGraphQLExecutor.class);
            for (RControllerGraphQLExecutor rControllerGraphQLExecutor : rControllerGraphQLExecutors) {
                //TODO: убрать проверку при переходе на расширяемую graphQl схему
                if (!localNodeRuntimeId.equals(rControllerGraphQLExecutor.getNodeRuntimeId())) {
                    continue;
                }
                for (RGraphQLType rGraphQLType : rControllerGraphQLExecutor.getGraphQLTypes()) {
                    mergeGraphQLType(
                            buildGraphQLTypeEnums,
                            buildGraphQLTypeOutObjects,
                            buildGraphQLTypeOutObjectUnions,
                            buildGraphQLTypeInObjects,
                            rGraphQLType
                    );
                }
            }

            //В этот map добавляются все построенные типы
            Map graphQLTypes = new HashMap();

            //Добавляем все скаляры
            for (GraphQLTypeScalar graphQLScalarType : graphQLSchemaType.typeScalars) {
                String name = graphQLScalarType.getName();
                graphQLTypes.put(name, graphQLScalarType.getGraphQLScalarType());
                graphQLTypes.put("collection:" + name, new GraphQLList(graphQLScalarType.getGraphQLScalarType()));
            }

            //Добавляем все enum
            for (RGraphQLTypeEnum rGraphQLEnumType : buildGraphQLTypeEnums) {
                buildGraphQLTypeEnum(graphQLTypes, rGraphQLEnumType);
            }

            //Разбираемся с зависимостями input объектами
            for (Map.Entry> entry : buildGraphQLTypeInObjects.entrySet()) {
                String graphQLTypeName = entry.getKey();
                Set graphQLTypeFields = entry.getValue();

                buildGraphQLTypeInObject(graphQLTypes, graphQLTypeName, graphQLTypeFields);
            }

            GraphQLCodeRegistry.Builder codeRegistryBuilder = GraphQLCodeRegistry.newCodeRegistry();

            //Разбираемся с зависимостями output объектов
            Map waitBuildGraphQLTypeOutObjects = new HashMap(buildGraphQLTypeOutObjects);
            while (!waitBuildGraphQLTypeOutObjects.isEmpty()) {
                boolean isCyclicDependency = true;
                for (MergeGraphQLTypeOutObject graphQLTypeOutObject : waitBuildGraphQLTypeOutObjects.values()) {

                    boolean isLoadedDependenciesType = true;
                    for (RGraphQLObjectTypeField typeGraphQLField : graphQLTypeOutObject.getFields()) {
                        String[] compositeTypes = typeGraphQLField.type.split(":");
                        for (String compositeType : compositeTypes) {
                            if ("collection".equals(compositeType)) continue;
                            if (!graphQLTypes.containsKey(compositeType)) {
                                isLoadedDependenciesType = false;
                            }
                        }
                    }

                    if (isLoadedDependenciesType) {
                        //Все зависимости-поля есть, можно загружать
                        buildGraphQLTypeOutObject(codeRegistryBuilder, graphQLTypes, graphQLTypeOutObject, buildGraphQLTypeOutObjectUnions);

                        //Загрузка прошла успешно
                        waitBuildGraphQLTypeOutObjects.remove(graphQLTypeOutObject.name);
                        isCyclicDependency = false;
                        break;
                    }
                }

                if (isCyclicDependency) {
                    //Блински циклическая зависимость, строим первую попавшую через ссылки
                    String graphQLTypeName = waitBuildGraphQLTypeOutObjects.keySet().iterator().next();
                    MergeGraphQLTypeOutObject graphQLTypeOutObject = waitBuildGraphQLTypeOutObjects.get(graphQLTypeName);

                    buildGraphQLTypeOutObject(codeRegistryBuilder, graphQLTypes, graphQLTypeOutObject, buildGraphQLTypeOutObjectUnions);

                    //Загрузка прошла успешно
                    waitBuildGraphQLTypeOutObjects.remove(graphQLTypeName);
                }
            }

            //Разбираемся с зависимостями output union объектов
            for (MergeGraphQLTypeOutObjectInterface mergeGraphQLTypeOutObjectUnion : buildGraphQLTypeOutObjectUnions.values()) {
                buildGraphQLTypeOutObjectUnion(codeRegistryBuilder, graphQLTypes, mergeGraphQLTypeOutObjectUnion);
            }

            GraphQLSchema schema = newSchema()
                    .query((GraphQLObjectType) graphQLTypes.get("query"))
                    .mutation((GraphQLObjectType) graphQLTypes.get("mutation"))
                    .subscription((GraphQLObjectType) graphQLTypes.get("subscription"))
                    .additionalTypes(new HashSet(graphQLTypes.values()))
                    .codeRegistry(codeRegistryBuilder.build())
                    .build();

            GraphQL graphQL = GraphQL.newGraphQL(schema)
                    .queryExecutionStrategy(new AsyncExecutionStrategy(dataFetcherExceptionHandler))
                    .mutationExecutionStrategy(new AsyncSerialExecutionStrategy(dataFetcherExceptionHandler))
                    .subscriptionExecutionStrategy(new SubscriptionExecutionStrategy(dataFetcherExceptionHandler))
                    .build();

            if (graphQLSchemaType.prepareCustomFields == null || graphQLSchemaType.prepareCustomFields.isEmpty()) {
                return new GraphQLExecutorImpl(schema, graphQL);
            } else {
                return new GraphQLExecutorPrepareImpl(component, schema, graphQL, buildGraphQLTypeOutObjects, buildGraphQLTypeOutObjectUnions, graphQLSchemaType);
            }
        } catch (Throwable throwable) {
            throw new GraphQLExecutorException(throwable);
        }
    }

    private void mergeGraphQLType(
            List buildGraphQLTypeEnums,
            Map buildGraphQLTypeOutObjects,
            Map buildGraphQLTypeOutObjectUnions,
            Map> buildGraphQLTypeInObjects,

            RGraphQLType rGraphQLType) throws GraphQLExecutorException {
        if (rGraphQLType instanceof RGraphQLTypeEnum) {
            buildGraphQLTypeEnums.add((RGraphQLTypeEnum) rGraphQLType);
        } else if (rGraphQLType instanceof RGraphQLTypeOutObject) {
            RGraphQLTypeOutObject rGraphQLObjectType = (RGraphQLTypeOutObject) rGraphQLType;

            String rTypeGraphQLName = rGraphQLType.getName();
            Set rTypeGraphQLFields = new HashSet(rGraphQLObjectType.getFields());

            MergeGraphQLTypeOutObject mergeGraphQLTypeOutObject = buildGraphQLTypeOutObjects.get(rTypeGraphQLName);
            if (mergeGraphQLTypeOutObject == null) {
                mergeGraphQLTypeOutObject = new MergeGraphQLTypeOutObject(rTypeGraphQLName, rGraphQLType.getDescription());
                buildGraphQLTypeOutObjects.put(rTypeGraphQLName, mergeGraphQLTypeOutObject);
            }

            //Мержим union типы
            for (String graphQLTypeUnionName : rGraphQLObjectType.getInterfaceGraphQLTypeNames()) {
                MergeGraphQLTypeOutObjectInterface mergeGraphQLTypeOutObjectUnion = buildGraphQLTypeOutObjectUnions.get(graphQLTypeUnionName);
                if (mergeGraphQLTypeOutObjectUnion == null) {
                    mergeGraphQLTypeOutObjectUnion = new MergeGraphQLTypeOutObjectInterface(graphQLTypeUnionName, rGraphQLType.getDescription());
                    buildGraphQLTypeOutObjectUnions.put(graphQLTypeUnionName, mergeGraphQLTypeOutObjectUnion);
                }
                mergeGraphQLTypeOutObjectUnion.mergePossible(rGraphQLObjectType.getClassName(), rTypeGraphQLName);
            }

            //Мержим
            mergeGraphQLTypeOutObject.mergeFields(rTypeGraphQLFields);
            mergeGraphQLTypeOutObject.mergeInterfaces(rGraphQLObjectType.getInterfaceGraphQLTypeNames());

        } else if (rGraphQLType instanceof RGraphQLTypeOutObjectInterface) {
            RGraphQLTypeOutObjectInterface rGraphQLTypeOutObjectUnion = (RGraphQLTypeOutObjectInterface) rGraphQLType;

            String rTypeGraphQLName = rGraphQLTypeOutObjectUnion.getName();

            MergeGraphQLTypeOutObjectInterface mergeGraphQLTypeOutObjectUnion = buildGraphQLTypeOutObjectUnions.get(rTypeGraphQLName);
            if (mergeGraphQLTypeOutObjectUnion == null) {
                mergeGraphQLTypeOutObjectUnion = new MergeGraphQLTypeOutObjectInterface(rTypeGraphQLName, rGraphQLType.getDescription());
                buildGraphQLTypeOutObjectUnions.put(rTypeGraphQLName, mergeGraphQLTypeOutObjectUnion);
            }

            //Добавляем общие поля
            mergeGraphQLTypeOutObjectUnion.mergeFields(rGraphQLTypeOutObjectUnion.getFields());

        } else if (rGraphQLType instanceof RGraphQLTypeInObject) {
            RGraphQLTypeInObject rGraphQLInputObjectType = (RGraphQLTypeInObject) rGraphQLType;

            String rTypeGraphQLName = rGraphQLInputObjectType.getName();
            Set rTypeGraphQLFields = new HashSet<>(rGraphQLInputObjectType.getFields());

            if (buildGraphQLTypeInObjects.containsKey(rTypeGraphQLName)) {
                throw new GraphQLExecutorException("Not unique name: " + rTypeGraphQLName);
            }

            buildGraphQLTypeInObjects.put(rTypeGraphQLName, rTypeGraphQLFields);
        } else {
            throw new GraphQLExecutorException("Not support type: " + rGraphQLType);
        }
    }

    private GraphQLObjectType buildGraphQLTypeOutObject(GraphQLCodeRegistry.Builder codeRegistryBuilder, Map graphQLTypes, MergeGraphQLTypeOutObject graphQLTypeOutObject, Map buildGraphQLTypeOutObjectUnions) throws GraphQLExecutorException {
        GraphQLObjectType.Builder graphQLObjectTypeBuilder = GraphQLObjectType.newObject();
        graphQLObjectTypeBuilder.name(graphQLTypeOutObject.name);

        if (graphQLTypeOutObject.description != null) {
            graphQLObjectTypeBuilder.description(graphQLTypeOutObject.description);
        }

        for (RGraphQLObjectTypeField typeGraphQLField : graphQLTypeOutObject.getFields()) {
            GraphQLFieldDefinition graphQLFieldDefinition = buildGraphQLFieldDefinition(codeRegistryBuilder, graphQLTypes, graphQLTypeOutObject.name, typeGraphQLField);
            graphQLObjectTypeBuilder.field(graphQLFieldDefinition);
        }

        for (String interfaceGraphQLTypeName : graphQLTypeOutObject.getInterfaceGraphQLTypeNames()) {
            graphQLObjectTypeBuilder.withInterface(new GraphQLTypeReference(interfaceGraphQLTypeName));

            //TODO необходимо отрефакторить - добавляем расширяющие полю от интерфейса
            //Необходимо добавлять только новые поля иначе перезаписывается новым полем с другим компонентом
            //в итоге выполнение уйдет не в ту подсистему
            MergeGraphQLTypeOutObjectInterface mergeGraphQLTypeOutObjectInterface = buildGraphQLTypeOutObjectUnions.get(interfaceGraphQLTypeName);
            for (RGraphQLObjectTypeField typeGraphQLField : mergeGraphQLTypeOutObjectInterface.getFields()) {
                //TODO необходимо отрефакторить! Логика совершено не очевидна
                if (!graphQLObjectTypeBuilder.hasField(typeGraphQLField.externalName)) {
                    GraphQLFieldDefinition graphQLFieldDefinition = buildGraphQLFieldDefinition(codeRegistryBuilder, graphQLTypes, graphQLTypeOutObject.name, typeGraphQLField);
                    graphQLObjectTypeBuilder.field(graphQLFieldDefinition);
                }
            }
        }

        GraphQLObjectType graphQLObjectType = graphQLObjectTypeBuilder.build();

        //Регистрируем этот тип
        graphQLTypes.put(graphQLTypeOutObject.name, graphQLObjectType);

        return graphQLObjectType;
    }

    private GraphQLInterfaceType buildGraphQLTypeOutObjectUnion(GraphQLCodeRegistry.Builder codeRegistryBuilder, Map graphQLTypes, MergeGraphQLTypeOutObjectInterface mergeGraphQLTypeOutObjectUnion) {

        GraphQLInterfaceType.Builder builder = GraphQLInterfaceType.newInterface().name(mergeGraphQLTypeOutObjectUnion.name);

        if (mergeGraphQLTypeOutObjectUnion.description != null) {
            builder.description(mergeGraphQLTypeOutObjectUnion.description);
        }

        for (RGraphQLObjectTypeField typeGraphQLField : mergeGraphQLTypeOutObjectUnion.getFields()) {
            GraphQLFieldDefinition graphQLFieldDefinition = buildGraphQLFieldDefinition(codeRegistryBuilder, graphQLTypes, mergeGraphQLTypeOutObjectUnion.name, typeGraphQLField);
            builder.field(graphQLFieldDefinition);
        }

        GraphQLInterfaceType graphQLInterfaceType = builder.build();

        //Регистрируем этот тип
        graphQLTypes.put(mergeGraphQLTypeOutObjectUnion.name, graphQLInterfaceType);

        //Добавляем резолвер
        codeRegistryBuilder.typeResolver(graphQLInterfaceType, new TypeResolver() {
            @Override
            public GraphQLObjectType getType(TypeResolutionEnvironment env) {
                String graphQLTypeName = mergeGraphQLTypeOutObjectUnion.getGraphQLTypeName(env.getObject().getClass().getName());
                if (graphQLTypeName == null) {
                    return null;
                } else {
                    return (GraphQLObjectType) graphQLTypes.get(graphQLTypeName);
                }
            }
        });

        return graphQLInterfaceType;
    }

    private GraphQLFieldDefinition buildGraphQLFieldDefinition(GraphQLCodeRegistry.Builder codeRegistryBuilder, Map graphQLTypes, String graphQLTypeName, RGraphQLObjectTypeField typeGraphQLField) {
        GraphQLFieldDefinition.Builder graphQLFieldDefinitionBuilder = GraphQLFieldDefinition.newFieldDefinition();

        graphQLFieldDefinitionBuilder.type(getGraphQLOutputType(graphQLTypes, typeGraphQLField.type))
                .name(typeGraphQLField.externalName);

        if (typeGraphQLField.description != null) {
            graphQLFieldDefinitionBuilder.description(typeGraphQLField.description);
        }

        if (typeGraphQLField.deprecated != null) {
            graphQLFieldDefinitionBuilder.deprecate(typeGraphQLField.deprecated);
        }

        if (typeGraphQLField.isField) {
            //Это обычное поле
            codeRegistryBuilder.dataFetcher(
                    FieldCoordinates.coordinates(graphQLTypeName, typeGraphQLField.externalName),
                    new ExtPropertyDataFetcher(typeGraphQLField.name)
            );
        } else {
            //Это у нас метод
            if (typeGraphQLField.arguments != null) {
                for (RGraphQLObjectTypeMethodArgument argument : typeGraphQLField.arguments) {
                    GraphQLArgument.Builder argumentBuilder = GraphQLArgument.newArgument();
                    argumentBuilder.name(argument.name);

                    if (argument.isNotNull) {
                        argumentBuilder.type(new GraphQLNonNull(getGraphQLInputType(graphQLTypes, argument.type)));
                    } else {
                        argumentBuilder.type(getGraphQLInputType(graphQLTypes, argument.type));
                    }

                    if (!Utils.isNullOrEmpty(argument.description)) {
                        argumentBuilder.description(argument.description);
                    }

                    graphQLFieldDefinitionBuilder.argument(argumentBuilder.build());
                }
            }

            ComponentDataFetcher componentDataFetcher;
            if (customRemoteDataFetcher != null) {
                try {
                    componentDataFetcher = (ComponentDataFetcher) customRemoteDataFetcher.newInstance(component.getRemotes(), sdkGraphQLItemExecutor, subscribeEngine, graphQLTypeName, typeGraphQLField);
                } catch (ReflectiveOperationException e) {
                    throw new GraphQLExecutorException("Exception build ComponentDataFetcher", e);
                }
            } else {
                componentDataFetcher = new ComponentDataFetcher(component.getRemotes(), sdkGraphQLItemExecutor, subscribeEngine, graphQLTypeName, typeGraphQLField);
            }
            codeRegistryBuilder.dataFetcher(
                    FieldCoordinates.coordinates(graphQLTypeName, typeGraphQLField.externalName),
                    componentDataFetcher
            );
        }

        return graphQLFieldDefinitionBuilder.build();
    }

    private GraphQLEnumType buildGraphQLTypeEnum(Map graphQLTypes, RGraphQLTypeEnum rGraphQLEnumType) {
        GraphQLEnumType.Builder graphQLObjectTypeEnumBuilder = GraphQLEnumType.newEnum();
        graphQLObjectTypeEnumBuilder.name(rGraphQLEnumType.getName());
        for (String enumValue : rGraphQLEnumType.getEnumValues()) {
            graphQLObjectTypeEnumBuilder.value(enumValue);
        }

        if (rGraphQLEnumType.getDescription() != null) {
            graphQLObjectTypeEnumBuilder.description(rGraphQLEnumType.getDescription());
        }

        GraphQLEnumType graphQLObjectTypeEnum = graphQLObjectTypeEnumBuilder.build();

        //Регистрируем этот тип
        graphQLTypes.put(rGraphQLEnumType.getName(), graphQLObjectTypeEnum);

        return graphQLObjectTypeEnum;
    }

    private GraphQLInputObjectType buildGraphQLTypeInObject(Map graphQLTypes, String graphQLTypeName, Set fields) throws GraphQLExecutorException {
        GraphQLInputObjectType.Builder gBuilder = GraphQLInputObjectType.newInputObject();
        gBuilder.name(graphQLTypeName);

        for (RGraphQLInputObjectTypeField field : fields) {
            GraphQLInputObjectField.Builder fieldBuilder = GraphQLInputObjectField.newInputObjectField();
            fieldBuilder.name(field.externalName);

            if (field.isNotNull) {
                fieldBuilder.type(new GraphQLNonNull(getGraphQLInputType(graphQLTypes, field.type)));
            } else {
                fieldBuilder.type(getGraphQLInputType(graphQLTypes, field.type));
            }

            gBuilder.field(fieldBuilder.build());
        }

        GraphQLInputObjectType graphQLInputObjectType = gBuilder.build();

        //Регистрируем этот тип
        graphQLTypes.put(graphQLTypeName, graphQLInputObjectType);

        return graphQLInputObjectType;
    }

    private GraphQLOutputType getGraphQLOutputType(Map graphQLTypes, String type) throws GraphQLExecutorException {
        String[] compositeTypes = type.split(":");
        if (compositeTypes.length == 1) {//Это простой объект
            GraphQLType graphQLType = getType(graphQLTypes, type);
            if (graphQLType instanceof GraphQLOutputType) {
                return (GraphQLOutputType) graphQLType;
            } else {
                throw new GraphQLExecutorException("GraphQLType: " + type + " is not GraphQLOutputType");
            }
        } else if ("collection".equals(compositeTypes[0])) {
            return new GraphQLList(getType(graphQLTypes, compositeTypes[1]));
        } else {
            throw new GraphQLExecutorException("not support");
        }
    }

    private GraphQLInputType getGraphQLInputType(Map graphQLTypes, String type) throws GraphQLExecutorException {
        String[] compositeTypes = type.split(":");
        if (compositeTypes.length == 1) {//Это простой объект
            GraphQLType graphQLType = getType(graphQLTypes, type);
            if (graphQLType instanceof GraphQLOutputType) {
                return (GraphQLInputType) graphQLType;
            } else if (graphQLType instanceof GraphQLInputObjectType) {
                return (GraphQLInputType) graphQLType;
            } else {
                throw new GraphQLExecutorException("GraphQLType: " + type + " is not GraphQLInputType");
            }
        } else if ("collection".equals(compositeTypes[0])) {
            return new GraphQLList(getGraphQLInputType(graphQLTypes, compositeTypes[1]));
        } else {
            throw new GraphQLExecutorException("not support");
        }
    }

    private GraphQLType getType(Map graphQLTypes, String type) {
        GraphQLType graphQLType = graphQLTypes.get(type);
        if (graphQLType != null) {
            return graphQLType;
        } else {
            return new GraphQLTypeReference(type);
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy