簡體   English   中英

基於授權的 ASP.Net Web Api 幫助頁面

[英]ASP.Net Web Api Help page based on authorization

我在 Windows 身份驗證后面使用 ASP.Net Web API,並使用 [Authorize] 屬性來指示用戶可以訪問哪些控制器和功能。 這很好用。 問題是我想讓幫助區域只反映用戶被授予訪問權限的內容。 好奇是否有人以某種方式實現了這一目標。 這是在控制器、應用程序啟動還是幫助控制器級別完成的。

提前致謝...

我的控制器之一的代碼片段

[Authorize]
public class TaktTimeController : ApiController
{
    private BIDataContainer db = new BIDataContainer();

    // GET api/TaktTime
    [Authorize(Roles="Admins")]
    public IQueryable<TaktTime> GetTaktTimes()
    {
        return db.TaktTimes;
    }

    // GET api/TaktTime/5
    [ResponseType(typeof(TaktTime))]
    [Authorize(Roles = "Admins")]
    public IHttpActionResult GetTaktTime(string id)
    {
        TaktTime takttime = db.TaktTimes.Find(id);
        if (takttime == null)
        {
            return NotFound();
        }

        return Ok(takttime);
    }

您將需要修改 HelpController.cs 並添加以下方法:

using System.Collections.ObjectModel;

private Collection<ApiDescription> FilteredDescriptions()
{
    var descriptionsToShow = new Collection<ApiDescription>();

    foreach (var apiDescription in Configuration.Services.GetApiExplorer().ApiDescriptions)
    {
        var actionDescriptor = apiDescription.ActionDescriptor as ReflectedHttpActionDescriptor;
        var authAttribute = actionDescriptor?.MethodInfo.CustomAttributes.FirstOrDefault(x => x.AttributeType.Name == nameof(System.Web.Http.AuthorizeAttribute));
        var roleArgument = authAttribute?.NamedArguments?.FirstOrDefault(x => x.MemberName == nameof(System.Web.Http.AuthorizeAttribute.Roles));
        var roles = roleArgument?.TypedValue.Value as string;
        if (roles?.Split(',').Any(role => User.IsInRole(role.Trim())) ?? false)
        {
            descriptionsToShow.Add(apiDescription);
        }
    }
    return descriptionsToShow;
}

並從 Index() 操作調用它:

return View(FilteredDescriptions());

這可以在剃刀視圖中實現,如下所示將是您所需要的。

 @if (User.IsInRole("admin"))
 {
     <div>
         <!--Text for admin here-->
     </div>
 }
 @if (User.IsInRole("user"))
 {
     <div>
         <!--Text for user here-->
     </div>
 }

可以在 WebApi 控制器中使用相同的邏輯

public string Get()
{
    if(User.IsInRole("admin"))
    {
        return "Text for admin";
    }

    if(User.IsInRole("user"))
    {
        return "Text for user";
    }
}

基於 Stanislav 的方法,我添加了對AllowAnonymous 、基於用戶名的授權、控制器屬性和全局授權過濾器的支持。

public ActionResult Index()
{
    ViewBag.DocumentationProvider = Configuration.Services.GetDocumentationProvider();
    //return View(Configuration.Services.GetApiExplorer().ApiDescriptions);
    return View(FilteredDescriptions());
}

private Collection<ApiDescription> FilteredDescriptions()
{
    var list = Configuration.Services.GetApiExplorer().ApiDescriptions
        .Where(apiDescription =>
        {
            // action attributes
            if (apiDescription.ActionDescriptor.GetCustomAttributes<AllowAnonymousAttribute>().Count != 0)
            {
                return true;
            }

            var actionAuthorizeAttributes = apiDescription.ActionDescriptor.GetCustomAttributes<AuthorizeAttribute>();

            if (actionAuthorizeAttributes.Count != 0)
            {
                return actionAuthorizeAttributes.All(IsUserAuthorized);
            }

            // controller attributes
            if (apiDescription.ActionDescriptor.ControllerDescriptor.GetCustomAttributes<AllowAnonymousAttribute>().Count != 0)
            {
                return true;
            }

            var controllerAuthorizeAttributes = apiDescription.ActionDescriptor.ControllerDescriptor.GetCustomAttributes<AuthorizeAttribute>();

            if (controllerAuthorizeAttributes.Count != 0)
            {
                return controllerAuthorizeAttributes.All(IsUserAuthorized);
            }

            // global attributes
            if (apiDescription.ActionDescriptor.Configuration.Filters.OfType<AllowAnonymousAttribute>().Any())
            {
                return true;
            }

            var globalAuthorizeAttributes = apiDescription.ActionDescriptor.Configuration.Filters.OfType<AuthorizeAttribute>().ToList();

            if (globalAuthorizeAttributes.Count != 0)
            {
                return globalAuthorizeAttributes.All(IsUserAuthorized);
            }

            return true;
        })
        .ToList();

    return new Collection<ApiDescription>(list);
}

private bool IsUserAuthorized(AuthorizeAttribute authorizeAttribute)
{
    return User.Identity.IsAuthenticated
        && (authorizeAttribute.Roles == "" || authorizeAttribute.Roles.Split(',').Any(role => User.IsInRole(role.Trim())))
        && (authorizeAttribute.Users == "" || authorizeAttribute.Users.Split(',').Any(user => User.Identity.Name == user));
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM