【问题标题】:ASP.NET MVC Custom RoleProvider cannot retrieve roles from database for usernameASP.NET MVC 自定义 RoleProvider 无法从数据库中检索用户名的角色
【发布时间】:2016-04-22 13:57:35
【问题描述】:

我似乎无法为上述问题找到正确的解决方案。我不断收到System.NullReferenceException: Object reference not set to an instance of an object.

我遵循了这个指南http://techbrij.com/custom-roleprovider-authorization-asp-net-mvc

错误消息来自我的自定义角色提供者,来自 var user = _VisitorService.GetVisitors().FirstOrDefault(u => u.Username == username); 行的 GetRolesForUser(string username)

VisitorService 在 Controller 中起作用,但在 RoleProvider 中不起作用。

以下是代码,请根据需要提供建议。提前谢谢你。

自定义角色提供者

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using TamilLeague.Service;

namespace TamilLeague.WebUI
{
    public class myRoleProvider : System.Web.Security.RoleProvider
    {
        private readonly IVisitorService _VisitorService;
        public myRoleProvider(IVisitorService visitorservice)
        {
            _VisitorService = visitorservice;
        }
        public myRoleProvider() { }

        public override string[] GetRolesForUser(string username)
        {            
            var user = _VisitorService.GetVisitors().FirstOrDefault(u => u.Username == username);
            if (user == null)
                return null;
            else
            {
                string role = user.Role.Title;
                string[] rol = { role };
                return rol;
            }
        }
}

我的控制器

[AllowAnonymous]
        [HttpPost]
        public ActionResult Login(UserLoginVM thisUser, string returnUrl)
        {
            var visitor = _VisitorService.GetVisitors().FirstOrDefault(v => v.Username.ToLower() == thisUser.Username.ToLower());

            if (visitor == null)
            {
                ModelState.AddModelError("Username", "Username not found in system. Please register or change the username.");
            }
            if(!visitor.checkPassword(thisUser.HashedPassword))
            {
                ModelState.AddModelError("Username", "Username or password is incorrect.");
            }

            if (visitor.IsFreezed == true)
            {
                ModelState.AddModelError("Username", "Account is freezed. Contact the administrator please.");
            }

            if (visitor.IsConfirmed == false)
            {
                ModelState.AddModelError("Username", "Account is not activated. Contact the administrator please or log into your email to activate your account.");
            }

            if (ModelState.IsValid)
            {
                FormsAuthentication.SetAuthCookie(thisUser.Username, true);
                if (!string.IsNullOrWhiteSpace(returnUrl))
                {
                    return Redirect(returnUrl);
                }
                else
                {
                    return RedirectToAction("GiveAccess", new { id = visitor.ID });
                }
            }
            return Content("Testing");
        }

GiveAccess 方法

public ActionResult GiveAccess(int ID)
        {
            var user = _VisitorService.GetVisitor(ID);
            String[] roles = Roles.Provider.GetRolesForUser(user.Username);

            if(roles.Contains("Administrator"))
            {
                return RedirectToAction("SysUser", "Admin");
            }
            else
            {
                return RedirectToAction("Index", "Member");
            }
            //RedirectToAction("Index", "Member");
        }

Web.config

<system.web>
    <authentication mode="Forms">
      <forms loginUrl="~/User/Login"/>
    </authentication>
    <roleManager enabled="true" defaultProvider="TamilLeagueRoleProvider">
      <providers>
        <clear/>
        <add name="TamilLeagueRoleProvider" type="TamilLeague.WebUI.myRoleProvider" cacheRolesInCookie="false"/>
      </providers>
    </roleManager>
    <compilation debug="true" targetFramework="4.5"/>
    <httpRuntime targetFramework="4.5"/>
  </system.web>

【问题讨论】:

    标签: c# asp.net asp.net-mvc asp.net-mvc-5 roleprovider


    【解决方案1】:

    您在 myRoleProvider 中有一个不实例化服务的无参数构造函数。你确定这个类没有进入那个构造函数吗?如果是,那么当您尝试使用该服务时,您将得到一个空引用异常。

    【讨论】:

    • 这就是我的想法.. 但是当我删除无参数构造函数时,我收到错误“没有为此对象定义无参数构造函数”。 :(
    • 请参阅下面的 Wins 答案。需要在无参构造函数中实例化服务
    【解决方案2】:

    您不能通过构造函数将依赖项注入到 RoleProvider。换句话说,Provider Model 现在不允许参数化构造函数。

    为了解决它,你想使用Service Locator Pattern

    例如,在 Autofac -

    private IVisitorService VisitorService { get; set; }
    
    public MyRoleProvider()
    {
       var cpa = (IContainerProviderAccessor)HttpContext.Current.ApplicationInstance;
       var cp = cpa.ContainerProvider;
    
       VisitorService = cp.RequestLifetime.Resolve<IVisitorService>();
    }
    

    【讨论】:

    • 嗨我实现了 autofac 现在我得到 IContainerProviderAccessor 找不到。 '私人 IVisitorService 访客服务 { 获取;放; } public myRoleProvider(IVisitorService visitorservice) { _VisitorService = visitorservice; } public myRoleProvider() { var cpa = (IContainerProviderAccessor) HttpContext.Current.ApplicationInstance; }'
    • 你能试试var visitorService = DependencyResolver.Current.GetService&lt;IVisitorService&gt;();吗?
    • 当我进入命名空间 Autofac.Integration.Web;它说命名空间 Autofac.Integration 中不存在 Web
    • 你要下载Autofac.Mvc5 from NuGet。如果您想了解更多信息,请查看here
    • Autofac.MVC5 已经安装。现在我得到None of the constructors found with 'Autofac.Core.Activators.Reflection.DefaultConstructorFinder' on type 'TamilLeague.WebUI.Controllers.UserController .heres 我的引导程序的一部分,它由全局`builder.RegisterAssemblyTypes(typeof(VisitorService).Assembly) .Where(t => t.Name.EndsWith("Service")) .AsImplementedInterfaces( ).InstancePerRequest();`
    猜你喜欢
    • 2018-09-18
    • 1970-01-01
    • 1970-01-01
    • 2018-07-27
    • 1970-01-01
    • 2014-10-22
    • 2016-06-15
    • 2019-02-16
    • 1970-01-01
    相关资源
    最近更新 更多