webapi IPrincipal并授权

时间:2012-07-24 17:57:11

标签: asp.net-mvc-4 asp.net-web-api

这是关于安全性MVC4 RC和“Install-Package Microsoft.AspNet.WebApi”。

我创建了一个自定义身份:System.Security.Principal.IIdentity,其中我将一些有价值的字符串和int存储在身份验证cookie中:

  [Serializable]
public class SiteIdentity : IIdentity
{
    public SiteIdentity(string name, string displayName, int userId, int siteId)
    {
        this.Name = name;
        this.DisplayName = displayName;
        this.UserId = userId;
        this.SiteId = siteId;

    }

    public SiteIdentity(string name, UserInfo userInfo)
        : this(name, userInfo.DisplayName, userInfo.UserId, userInfo.SiteId)
    {
        if (userInfo == null) throw new ArgumentNullException("userInfo");
        this.AuthenticationType = userInfo.AutheticationType;
        this.ClaimsIdentifier = userInfo.ClaimsIdentifier;
    }

    public SiteIdentity(FormsAuthenticationTicket ticket)
        : this(ticket.Name, UserInfo.FromString(ticket.UserData))
    {
        if (ticket == null) throw new ArgumentNullException("ticket");
    }

......不完整,但我想你猜。

但首先是我的webapi控制器的结构。我已经创建了扩展控制器,我扩展了所有的webapi控制器:

   public class _AuthorizedApiController : ApiController
{

        protected readonly Site.Web.Domain.Services.IUserServices _userServices;

        public _AuthorizedApiController(Site.Web.Domain.Services.IUserServices userServices)
        {
            if (userServices == null) throw new ArgumentNullException("userServices");
            this._userServices = userServices;

        }

        protected int CurrentUserId
        {
            get { return this.User.SiteIdentity().UserId; }
        }

        private Site.Web.Domain.Models.User currentUser;

        public Site.Web.Domain.Models.User CurrentUser
        {
            get
            {
                return this.currentUser ??
                       (this.currentUser = this._userServices.GetUserFromIdentity(this.User.SiteIdentity()));
            }
        }

        protected int CurrentSiteId
        {
            get { return this.User.SiteIdentity().SiteId; }
        }

}

所以我的webapi控制器是:

    public class ServicioController : _AuthorizedApiController
{
    //http://www.asp.net/web-api/overview/web-api-routing-and-actions/routing-in-aspnet-web-api
    //http://www.asp.net/web-api/overview/web-api-routing-and-actions/exception-handling

    static readonly IServicioStatusRepository repositoryServicioStatus = 
        new ServicioStatusRepository(new Site.Web.Data.DatabaseFactory());



    public ServicioController(Site.Web.Domain.Services.IUserServices userServices)
    : base(userServices)
    {

    }



    public IEnumerable<ServicioStatusA> GetServiciosStatus()
    {
        IEnumerable<ServicioStatusA> coleccion;
        var estevalor = CurrentUser.SiteId;
     }

正如您所看到我使用IoC但问题是当我尝试读取CurrentUser.SiteId时。我收到这个错误:

无法将“System.Web.Security.FormsIdentity”类型的对象强制转换为“Site.Web.Models.SiteIdentity”。

在这个返回函数中:

       public static Site.Web.Models.SiteIdentity SiteIdentity(this System.Security.Principal.IPrincipal principal)
    {
        return (Site.Web.Models.SiteIdentity)principal.Identity;
    }

我在global.asax.cs中使用这个“工件”来保存会话和信息:

    public override void Init()
    {
        this.PostAuthenticateRequest += this.PostAuthenticateRequestHandler;
        //            this.EndRequest += this.EndRequestHandler;

        base.Init();
    }


    private void PostAuthenticateRequestHandler(object sender, EventArgs e)
    {
        if (IsWebApiRequest())
        {
            string esto = "popopopopo";
        }


        HttpCookie authCookie = this.Context.Request.Cookies[FormsAuthentication.FormsCookieName];
        if (IsValidAuthCookie(authCookie))
        {
            // var formsAuthentication = ServiceLocator.Current.GetInstance<IFormsAuthentication>();
            var formsAuthentication = new FormsAuthenticationService();

            var ticket = formsAuthentication.Decrypt(authCookie.Value);
            var siteIdentity = new SiteIdentity(ticket);
            this.Context.User = new GenericPrincipal(siteIdentity, null);

            // Reset cookie for a sliding expiration.
            formsAuthentication.SetAuthCookie(this.Context, ticket);
        }
    }

而且我猜是当有一个“正常”的MVC调用时,每个都可以正常工作,但是当有一个webapi调用时,我可以从cookie中恢复所有内容但是我有:

System.Security.Principal.GenericPrincipal  + Identity:Site.Web.Model.SiteIdentity

而不是:

System.Security.Principal.GenericPrincipal  + Identity:System.web.security.FormsIdentity

提前感谢您的支持

ADEN-UM:

谷歌搜索我也尝试将身份保留在线程中,所以在PostAuthenticateRequestHandler里面输入:

 System.Threading.Thread.CurrentPrincipal = this.Context.User;

但现在我已经为所有请求提出以下错误,不仅是webapi:

     [SerializationException: Type is not resolved for member 'Site.Web.Models.SiteIdentity,Site.Web, Version=1.0.0.0, Culture=neutral,PublicKeyToken=null'.]
   Microsoft.VisualStudio.WebHost.Connection.get_RemoteIP() +0
   Microsoft.VisualStudio.WebHost.Request.GetRemoteAddress() +65
   System.Web.HttpRequest.get_IsLocal() +23
   System.Web.Configuration.CustomErrorsSection.CustomErrorsEnabled(HttpRequest request) +86
   System.Web.HttpContextWrapper.get_IsCustomErrorEnabled() +45
   System.Web.Mvc.HandleErrorAttribute.OnException(ExceptionContext filterContext) +72
   System.Web.Mvc.ControllerActionInvoker.InvokeExceptionFilters(ControllerContext controllerContext, IList`1 filters, Exception exception) +115
   System.Web.Mvc.Async.<>c__DisplayClass25.<BeginInvokeAction>b__22(IAsyncResult asyncResult) +105
   System.Web.Mvc.Async.WrappedAsyncResult`1.End() +57
   System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeAction(IAsyncResult asyncResult) +45
   System.Web.Mvc.<>c__DisplayClass1d.<BeginExecuteCore>b__18(IAsyncResult asyncResult) +14
   System.Web.Mvc.Async.<>c__DisplayClass4.<MakeVoidDelegate>b__3(IAsyncResult ar) +25
   System.Web.Mvc.Async.WrappedAsyncResult`1.End() +62
   System.Web.Mvc.Controller.EndExecuteCore(IAsyncResult asyncResult) +61
   System.Web.Mvc.Async.<>c__DisplayClass4.<MakeVoidDelegate>b__3(IAsyncResult ar) +25
   System.Web.Mvc.Async.WrappedAsyncResult`1.End() +62
   System.Web.Mvc.Controller.EndExecute(IAsyncResult asyncResult) +49
   System.Web.Mvc.Controller.System.Web.Mvc.Async.IAsyncController.EndExecute(IAsyncResult asyncResult) +10
   System.Web.Mvc.<>c__DisplayClassb.<BeginProcessRequest>b__4(IAsyncResult asyncResult) +28
   System.Web.Mvc.Async.<>c__DisplayClass4.<MakeVoidDelegate>b__3(IAsyncResult ar) +25
   System.Web.Mvc.Async.WrappedAsyncResult`1.End() +62
   System.Web.Mvc.<>c__DisplayClasse.<EndProcessRequest>b__d() +50
   System.Web.Mvc.SecurityUtil.<GetCallInAppTrustThunk>b__0(Action f) +7
   System.Web.Mvc.SecurityUtil.ProcessInApplicationTrust(Action action) +22
   System.Web.Mvc.MvcHandler.EndProcessRequest(IAsyncResult asyncResult) +60
   System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.EndProcessRequest(IAsyncResult result) +9
   System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +8970061
   System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +184

0 个答案:

没有答案