Authorization rules determine who can create facts.
They are defined in the JinagaConfig
class.
Even though the rules are defined within the client, they are enforced by the replicator.
Add a static method to the JinagaConfig
class called Authorization
.
This method should return a string that describes the authorization rules.
Build authorization rules from your model.
public static class JinagaConfig
{
public static string Authorization() =>
AuthorizationRules.Describe(Authorize);
private static AuthorizationRules Authorize(AuthorizationRules r) => r
.Any<User>()
.Type<UserName>(name => name.user)
.Type<Site>(site => site.creator)
.Type<SiteName>(name => name.site.creator)
.Type<SiteDomain>(domain => domain.site.creator)
.Type<Post>(post => post.site.creator)
.Type<PostTitle>(title => title.post.site.creator)
.Type<PostDeleted>(deleted => deleted.post.site.creator)
.Type<Publish>(publish => publish.post.site.creator);
}
The Type
method defines the user who can create a fact of a given type.
It is common for this user to be a predecessor of the fact.
In that case, a lambda expression follows the graph to the predecessor.
Sometimes the authorized user is related through a successor. This happens when the original creator grants permission to another user. To express this kind of rule, the lambda expression takes two parameters: the fact being created and the fact repository.
.Type<Post>((post, facts) =>
from guestBlogger in facts.OfType<GuestBlogger>()
where guestBlogger.site == post.site
from user in facts.OfType<User>()
where user == guestBlogger.guest
select user
)
Type rules can be combined. If more than one rule is given, then a user matching any of the rules is authorized to create the fact.
The Any
method allows any user to create a fact of a given type.
It is common for the User
fact to be created by any user.
The User
fact has only a public key.
Several patterns require a person to create a User
fact representing another person so that they can initiate a conversation.
The No
method describes a fact that no user can create.
This method is rarely used.
The With
method chains rule sets.
This is useful when breaking a model into modules.
public static class SiteModule
{
public static AuthorizationRules Authorize(AuthorizationRules r) => r
.Type<Site>(site => site.creator)
.Type<SiteName>(name => name.site.creator)
.Type<SiteDomain>(domain => domain.site.creator);
}
public static class JinagaConfig
{
private static AuthorizationRules Authorize(AuthorizationRules r) => r
.Any<User>()
.Type<UserName>(name => name.user)
.With(SiteModule.Authorize)
.With(PostModule.Authorize);
}
To deploy authorization rules to a hosted replicator, use the dotnet jinaga
command line tool.
Install the tool by running the following command.
dotnet tool install -g Jinaga.Tool
Then run the following command to deploy the authorization rules to a hosted replicator.
dotnet jinaga deploy authorization {assembly} {endpoint} {secret}
The {assembly}
parameter is the path to the assembly containing the JinagaConfig
class.
You can find the endpoint and secret in the replicator's configuration.
If instead you are running your own replicator, run the following command to write the authorization rules to a file.
dotnet jinaga print authorization {assembly} > authorization.txt