GranularPermissions 1.0.5
dotnet add package GranularPermissions --version 1.0.5
NuGet\Install-Package GranularPermissions -Version 1.0.5
<PackageReference Include="GranularPermissions" Version="1.0.5" />
<PackageVersion Include="GranularPermissions" Version="1.0.5" />
<PackageReference Include="GranularPermissions" />
paket add GranularPermissions --version 1.0.5
#r "nuget: GranularPermissions, 1.0.5"
#:package GranularPermissions@1.0.5
#addin nuget:?package=GranularPermissions&version=1.0.5
#tool nuget:?package=GranularPermissions&version=1.0.5
GranularPermissions
The world's most over-engineered permissions system.
Supports net5.0.
Features
- Generic nodes (not tied to a resource)
- Resource-bound nodes, evaluated with respect to a particular resource marked
IPermissionManaged - Simple chains allow/deny grants with respect to an identifier (e.g. user ID)
- Evaluated one after each other in order of provided
Indexto come up with a final pass/fail answer
- Evaluated one after each other in order of provided
- Default disallow policy if no matching grants
- Complex resource-bound grants using a DSL which is compiled into AST transformation at startup and then evaluated at runtime
- AspNetMvc (Core) extensions for registering services, logging permissions for debugging etc
Terminology
- Node: A permission entry. Something that can be done that needs its access controlled.
- These have a key which by convention is represented as
EntityName.[SubGroup].Action.
- These have a key which by convention is represented as
- Grants: Allow/deny rules that cover a single permission node. Can be typed as
GenericorResourceBound. - ResourceBound grant: Evaluation of the grant must be performed in the context pf a resource.
- For example,
Product.Editprobably requires the product in question to be considered when checking to see if the user should have the permission or not.
- For example,
- Generic grant: Does not require a resource when evaluating. E.g.
Product.Create. - Chain: grants are organised into chains and have identifiers within a chain. When nodes are checked, all
grants that match the identifier in the specified chain are considered.
- Example chains:
GroupsorUsers - Example identifiers:
Group IDorUser ID
- Example chains:
- Condition: An additional requirement on top of a ResourceBound grant. Written in a DSL for this permissions system.
DSL examples
new Cat
{
Breed = CatBreed.Bengal,
Age = 10,
Name = "Felix"
}
You could write some conditions for a resource bound grant on node Cat.Adopt:
resource.Name == "Felix" || resource.Age < 10
resource.Age != 5
Supported operators: <=, >=, <, >, &&, ||, ., ==, !=, !, ~= (regex)
Usage
From an ASP.NET MVC Core project, in ConfigureServices in Startup.cs:
services.AddScoped<IPermissionGrantProvider, SomePermissionGrantProvider>();
services.AddGranularPermissions(typeof(Permissions));
SomePermissionGrantProvider must implement IPermissionGrantProvider. Its role is to
return all grants (which implement IPermissionGrantSerialized) persisted in the system.
You may wish to retrieve them from a database, for instance.
The Permissions class must define all permission nodes you wish to exist in your project:
public static class Permissions
{
public static class Product
{
public static readonly ResourceNode<ProductModel> View =
new ResourceNode<ProductModel>("Product.View", "View an individual product");
public static readonly GenericNode Create =
new GenericNode("Product.Create", "Create a product");
public static readonly ResourceNode<ProductModel> Buy =
new ResourceNode<ProductModel>("Product.Purchase", "Purchase an individual product");
}
public static class Cat
{
public static readonly ResourceNode<ProductModel> Pet =
new ResourceNode<ProductModel>("Cat.Pet", "Pet the cat without being bitten/scratched");
public static readonly GenericNode Adopt =
new GenericNode("Cat.Adopt", "Be adopted by a cat");
}
}
To check a permission within a specified chain, call GetResultUsingChain on the IPermissionsService instance which will return a PermissionResult (Unset, Allow or Deny).
It is possible to reload the grants at runtime by calling ReplaceAllGrants with a new IEnumerable<IPermissionGrantSerialized>.
Example use-case
A web application has two groups which have different levels of access. Group 1 is for "Everyone" and includes a basic level of permission grants. Group 2, "Administrators" includes a higher level of access for a subset of application users who are in this group.
Within GranularPermissions, you'd have:
- One chain,
"Groups" - A set of
IPermissionGrantSerializedfor the "Groups" chain with Identifier=1. These will apply to all users in the Everyone group. - A set of
IPermissionGrantSerializedfor the "Groups" chain with Identifier=2. These will apply to all users in the Administrators group. - Some
IPermissionGrantProviderwhich returns the aforementionedIPermissionGrantSerializedinstances from DB
A simple permissions checker would call GetResultUsingChain("Groups", Permissions.Node.ToCheck, groupId) for each of the user's groups and then aggregate the results to come up with a final allowed/denied result. For example, the administrators group may be considered a higher priority than the everyone group.
For resource bound nodes, it's simply a case of passing an additional argument GetResultUsingChain("Groups", Permissions.Node.ToCheckWithResource, groupId, resourceToCheckAgainst).
TODO
- Add ability to register DSL functions/identifiers
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net5.0 is compatible. net5.0-windows was computed. net6.0 was computed. net6.0-android was computed. net6.0-ios was computed. net6.0-maccatalyst was computed. net6.0-macos was computed. net6.0-tvos was computed. net6.0-windows was computed. net7.0 was computed. net7.0-android was computed. net7.0-ios was computed. net7.0-maccatalyst was computed. net7.0-macos was computed. net7.0-tvos was computed. net7.0-windows was computed. net8.0 was computed. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 was computed. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 was computed. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net5.0
- Loyc.Syntax (>= 26.8.1)
NuGet packages (1)
Showing the top 1 NuGet packages that depend on GranularPermissions:
| Package | Downloads |
|---|---|
|
GranularPermissions.Mvc
ASP.NET Core MVC integration for GranularPermissions. |
GitHub repositories
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 1.0.5 | 1,566 | 5/16/2021 |
| 1.0.3 | 2,473 | 6/14/2019 |
| 1.0.2-beta | 1,456 | 8/23/2018 |
| 1.0.1-beta | 945 | 8/14/2018 |
| 1.0.0-beta | 1,491 | 4/16/2018 |
| 0.0.5-alpha | 1,403 | 4/16/2018 |
| 0.0.4-alpha | 1,466 | 3/21/2018 |
| 0.0.3-alpha | 1,465 | 3/20/2018 |
| 0.0.2-alpha | 1,449 | 3/20/2018 |
| 0.0.1-alpha | 1,540 | 3/19/2018 |