Documentation ¶
Overview ¶
Package perm provides authorization testing functions based on permission sets.
Index ¶
- type Condition
- type Implication
- type ImplicationSet
- type Object
- type Ownable
- type Permission
- type PermissionSet
- func (ps PermissionSet) AllowsVerbObj(verb string, obj Object) bool
- func (ps PermissionSet) ApplyImplication(impl Implication)
- func (ps PermissionSet) ApplyImplications(is ImplicationSet)
- func (ps PermissionSet) Copy() PermissionSet
- func (ps PermissionSet) Has(name string, minLevel int) bool
- func (ps PermissionSet) Meets(c Condition) bool
- func (ps PermissionSet) Merge(permission Permission)
- func (ps PermissionSet) Positive(name string) bool
- func (ps PermissionSet) String() string
- type Policy
- type VerbPolicy
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type Condition ¶
type Condition struct { // The permission which the condition requires. Name string // The minimum level of the permission (greater than or equal to). MinLevel int }
A Condition represents some sort of predicate applied to an actor's permission set.
While it currently has the same fields as Permission, it is a different structure because the semantics of the fields are different; MinLevel is greater-than-or-equal-to matched to the Level of a Permission.
func ParseCondition ¶
Parse a condition string such as "some-permission(5)".
type Implication ¶
type Implication struct { // The Condition which must be met in order for the Implication to apply. Condition Condition // The Permission which is merged with a PermissionSet if the Implication // applies. ImpliedPermission Permission }
An implication represents a permission which can be implied by a condition (that is, by another permission).
If the Condition is met, ImpliedPermission is implied. The ImpliedPermission will be merged with the PermissionSet, which means that ImpliedPermission will only raise the level of that permission, not lower it.
func (*Implication) String ¶
func (impl *Implication) String() string
Returns a string representation of the implication in the form "condition => implied-permission", e.g. "foo(5) => bar(10)".
type ImplicationSet ¶
type ImplicationSet []Implication
A set of implications.
func LoadImplicationsFromFile ¶
func LoadImplicationsFromFile(filename string) (ImplicationSet, error)
Load implications in the textual form from a file.
func ParseImplications ¶
func ParseImplications(implications string) (ImplicationSet, error)
Parses an implications string such as "a(1) => b(2), c(3) => d(4)".
Implications may be separated by commas or newlines.
func (ImplicationSet) String ¶
func (is ImplicationSet) String() string
Returns a comma separated list of stringized Implications.
type Object ¶
type Object interface { // Return the security policy for this object or nil if no security policy // is assigned. PermPolicy() Policy }
An object which can reference a security policy.
type Ownable ¶
type Ownable interface { // Returns the owner ID. The owner ID should have a sensible string form. // // Return (nil, false) if no owner ID is assigned. PermOwner() (ownerID interface{}, ok bool) }
An object which may have an owner.
type Permission ¶
type Permission struct { // The permission name. Name string // The permission level. Aabsent permissions default to level 0, present // permissions default to level 1. Level int }
A Permission is a label which may be possessed by some manner of actor. The authorization of a user to take actions depends on the Permissions they have.
Each permission is comprised of a name and a level, written as "name(level)". For example, Permission{ Name: "admin", Level: 10, } can be written in this shorthand as "admin(10)".
Stating that an actor must have the permission "foo(5)" means that their foo permission must exist and have a level greater than or equal to 5.
An actor is considered to have all permissions they don't have as level 0. The default level for a permission an actor is granted is generally level 1. Thus for most permissions, checking whether a permission is positive is an effective way of checking whether an actor has that permission.
Do not make "negative" permissions like "banned". Instead, make a positive permission like "can-access" with a negative level. Then "can-access(0)" is necessary to access a service. Explicitly assign banned actors "can-access(-1)".
Permission names should conventionally be formed using lowercase letters, numbers and hyphens, not underscores. The actually permitted set of characters is larger than this; underscores, dots and colons characters are allowed.
func ParsePermission ¶
func ParsePermission(permission string) (Permission, error)
Parse a permission string such as "some-permission(5)".
func (*Permission) String ¶
func (p *Permission) String() string
Returns a string in the form "name(level)".
type PermissionSet ¶
type PermissionSet map[string]Permission
A permission set is a set of permissions held by an actor.
(The invariant s[k].Name == k for all k in permission set s must be maintained at all times.)
func (PermissionSet) AllowsVerbObj ¶
func (ps PermissionSet) AllowsVerbObj(verb string, obj Object) bool
Tests whether a permission set allows a given verb to be performed on a given object.
If the object can nominate a security policy, that policy is used. Otherwise, condition VERB(1) is checked for, where VERB is the verb name given.
func (PermissionSet) ApplyImplication ¶
func (ps PermissionSet) ApplyImplication(impl Implication)
Conditionally apply a given implication.
func (PermissionSet) ApplyImplications ¶
func (ps PermissionSet) ApplyImplications(is ImplicationSet)
Apply a set of implications.
func (PermissionSet) Copy ¶
func (ps PermissionSet) Copy() PermissionSet
Makes a copy of the permission set.
func (PermissionSet) Has ¶
func (ps PermissionSet) Has(name string, minLevel int) bool
Returns true if the permission set contains a permission with the given name and a level greater than or equal to the given level.
Note: If level less than or equal to 0, returns true if the user does not have the permission set.
func (PermissionSet) Meets ¶
func (ps PermissionSet) Meets(c Condition) bool
Returns true iff the condition is met.
func (PermissionSet) Merge ¶
func (ps PermissionSet) Merge(permission Permission)
Merges a permission into a permission set. If the permission does not exist in the set, it is added. If the permission already exists, its level will be raised if the new permission has a higher level; otherwise, nothing is changed.
func (PermissionSet) Positive ¶
func (ps PermissionSet) Positive(name string) bool
Returns true iff the permission set contains the permission with the given name with a positive level.
func (PermissionSet) String ¶
func (ps PermissionSet) String() string
type Policy ¶
type Policy interface { // Returns true iff the policy allows the given verb to be carried out given // the given PermissionSet and object. obj may be nil. The meaning of this // depends on the policy. AllowsVerbObj(verb string, ps PermissionSet, obj interface{}) bool }
Policy represents a policy which may be nominated by objects under access control. It can authorize or deny an action based on the actor (permission set), object (if specified) and the verb being performed.
type VerbPolicy ¶
A simple policy based on mapping verb names to conditions.
If a verb is not specified in the map, the condition VERB(1) is used, where VERB is the verb name.
Also supports ownership semantics: if a verb nominates a condition with name "owner", that condition is substituted for a condition "user-id:OWNER-ID(1)", where OWNER-ID is string form of the the owner ID of the object being accessed. If no object is specified, or the object does not express an owner, ownership-based checks fail.
func (*VerbPolicy) AllowsVerbObj ¶
func (p *VerbPolicy) AllowsVerbObj(verb string, ps PermissionSet, obj interface{}) bool
Returns true iff the policy allows the given verb to be carried out given the given PermissionSet.
If an object is given and supports the Ownable interface, and it nominates an owner ID, and the verb requires ownership, returns true if the "user-id:OWNER-ID(1)" condition is met, where OWNER-ID is the string representation of the owner ID. (The idea is that you axiomatically assign every user the permission "user-id:USER-ID(1)", where USER-ID is their user ID.)
obj may be nil, in which case owner-based checks fail.