当前位置: 首页 > 知识库问答 >
问题:

确保控制器存在无参数公共构造函数错误

陈浩
2023-03-14

我一直遵循这个非常有效的教程,直到我修改了我的DbContext,增加了一个构造函数。我现在对决议有问题,不知道该怎么做才能解决这个问题。有没有一种简单的方法来强制它获取无参数构造函数,或者我的方法不正确?

DbContext有两个构造函数:

public class DashboardDbContext : DbContext
{
    public DashboardDbContext() : base("DefaultConnection") { }

    public DashboardDbContext(DbConnection dbConnection, bool owns)
        : base(dbConnection, owns) { }
}

SiteController构造函数:

private readonly IDashboardRepository _repo;

public SiteController(IDashboardRepository repo)
{
    _repo = repo;
}

仓库:

DashboardDbContext _context;

public DashboardRepository(DashboardDbContext context)
{
    _context = context;
}

UnityResolver代码:

public class UnityResolver : IDependencyResolver
{
    private readonly IUnityContainer _container;

    public UnityResolver(IUnityContainer container)
    {
        _container = container;
    }

    public object GetService(Type serviceType)
    {
        try
        {
            return _container.Resolve(serviceType);
        }
        catch (ResolutionFailedException)
        {
            return null;
        }
    }

    public IEnumerable<object> GetServices(Type serviceType)
    {
        try
        {
            return _container.ResolveAll(serviceType);
        }
        catch (ResolutionFailedException)
        {
            return new List<object>();
        }
    }

    public IDependencyScope BeginScope()
    {
        var child = _container.CreateChildContainer();
        return new UnityResolver(child);
    }

    public void Dispose()
    {
        _container.Dispose();
    }
}

WebApiConfig:

var container = new UnityContainer();
container.RegisterType<IDashboardRepository, DashboardRepository>(new HierarchicalLifetimeManager());
config.DependencyResolver = new UnityResolver(container);

WebApi调用出错:

系统。无效操作异常:尝试创建SiteController类型的控制器时出错。确保控制器具有无参数公共构造函数。

at System.Web.Http.Dispatcher.DefaultHttpControllerActivator.Create(HttpRequestMessage request, HttpControllerDescriptor controllerDescriptor, Type controllerType) 
at System.Web.Http.Controllers.HttpControllerDescriptor.CreateController(HttpRequestMessage request) 
at System.Web.Http.Dispatcher.HttpControllerDispatcher.SendAsyncCore(HttpRequestMessage request, CancellationToken cancellationToken) 
at System.Web.Http.Dispatcher.HttpControllerDispatcher.<SendAsync>d__0.MoveNext()

内部异常:系统。ArgumentException:键入“Dashboard”。网状物控制器。SiteController“”没有默认构造函数。

at System.Linq.Expressions.Expression.New(Type type) 
at System.Web.Http.Internal.TypeActivator.Create[TBase](Type instanceType) 
at System.Web.Http.Dispatcher.DefaultHttpControllerActivator.GetInstanceOrActivator(HttpRequestMessage request, Type controllerType, Func`1& activator) 
at System.Web.Http.Dispatcher.DefaultHttpControllerActivator.Create(HttpRequestMessage request, HttpControllerDescriptor controllerDescriptor, Type controllerType)

该教程非常棒,在我添加第二个构造函数之前一直对我很好。

共有3个答案

卫建义
2023-03-14

我有同样的问题,我通过在UnityConfig.cs文件中进行更改来解决它为了解决UnityConfig.cs文件中的依赖问题,您必须添加:

public static void RegisterComponents()    
{
    var container = new UnityContainer();
    container.RegisterType<ITestService, TestService>();
    DependencyResolver.SetResolver(new UnityDependencyResolver(container));
}
公孙宏远
2023-03-14

在我的例子中,这是因为注入依赖项的构造函数内部出现异常(在您的示例中,在DashboardRepository构造函数内部)。该异常在MVC基础架构中的某个地方被捕获。我在相关地方添加日志后发现了这一点。

邓威
2023-03-14

发生的事情是你被这个问题咬了。基本上,发生的情况是您没有在容器中显式注册控制器。Unity试图为您解析未注册的具体类型,但是因为它无法解析它(由配置中的错误引起),所以它返回null。它被迫返回null,因为Web API由于IDependencyResolver契约而强制返回null。由于Unity返回null,Web API将尝试创建控制器本身,但是由于它没有默认构造函数,它将抛出“确保控制器具有无参数公共构造函数”异常。此异常消息具有误导性,无法解释真正的原因。

如果显式注册控制器,您会看到更清晰的异常消息,这就是为什么您应该始终显式注册所有根类型。

但是当然,配置错误来自于您将第二个构造函数添加到您的DbContext。Unity总是试图选择具有最多参数的构造函数,但是它不知道如何解析这个特定的构造函数。

所以真正的原因是您试图使用Unity的自动连接功能来创建DbContextDbContext是一种不应该自动连接的特殊类型。它是一个框架类型,因此您应该回退到使用工厂委托注册它:

container.Register<DashboardDbContext>(
    new InjectionFactory(c => new DashboardDbContext())); 
 类似资料:
  • 最近,我将Paho MQTT Spy项目导入Eclipse。导入结束时出现错误: 为什么我会收到这条信息,这意味着什么?怎么修? 我正在使用Java13.0.1 我试图用maven构建项目,得到了同样的错误。 我添加了下面的依赖项到pom.xml 现在pom.xml如下所示: Maven给出了错误: UPD Java8解决了问题,但我仍然试图使java 13与它一起工作。 正在尝试使用下面定义的p

  • 问题内容: 在编组期间,JAXB需要一个公共的无参数构造函数吗? 我正在传递一个对象,而不是一个类。为什么JAXB需要构造函数?要构造什么? 问题答案: 在执行封送操作期间,JAXB实现不应需要无参数构造函数。JAXB确实需要一个解组。通常,在创建JAXBContext时,缺少no- arg构造函数会导致错误。您正在使用的JAXB实现可能会延迟初始化,直到执行实际操作为止。 通常,在将来的JAXB

  • 我正在浏览hibernate留档,文档说hibernate需要为我们所有的持久类提供一个no-arg构造函数: 无参数构造函数是所有持久类的要求;Hibernate必须使用Java反射为您创建对象。构造器可以是私有的,但是在没有字节码插装的情况下,运行时代理生成和有效的数据检索需要包或公共可见性。 但是当我通过创建一个没有任何无参数构造函数的POJO类并放置一个接受参数的构造函数来创建一个示例程序

  • 问题内容: 我有一个用JUnit4语法编写的测试类,可以使用“以junit测试方式运行”选项在eclipse中运行而不会失败。通过蚂蚁目标运行相同的测试时,出现以下错误: 我在类中没有public no arg构造函数,但这真的有必要吗? 这是我的蚂蚁目标 测试类没有构造函数,但是它具有带有默认修饰符的内部类。它也有一个匿名内部类。两个内部类均给出“ Test类应具有公共零参数构造函数错误”。我正

  • 我的问题是关于OOP(C)中的构造函数。当我在一个类中将默认构造函数定义为private,并且在main中将该类的一个对象初始化为default时,就会出现默认构造函数不可访问的错误。这很好。但我也在Public部分中使用默认参数构造函数,当我再次在main中初始化对象时,就会出现对函数重载的不明确调用。所以我的问题是,如果不能从main访问私有构造函数,那么编译器应该调用公共部分中的构造函数,这

  • 我的类扩展,如下所示: 像这样呼唤: 但我总是得到: