ABP框架系列之十三:(Authorization-授權)


Introduction

Almost all enterprise applications use authorization in some level. Authorization is used to check if a user is allowed to perform some specific operation in the application. ASP.NET Boilerplate defines a permission basedinfrastructure to implement authorization.

幾乎所有的企業應用程序使用授權
授權被用來檢查用戶是否被允許一些具體操作中的應用。
ASP.NET的模板定義實現授權許可基礎的接口。

About IPermissionChecker

Authorization system uses IPermissionChecker to check permissions. While you can implement it in your own way, it's fully implemented in module-zero project. If it's not implemented, NullPermissionChecker is used which grants all permissions to everyone.

授權系統使用ipermissionchecker to檢查權限。當你實現它自己的方式,這是完全implemented in模塊零的項目。
如果不實現,nullpermissionchecker被用來定義所有人的權限。

Defining Permissions

A unique permission is defined for each operation needed to be authorized. We should define a permission before use it. ASP.NET Boilerplate is designed to be modular. So, different modules can have different permissions. A module should create a class derived from AuthorizationProvider in order to define it's permissions. An example authorization provider is shown below:

為每個需要授權的操作定義唯一的權限。在使用許可之前,我們應該定義它。ASP.NET樣板的設計是模塊化的。因此,不同的模塊可以有不同的權限。一個模塊應該創建一個派生類從AuthorizationProvider來定義它的權限。下面給出一個示例授權提供者:

public class MyAuthorizationProvider : AuthorizationProvider
{
    public override void SetPermissions(IPermissionDefinitionContext context)
    {
        var administration = context.CreatePermission("Administration");

        var userManagement = administration.CreateChildPermission("Administration.UserManagement");
        userManagement.CreateChildPermission("Administration.UserManagement.CreateUser");

        var roleManagement = administration.CreateChildPermission("Administration.RoleManagement");
    }
}
			

IPermissionDefinitionContext has methods to get and create permissions.

A permission have some properties to define it:

  • Name: a system-wide unique name. It's good idea to define a const string for a permission name instead of a magic string. We prefer to use . (dot) notation for hierarchical names but it's not required. You can set any name you like. Only rule is that it must be unique.
  • 系統范圍唯一名稱。為一個權限名稱而不是一個字符串定義一個const字符串是個好主意。我們更喜歡使用。層次結構名稱的(點)符號,但不是必需的。您可以設置任何您喜歡的名稱。唯一的規則是它必須是唯一的。
  • Display name: A localizable string that can be used to show permission, later in UI.
  • 可本地化的字符串,可以用來顯示權限,后來在UI。
  • Description: A localizable string that can be used to show definition of the permission, later in UI.
  • 可本地化的字符串,可以用來顯示權限定義,在以后的UI。
  • MultiTenancySides: For multi-tenant application, a permission can be used by tenants or the host. This is a Flags enumeration and thus a permission can be used in both sides.
  • 對於多租戶應用程序,租戶或主機可以使用權限。這是一個枚舉標記,因此可以在兩邊使用權限。
  • featureDependency: Can be used to declare a dependency to features. Thus, this permission can be granted only if feature dependency is satisfied. It waits for an object implements IFeatureDependency. Default implementation is the SimpleFeatureDependency class. Example usage: new SimpleFeatureDependency("MyFeatureName")
  • 可以用來聲明對特性的依賴關系。因此,只有在滿足特性依賴時才能授予此權限。它在等待一個對象實現ifeaturedependency。默認的實現是simplefeaturedependency類。使用示例:新simplefeaturedependency(“myfeaturename”)

A permission can have a parent and child permissions. While this does not effect permission checking, it may help to group permissions in UI.

After creating an authorization provider, we should register it in PreInitialize method of our module:

權限可以具有父級和子級權限。雖然這不影響權限檢查,但它可能有助於在用戶界面中分組權限。

在創建一個授權商,我們應該登記在分發我們的模塊的方法:

Configuration.Authorization.Providers.Add<MyAuthorizationProvider>();

Authorization providers are registered to dependency injection automatically. So, an authorization provider can inject any dependency (like a repository) to build permission definitions using some other sources.

授權提供者自動注冊到依賴注入。因此,授權提供者可以注入任何依賴項(如存儲庫)以使用其他來源構建權限定義。

Checking Permissions(檢查權限

Using AbpAuthorize Attribute

AbpAuthorize (AbpMvcAuthorize for MVC Controllers and AbpApiAuthorize for Web API Controllers) attribute is the easiest and most common way of checking permissions. Consider the application service method shown below:

abpauthorize(abpmvcauthorize用於Web API控制器MVC控制器和abpapiauthorize)檢查權限屬性是最簡單、最常用的方式。考慮下面所示的應用程序服務方法:

[AbpAuthorize("Administration.UserManagement.CreateUser")]
public void CreateUser(CreateUserInput input)
{
    //A user can not execute this method if he is not granted for "Administration.UserManagement.CreateUser" permission.
}

CreateUser method can not be called by a user who is not granted for permission "Administration.UserManagement.CreateUser".

AbpAuthorize attribute also checks if current user is logged in (using IAbpSession.UserId). So, if we declare an AbpAuthorize for a method, it only checks for login:

[AbpAuthorize]
public void SomeMethod(SomeMethodInput input)
{
    //A user can not execute this method if he did not login.
}
AbpAuthorize attribute notes

ASP.NET Boilerplate uses power of dynamic method interception for authorization. So, there is some restrictions for the methods use AbpAuthorize attribute.

ASP.NET樣板使用授權的動態方法攔截能力。所以,有一些限制使用的方法abpauthorize屬性。

  • Can not use it for private methods.
  • Can not use it for static methods.
  • Can not use it for methods of a non-injected class (We must use dependency injection).

Also,

  • Can use it for any public method if the method is called over an interface (like Application Services used over interface).
  • A method should be virtual if it's called directly from class reference (like ASP.NET MVC or Web API Controllers).
  • A method should be virtual if it's protected.

Notice: There are four types of authorize attributes:

  • In an application service (application layer), we use Abp.Authorization.AbpAuthorize attribute.
  • In an MVC controller (web layer), we use Abp.Web.Mvc.Authorization.AbpMvcAuthorize attribute.
  • In ASP.NET Web API, we use Abp.WebApi.Authorization.AbpApiAuthorize attribute.
  • In ASP.NET Core, we use Abp.AspNetCore.Mvc.Authorization.AbpMvcAuthorize attribute.

This difference comes from inheritance. In application layer it's completely ASP.NET Boilerplate's implementation and does not extend any class. But, int MVC and Web API, it inherits from Authorize attributes of those frameworks.

這種差異來自於繼承。在應用層,它是完全ASP.NET樣板的實施並沒有擴展任何類。但是,MVC和Web API繼承了這些框架的授權屬性。

Suppress Authorization(禁止授權

You can disable authorization for a method/class by adding AbpAllowAnonymous attribute to aplication services. Use AllowAnonymous for MVC, Web API and ASP.NET Core Controllers, which are native attributes of these frameworks.

您可以通過添加abpallowanonymous屬性應用服務禁用方法/類授權。使用allowanonymous MVC,Web API和ASP.NET的核心控制器,這是這些框架固有的屬性。

Using IPermissionChecker

While AbpAuthorize attribute pretty enough for most cases, there must be situations we should check for a permission in a method body. We can inject and use IPermissionChecker for that as shown in the example below:

而abpauthorize屬性多數情況下不夠漂亮,必須有情況我們應該檢查在方法體的權限。我們可以注入用IPermissionChecker,如以下示例所示:

public void CreateUser(CreateOrUpdateUserInput input)
{
    if (!PermissionChecker.IsGranted("Administration.UserManagement.CreateUser"))
    {
        throw new AbpAuthorizationException("You are not authorized to create user!");
    }

    //A user can not reach this point if he is not granted for "Administration.UserManagement.CreateUser" permission.
}

Surely, you can code any logic since IsGranted simply returns true or false (It has Async version also). If you simply check a permission and throw an exception as shown above, you can use the Authorize method:

當然,你可以從任何代碼邏輯簡單得返回TRUE或FALSE(具有異步版本)。如果只檢查權限並拋出一個異常,如上所示,您可以使用授權方法:

public void CreateUser(CreateOrUpdateUserInput input)
{
    PermissionChecker.Authorize("Administration.UserManagement.CreateUser");

    //A user can not reach this point if he is not granted for "Administration.UserManagement.CreateUser" permission.
}

Since authorization is widely used, ApplicationService and some common base classes inject and define PermissionChecker property. Thus, permission checker can be used without injecting in application service classes.

由於授權的應用非常廣泛,應用服務和一些常見的基類定義屬性注入和PermissionChecker。因此,可以在不注入應用程序服務類的情況下使用權限檢查器。

In Razor Views

Base view class defines IsGranted method to check if current user has a permission. Thus, we can conditionally render the view. Example:

View基類定義檢查當前用戶有權限的權限的方法。因此,我們可以有條件地呈現視圖。例子:

@if (IsGranted("Administration.UserManagement.CreateUser"))
{
    <button id="CreateNewUserButton" class="btn btn-primary"><i class="fa fa-plus"></i> @L("CreateNewUser")</button>
}

Client Side (Javascript)(客戶端

In the client side, we can use API defined in abp.auth namespace. In most case, we need to check if current user has a specific permission (with permission name). Example:

在客戶端,我們可以使用API在abp.auth命名空間定義。在大多數情況下,我們需要檢查當前用戶是否有特定的權限(使用權限名稱)。例子:

abp.auth.isGranted('Administration.UserManagement.CreateUser');

You can also use abp.auth.grantedPermissions to get all granted permissions or abp.auth.allPermissions to get all available permission names in the application. Check abp.auth namespace on runtime for others.

你也可以使用abp.auth.grantedpermissions得到所有授予的權限或abp.auth.allpermissions中獲得所有可用的權限名稱。檢查abp.auth命名空間在運行時為他人。

Permission Manager(權限管理

We may need to definitions of permission. IPermissionManager can be injected and used in that case.


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM