On Thu, 03 Aug 2006 19:58:58 -0500, "L. Daniel Burr" <[EMAIL PROTECTED]> wrote:
On Thu, 03 Aug 2006 17:54:54 -0500, Valentino Volonghi aka Dialtone
<[EMAIL PROTECTED]> wrote:
I think this whole discussion is based on a misunderstanding.
I agree.
To me, the bottom line is this: If all you are ever going to do is build
web applications, then you will *never* see any real point in jumping
through all of cred's hoops (portal, avatar, mind, WTF?
Guard _should_ support single-sign-on systems like OpenID or Active Directory,
to minimize the number of passwords that users have to remember when
interacting with Twisted sites.
If it did, it would be a lot easier to sell some of the learning required to
use it well. But I think that we could do a lot to make the learning seem
easier: once over the initial hump, guard is not hard to use and the conceptual
design is very simple.
I just want a freaking username/password combo, secured by SSL, like almost
every other web app on Earth!).
Until we can address the prevelance of username/password systems, Guard should
pretty do what it does and get out of your way. I don't think that it should
present any additional difficulty due to the fact that it's trying to do more
than usernames and passwords: in fact, guard _ONLY_ supports usernames and
passwords right now. I think that interacting with it through a slightly
higher-level system like Mantissa is pretty easy, so some focus on a bit of
boilerplate to hide some of the more advanced details would be good.
Where people tend to get tripped up is the fact that Guard treats resources as
objects or capabilities, whereas the typical web mentality is to treat them as
files or functions. Despite the fact that it's a very common mentality, it
leads to atrocious, insecure code. I think we should be doing everything
possible to make the advantages of the guard model clear, and not providing a
bug-prone and flaky way to do authentication simply because it seems
comfortable and familiar.
I strongly believe that the capability-style authentication that guard provides
is significantly more secure than the typical crap that ends up in most web
applications. This has nothing to do with other protocols, except for the fact
that programmers writing code to speak other protocols don't have the baggage
of thinking of every chat room as a file on disk, or every email as a
stateless, universally accessible object which customizes itself on demand. In
a guard-style application, your resources look like this:
class NormalResource(...):
def __init__(self, userObj):
self.userObj = userObj
def child_lala(self):
return HarmlessResource(self.userObj.harmlessStuff)
class AdminResource(NormalResource):
def child_rootme(self):
return DestroyEverythingResource(self.userObj.stuffAllowedToDestroy)
def child_lala(self):
return NotQuiteHarmlessResource(self.userObj.harmlessStuff)
Whereas what most web developers, only recently dragged in from PHP, _want_ to
do is this:
ADMIN_USERNAMES = ['bob', 'jim', 'me']
class IDontKnowAnythingAboutEncapsulationResource(...):
def child_lala(self):
global PAGE_MODE
global HARMLESS_STUFF
global USERNAME
PAGE_MODE = 'harmless'
HARMLESS_STUFF = getHarmlessStuff(USERNAME)
if USERNAME.lower() in ADMIN_USERNAMES:
PAGE_MODE = 'not_quite_harmless'
return self
def child_rootme(self):
global PAGE_MODE
global ALLOW_DESTROY
PAGE_MODE = 'rootme'
global USERNAME
if USERNAME.lower() in ADMIN_USERNAMES:
ALLOW_DESTROY = getAllowedToDestroyStuff(USERNAME)
else:
PAGE_MODE = '404'
return self
Obviously I'm exaggerating somewhat for effect here, but this really is a
common style, especially once you realize that the database, the request, the
session, and the context are all just different forms of global variables.
Due to the resources-are-files mentality, it has become conventional wisdom that passing
arguments to the constructors of objects is a hardship, if those objects happen to be
resources. This should stop. Just about every other kind of programming seems to be on
board with the whole "global variables are bad" thing.
Also, did you spot the hidden security bug in the second example? '.lower()'
is locale dependent, so the security check in child_rootme may be wrong
depending on the locale the server is run in. For example, on a turkish
server, 'JİM' would be able to access administrative functions, but 'JIM' would
not.
Even without weird trivia like that, it's a lot easier to forget an 'if' check
for authentication on a sensitive operation than to accidentally implement it
in the wrong class, or accidentally implement it twice.
_______________________________________________
Twisted-web mailing list
[email protected]
http://twistedmatrix.com/cgi-bin/mailman/listinfo/twisted-web