This is a combined reply to the questions raised by both cmlenz and
cboos.
On Wed, 2006-01-25 at 17:12, Christopher Lenz wrote:
> In general I think you need to provide more info here. I'm pretty
> sure we don't want a huge complicated access control system that has
> all kinds of different options for limiting access.
A security system that nobody can understand or use is a boat anchor,
not security system. By virtue of its purpose, the system will have to
be simple to use.
> A combination of RBAC and LBAC actually sounds pretty nice. I'm not
> sure about the others...
cboos brings up a number of tickets requesting this-or-that kind of
fine-grained discretionary access control. In my first email, I made a
list of features to be included in a real security subsystem. Role-based
and label-based access control I think everyone understands.
RBAC allows you to assign capabilities on an entity to a list of roles.
That is, you can say "role xyz has write access on /some/wiki/page".
Label-based access control puts a tag on a resource, and actions on
labels can be assigned to principals (set label ReallySecretStuff on
ticket:134; let user puffy see ReallySecretStuff).
At this point, I should state that a 'resource' in the Trac context is
the same as an 'entity'. An 'entity' is any wiki page, ticket,
milestone, or other information object to which trac gives a user
access.
The "Mandatory Access Control" that I mentioned in my previous email
trips over the trusted-system definition of MAC and gloms some things
together inappropriately. We can divide this into two parts:
Part 1: Non-Circumventable Access Control:
Requirement: It must not be possible for a Component (read: malicious
(or clueless) plugin to circumvent the security system.
Consequence 1: Access control must be implemented as close to the data
access layer as possible.
Consequence 2: It must not be possible to acquire a reference to the
SecuritySystem component, then redefine its methods, thus bypassing the
system entirely.
Part 2: Mandatory Access Control:
Requirement: It should not be possible for an owner of an entity to
assign to an entity access controls more permissive than the system
security policy.
Explanation: If a Trac Admin declares that tickets may only be read by
authenticated principals, it should not be possible for the ticket owner
to allow anonymous access to his ticket.
SecureComponents become a logical necessity brought about by the
intended non-circumventability of the system. The security system needs
to be a black box.
The idea of a SecurityAdministrator role would prevent operators of a
trac production system from being able to change the security policy of
the system. This is mostly theoretical right now.
If one is controlling access to entities, one wants to make absolutely
sure a principal can't access something he shouldn't, and failing that,
should know that he has. An event auditor would sit at the data access
layer (like the access control system) and log everything that is done
to the database.
> It's essential to keep in mind that Trac is lightweight, and by all
> means intended to remain lightweight. While in the long-term we'll
> need some way to allow people to have some wiki pages / tickets only
> readable/modifiable/etc by some groups of people, an acceptable
> solution needs to be reasonably flexible but simple. Per-entity ACLs
> are something that I personally think is overkill, for example.
Doing any sort of access control is non-trivial, and the devil is in the
details. If we want a simple implementation of the access control
system, then we heap a lot of complexity upon the client (say, making
trac.wiki.web_ui do access control...). If we want simplicity for the
client, then the implementation is going to be somewhat complicated.
Let me be clear by saying that I intend to make the security system as
transparent to the programmer as possible (to the point where a naive
Component written for trac 0.9's security model should still function
(with a few minor changes, maybe) while allowing aware components full
access to a powerful security system.
To put it more concisely, unless you want to use the access control
system or touch an entity that's access-controlled, you don't need to
even know it's there. And if you do, it's not going to be much different
than the way things are now.
> Consider this a request for more detail. And some pseudo-code
> snippets showing *how* you actually intend to implement this would
> also be nice.
Are you more interested in how the security system is going to be
written, or how a client will interact with it?
Imagine a simplified Wiki viewer:
class StupidWiki(SecureComponent):
resource_identifier = stupidwiki
def match_request(self, req):
pname = extract_page_name(req)
if (self.acs.authorize(self, pname, req.authname, 'READ'):
req[pagename] = extract_page_name(req)
return 1
def process_request(self, req):
self.acs.assert_authorized(self, req, 'READ')
db = self.db.get_cxn(princ=req.authname, caller=self)
<...build HDF...>
self.acs.supplement_hdf() #This is because of the trac.ACL stuff
#in the templates (may never need)
return wiki.cs, None
def _get_acs(self):
return AccessControlSystem(self.env)
acs = property(self._get_acs)
This is the level of programmer complexity I'm envisioning.
At the data access layer, say:
create_dbhandle_for_principal(princ)
get_request(sqlstatement)
if_uses_advanced_access_control(caller)
transform(sqlstatement) #make access aware query
return execute(sqlstatement)
Anything more precise that I'd write a priori about implementation
details are destined to be wrong.
I welcome your feedback.
Cheers,
-Jesse Kempf
_______________________________________________
Trac-dev mailing list
[email protected]
http://lists.edgewall.com/mailman/listinfo/trac-dev