对象引用未设置为对象#2的实例

时间:2012-02-21 15:45:46

标签: c# asp.net-mvc-3 c#-4.0 .net-4.0 nullreferenceexception

public class AccountController : Controller
{

    private LoginModel loginModel = null;

    #region Constructor
    public AccountController(LoginModel loginModel)
    {
        this.loginModel = loginModel;
    }

    public AccountController()
    {
    }
    #endregion

    #region Login
    //
    // GET: /Account/Login
    public ActionResult Login()
    {
        return View();
    }

    //
    // POST: /Account/Login
    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Login(string userName, string password, bool rememberMe, string returnUrl)
    {
        try
        {
            string displayFullName = null, token = null;

            LoginViewModel loginViewModel = new LoginViewModel();
            loginViewModel.UserName = userName;
            loginViewModel.Password = password;
            loginViewModel.RememberMe = rememberMe;

            ModelState.AddModelErrors(loginViewModel.ValidateLogIn());

            if (!ModelState.IsValid)
            {
                return View();
            }

            //login failed than return view. 
            if (!this.loginModel.LogIn(loginViewModel, ref displayFullName, ref token))
            {
                ModelState.AddModelError("_FORM", PortalErrors.IncorrectDataMsg);
                return View();
            }

            if (Url.IsLocalUrl(returnUrl) && returnUrl.Length > 1 && returnUrl.StartsWith("/")
                    && !returnUrl.StartsWith("//") && !returnUrl.StartsWith("/\\"))
            {
                return Redirect(returnUrl);
            }
            else
            {
                return RedirectToAction("Index", "Home");
            }

        }
        catch (Exception exc)
        {
            ModelState.AddModelError("_FORM", PortalErrors.CommonErrMsg);
            return View();
        }
    } 

我在上面的代码上遇到错误if(!this.loginModel.LogIn(loginViewModel,ref displayFullName,ref token))

任何人都可以帮忙解决这个问题吗?

5 个答案:

答案 0 :(得分:3)

嗯,你有两个cosntructor - 其中一个设置this.loginModel(虽然它没有检查它是否将它设置为非空值);另一个没有。

正在调用哪个构造函数?如果它是无参数的那个,那么我对你得到那个错误并不感到惊讶。你需要两个构造函数吗?这是由一些DI框架实例化的吗?

答案 1 :(得分:2)

当然这是因为loginModel应该在构造函数中设置;但MVC不会触发设置它的构造函数;它将触发默认构造函数 - 所以到那时它是null;因此NullReferenceException

我猜你从别人那里继承了这个控制器;并且他们已经为它编写了单元测试 - 因此是额外的构造函数;除非像Jon提到的那样,网站上有一些活跃的DI框架(在这种情况下,它的配置错误)。

如果有一个DI框架创建控制器 - 然后检查它是否可以解析LoginModel的实例。一种简单的方法和良好的做法是检查在该构造函数中传递的空LoginModel并抛出异常(通常为ArgumentNullException;如此处另一个答案中提到的代码契约的使用是好的计划)然后再次运行该网站。要么你会得到同样的错误(在这种情况下可能没有涉及DI),或者你会得到你的ArgumentNullException - 在这种情况下存在并且配置错误。

如果没有,你需要修改控制器的默认构造函数来创建LoginModel的默认实例 - 可能它已经在数据库或类似的东西 - 最终你需要看看在项目的其余部分代码中找出一个。

答案 2 :(得分:1)

好吧,看起来this.loginModel为空(或者,它可能是this.loginModel.Login调用中的内容)。

我怀疑前者是因为你有

public AccountController() { }

您从未设置this.loginModel

此外,在此构造函数中

public AccountController(LoginModel loginModel) {
    this.loginModel = loginModel;
}

您没有检查loginModel是不是null。我想你删除无参数构造函数,你应该添加一个契约

Contract.Requires(loginModel != null);

答案 3 :(得分:1)

在相关的行上放置一个调试器断点。

当代码停在那里时,是否有任何变量为空?

我的猜测是this.loginModel在那里为空。您无法在空实例上调用实例方法。

答案 4 :(得分:1)

我猜loginModel为null。如果使用无参数构造函数实例化AccountController,则会导致此问题。