.NET Core - 解决 IServiceProvider 依赖项

ricky32

我将 GraphQL 2.4.0 与 .NET Core 3.1 解决方案和 Microsoft DI 一起使用。我的Schema.cs样子:

public class MySchema : GraphQL.Types.Schema
{
    private ISchema _schema { get; set; }
    public ISchema GraphQLSchema
    {
        get
        {
            return this._schema;
        }
    }

    public MySchema(IServiceProvider sp)
    {
        this._schema = Schema.For(@"
            type MyObj{
                id: ID
                name: String,
                type: String,
                createdAt: String
            }

            type Mutation {
                objSync(type: String): MyObj
            }

            type Query {
                myobj: MyObj
            }
        ", _ =>
        {
            _.DependencyResolver = new FuncDependencyResolver(t => sp.GetService(t)); // Since I'm using v2.4
            _.Types.Include<MyQuery>();
            _.Types.Include<MyMutation>();
        });
    }
}

MyMutation.cs 看起来像:

[GraphQLMetadata("MyMutation")]
public class MyMutation
{
    private readonly ISomeType someType;

    public MyMutation(ISomeType someType)
    {
        this.someType= someType;
    }

    [GraphQLMetadata("objSync")]
    public MyObj SyncObj(string type)
    {
        byte[] _bytes = null;
        _bytes = someType.Process(type).Result;
        return new Obj { File = Encoding.UTF8.GetString(_bytes , 0, _bytes .Length) };
    }
}

我正在解决依赖项,Startup.cs例如:

...
public static void AddServices(this IServiceCollection services)
{
    services.AddSingleton<IDependencyResolver>(_ => new FuncDependencyResolver(_.GetRequiredService));
    services.AddSingleton<IDocumentExecuter, DocumentExecuter>();
    services.AddSingleton<IDocumentWriter, DocumentWriter>();
    services.AddSingleton<MyMutation>();
    services.AddSingleton<IServiceProvider>();
    services.AddScoped<ISchema, MySchema>();
    services.AddSingleton<ISomeType, SomeManager>();
    ...
}
...

GraphQLController.cs以以下方式使用架构

[Route("graphql")]
[ApiController]
public class GraphQLController: ControllerBase
{
    MySchema schema;
    IServiceProvider serviceProvider;

    public GraphQLController(IServiceProvider serviceProvider)
    {
        schema = new MySchema(serviceProvider);
    }

    [HttpPost]
    public ActionResult Post([FromBody] GraphQLQuery query)
    {
        try
        {
            var inputs = query.Variables.ToInputs();

            var result = new DocumentExecuter().ExecuteAsync(_ =>
            {
                _.Schema = schema.GraphQLSchema;
                _.Query = query.Query;
                _.OperationName = query.OperationName;
                _.Inputs = inputs;
            }).Result;

            if (result.Errors?.Count > 0)
            {
                return BadRequest();
            }

            return Ok(result);
        }
        catch (Exception ex)
        {
            return BadRequest();
        }
    }
}

通过上述设置,我得到了一个例外:

Unhandled exception. System.ArgumentException: Cannot instantiate implementation type 'System.IServiceProvider' for service type 'System.IServiceProvider'.
   at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.Populate()
   at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory..ctor(IEnumerable`1 descriptors)
   at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngine..ctor(IEnumerable`1 serviceDescriptors, IServiceProviderEngineCallback callback)
   at Microsoft.Extensions.DependencyInjection.ServiceLookup.CompiledServiceProviderEngine..ctor(IEnumerable`1 serviceDescriptors, IServiceProviderEngineCallback callback)
   at Microsoft.Extensions.DependencyInjection.ServiceProvider..ctor(IEnumerable`1 serviceDescriptors, ServiceProviderOptions options)
   at Microsoft.Extensions.DependencyInjection.ServiceCollectionContainerBuilderExtensions.BuildServiceProvider(IServiceCollection services, ServiceProviderOptions options)
   at Microsoft.Extensions.DependencyInjection.ServiceCollectionContainerBuilderExtensions.BuildServiceProvider(IServiceCollection services)
   at Microsoft.AspNetCore.Hosting.WebHost.Initialize()
   at Microsoft.AspNetCore.Hosting.WebHostBuilder.Build()
   at App.Api.Program.Main(String[] args)

问题:如果我必须实例化它,那么MySchema期望IServiceProvider输入。我如何实例化它?还是有另一种调用方式MySchema

nvoigt

删除这一行:

services.AddSingleton<IServiceProvider>();

你不能注册一个接口,你必须注册一个类或结构,但最重要的是,IServiceProvider框架已经交给了它。您无需向您的服务提供商注册服务提供商

当我们在做的时候:

public GraphQLController(IServiceProvider serviceProvider)
{
    schema = new MySchema(serviceProvider);
}

如果您使用 DI,请不要手动执行:

public GraphQLController(IMySchema schema)
{
    this.schema = schema; // this.schema needs to be IMySchema as well
}

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章