Skip to content
This repository was archived by the owner on Dec 19, 2023. It is now read-only.
This repository was archived by the owner on Dec 19, 2023. It is now read-only.

Unable to inject executionStrategies bean #336

@petr-ujezdsky

Description

@petr-ujezdsky

TL;DR

public class GraphQLWebAutoConfiguration {

    @Autowired(required = false)
    private Map<String, ExecutionStrategy> executionStrategies;

is populated by spring as map beanName -> bean, when I have some ExecutionStrategy in spring context.

Problem

I was trying to inject my custom executionStrategies bean for ExecutionStrategyProvider creation inside GraphQLWebAutoConfiguration.

In my own @Configuration annotated class I have created simple bean

@Configuration
public class GraphqlConfiguration {

    @Bean
    public Map<String, ExecutionStrategy> executionStrategies(AsyncTransactionalExecutionStrategy strategy) {
        Map<String, ExecutionStrategy> executionStrategyMap = new HashMap<>();
        executionStrategyMap.put(QUERY_EXECUTION_STRATEGY, strategy);
        executionStrategyMap.put(MUTATION_EXECUTION_STRATEGY, new AsyncExecutionStrategy());
        return executionStrategyMap;
    }
}

Where AsyncTransactionalExecutionStrategy is another bean (with transaction over whole graphql execution to enable lazy hibernate calls)

@Component
public class AsyncTransactionalExecutionStrategy extends AsyncExecutionStrategy {

    @Override
    @Transactional
    public CompletableFuture<ExecutionResult> execute(ExecutionContext executionContext, ExecutionStrategyParameters parameters) throws NonNullableFieldWasNullException {
        return super.execute(executionContext, parameters);
    }
}

The problem is, that the executionStrategyProvider(...) inside GraphQLWebAutoConfiguration is called before my configuration and my map bean creation.

public class GraphQLWebAutoConfiguration {

    @Autowired(required = false)
    private Map<String, ExecutionStrategy> executionStrategies;

executionStrategies is injected with map beanName -> bean (of 1 instance) instead of map from my bean that uses GraphQLWebAutoConfiguration.QUERY_EXECUTION_STRATEGY and alike as keys. The executionStrategyProvider then works unexpectedly - it uses the one strategy for query, mutation and subscription.

Solution (kind of)

The solution is to name my bean using the expected keys

@Component(QUERY_EXECUTION_STRATEGY)
public class AsyncTransactionalExecutionStrategy extends AsyncExecutionStrategy {

and do not use the executionStrategies(...) bean inside my config. This populates the executionStrategies map with proper keys (beanName = expected key). But is this the "right" way that is intended?

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions