[kforge-dev] access control
John Bywater
john.bywater at appropriatesoftwarefoundation.org
Thu Jan 12 21:52:08 UTC 2006
[written to clarify my own understanding - I've been reworking the code
and I think I've worked it out :-)]
So, after a discussion today [now yesterday] regarding access control
between Rufus and I, I thought I'd try to write a narrative of the
access control scenario based on Rufus's design.
Plot summary (indents mean 'sub-plot'). -
- log in person
- browse pages
- make request
- handle request
- authorise person for action on object
- check system-wide role permissions
- if project view: check project role for permissions
- take (or refuse) action on object
A person logins in with the intention of taking an action against a
domain object. -
This creates a session, which is available as "self.session" on all kui
views. (If session isn't True, then there isn't a logged in user for the
request. A reference to the person is "self.session.person" on all kui
views.)
A person browses various pages of the system. -
(How can the system control actions taken by people on the system's
domain objects?)
In general, we want to control access to domain objects by considering
the action to be taken, the person requesting the action, and the object
(domain object or domain object class) that will receive the action.
As a policy, we want to deny action, unless the person who requests the
action has sufficient permission.
So we also want to have permissions, which allow an action to be taken
on a particular set of protected domain objects.
We want to grant permissions to roles, and associate people with roles.
We want to say that a person has a particular permission if any of the
roles they are associated with has that permission.
We want to protect domain objects. We want to protect domain objects
with protection objects. We want a protection object to be responsible
for knowing about the domain objects it protects, and we want a
protection object to be capable of reporting whether it protects an
object (domain object or domain object class) or not.
So, in general, and at first, we can associate a person directly with a
role, and attempt to authorise access by checking whether an acting
person's role has permission (for the requested action to be taken on
the object that will receive the action). This direct association of a
person with a role could be known as a person's "system role".)
Secondly, by providing memberships of projects to people, and
associating each membership with a role, we can associate a person with
more than one role.
Additionally, by creating an administration project with special
administration services, controlled access to administration features
can be provided.
At this point, there are two rather underdesigned concerns:
Firstly, there is a question concerning how a protection object knows of
the objects that it protects. Or, perhaps better, there is a question
concerning how a protection object records the set of domain objects it
protects.
Secondly, there is a question concerning the composition of permissions
granted by the different associations. A system role seems to pertains
to all the objects within the system. A project role seems to pertain to
all the objects within a project in the system. An administration
project role seems to pertain to all the objects that are operated on by
the services of the administration, so this might mean all the objects
within the system, according to the technical capabilities of the
administration project services.
A person's browser makes a request on the servier. -
Let's say that the requests made whilst browsing will be handled with
request handlers. In KForge, request handlers are methods on kui view
objects. The handler is responsible for initiating the action to be
taken in response to the request. The handler is also responsible for
having, in the terms of the access control system, a name for the action
it takes.
It should be noted that we can't prevent direct access in the code to
the domain model. So we must require that request handlers cooperate
with the access control system by asking it for proper permission before
acting.
A request handler is also responsible for knowing, again in the terms of
the access control system, what domain objects it acts on.
A handler requests authorisation for a person to act on an object. -
The handler knows: the acting person (as "self.session.person"), the
action (as "self.actionName"), and the object (domain object or domain
object class) to receive the action.
Therefore it must be on this basis that authorisation to act is
requested. And it may be that a handler makes a series of authorisation
requests to the access control system.
A handler may seek several authorisations, e.g. to read a project, to
read members of a project, and to create a member of that project.
Therefore, it seems that a handler wants to ask an access controller
whether a person has permission to take a named action on an object.
Additionally, because of the project-membership-role-permissions
feature, it would seem that a request handler is obliged to tell the
access controller whether the handler is part of a project view, and if
so which project is being viewed.
I suggest the following method:
AccessController.authorise(person, actionName, object, project=None)
The authorise method: firstly examines the system wide role (iterating
through permissions to see whether a permission exists for that
actionName, and if so, whether that permission's protection object
protects the object; and secondly, if no permission has been found so
far and there is a project, examines the project role for a permission.
Access is allowed. -
Handler takes action on object. Respond normally.
Access is denied. -
Log details of failure. Respond with redirect to "permission denied" page.
More information about the kforge-dev
mailing list