[Twisted-Python] Perspective vs. Identity question
So I'm trying to figure out the whole PB thing; I smell a lot of potential there but haven't figured out enough to actually use it yet. I figured a question here might start to clear up my confusion. I'll start with what I think I know so that if I'm wrong someone can correct my understanding. I intend to turn this into some kind of documentation so that my ignorance can be used towards some greater good :). I think I get the PB remote-method scheme up to the level demonstrated in docs/examples/pbsimple.py (using pb.connect and remote_* methods). In trying to figure out the Perspective/Identity layer (as in pbecho.py), what I've figured out so far is: Application instances hold an Authorizer, usually a DefaultAuthorizer. A DefaultAuthorizer has a collection of Identity objects, each with a unique identityName. That collection doesn't have to be a static list: .getIdentityRequest() could be overridden to do some kind of asynchronous lookup (LDAP comes to mind). Each Identity has a username and a password. It also has a list of "keys" (.keyring), each of which is a (perspectivename, servicename) tuple. If the remote client knows both username and password for a given Identity, then they are allowed to ask that Identity for any perspective on its keyring by supplying a (servicename/perspectivename) pair. The identity.requestPerspectiveForKey() method is supposed to find the named Perspective (asynchronously), run .attach() on it, then give a reference to the client. Once the client has that remote reference, they can do any perspective_* method they like. So my understanding breaks down in how this is all supposed to work in practice. I keep thinking of it in terms of a login shell or game, where you have a bunch of user accounts, and a user is using their client program to connect in. Let's say there are two Services: Shell and Game, and that the same users are allowed to connect to both. Then: Each user has one Identity object, with a username and password. These Identities could be created ahead of time (say, from /etc/passwd) and stored in the DefaultAuthorizer's list. Or, they might be created on the fly by a custom Authorizer class. The important thing is that .getIdentityRequest returns a valid Identity object when asked. Each user might talk to two potential Perpective objects. When user 'bob' is attached in to do shell stuff, he could use a Perspective called 'bob_shell', which is part of the Shell service. (I think the perspectivename is scoped to the Service, so this could just be named 'bob', but that would make this description confusing). When he is doing game stuff, he could use a Perspective called 'bob_game', part of the Game service. Presumably bob_shell and bob_game are instances of different subclasses of pb.Perspective, one which offers shell-like remote methods and the other offering game-like methods. The cross-user shared state that represents the communal game world could be stored up in the Game Service object, anything that needs to be shared between both the game and the shell could go in the overall Application object. Now, how are those Perspectives supposed to be created? Do they get built ahead of time (at the same time the Identities are made)? Are they supposed to outlast the client connection? In all the doc/example/ programs, a single Perspective is created ahead of time, and then a single Identity is created from that Perspective, using the .makeIdentity() utility method. The largest example I've been able to find is twisted.words, but as far as I can tell it does the same thing.. I think the words.Participant (subclassed from pb.Perspective) hangs around all the time whether or not the client is attached (it has a .status flag that starts as OFFLINE), and the perspectives are always created ahead of time (tap/words.py does svc.createPerspective(n).makeIdentity(pw)) based upon who is allowed to connect. I can see that the Perspective is kind of an in-server proxy for the remote user: the client can make it do anything they want (well, any perspective_* methods at least), and the perspective can outlast the client's connection (its .attached/.detached are called to let it know when the client comes and goes). But if it isn't supposed to (or doesn't need to) outlive the connection, then must it still be created ahead of time? Is identity.requestPerspectiveForKey() allowed to create new perspective objects on the fly? Sorry for the length. Tell me if I'm on the right track here.. if so, I'll try to put together some kind of multi-Perspective example program (maybe the telnet/game thing I just described) with a big how-it-works writeup, something that explains the concepts I just went over. An example+writeup like that would have helped / will help me figure out this part of Twisted.. maybe it could help others too. thanks much, -Brian, twisting a little bit more each day
sounds like you are on the right track. For another example, take a look at twisted.enterprise.dbcred. It has two authorizers that create perspective and identities from a relational database and a "reflector" which is another type of data source. In my application, perspectives and identities live in a relational database, and pb.perspective objects are created when a user logs in and removed when the user logs out. my identities objects are created inside of Authorizer.getIdentityRequest() and my perspectives created inside of service.getPerspectiveRequest(). -----Original Message----- From: twisted-python-admin@twistedmatrix.com [mailto:twisted-python-admin@twistedmatrix.com]On Behalf Of Brian Warner Sent: Saturday, September 14, 2002 3:35 AM To: twisted-python@twistedmatrix.com Subject: [Twisted-Python] Perspective vs. Identity question So I'm trying to figure out the whole PB thing; I smell a lot of potential there but haven't figured out enough to actually use it yet. I figured a question here might start to clear up my confusion. I'll start with what I think I know so that if I'm wrong someone can correct my understanding. I intend to turn this into some kind of documentation so that my ignorance can be used towards some greater good :). I think I get the PB remote-method scheme up to the level demonstrated in docs/examples/pbsimple.py (using pb.connect and remote_* methods). In trying to figure out the Perspective/Identity layer (as in pbecho.py), what I've figured out so far is: Application instances hold an Authorizer, usually a DefaultAuthorizer. A DefaultAuthorizer has a collection of Identity objects, each with a unique identityName. That collection doesn't have to be a static list: .getIdentityRequest() could be overridden to do some kind of asynchronous lookup (LDAP comes to mind). Each Identity has a username and a password. It also has a list of "keys" (.keyring), each of which is a (perspectivename, servicename) tuple. If the remote client knows both username and password for a given Identity, then they are allowed to ask that Identity for any perspective on its keyring by supplying a (servicename/perspectivename) pair. The identity.requestPerspectiveForKey() method is supposed to find the named Perspective (asynchronously), run .attach() on it, then give a reference to the client. Once the client has that remote reference, they can do any perspective_* method they like. So my understanding breaks down in how this is all supposed to work in practice. I keep thinking of it in terms of a login shell or game, where you have a bunch of user accounts, and a user is using their client program to connect in. Let's say there are two Services: Shell and Game, and that the same users are allowed to connect to both. Then: Each user has one Identity object, with a username and password. These Identities could be created ahead of time (say, from /etc/passwd) and stored in the DefaultAuthorizer's list. Or, they might be created on the fly by a custom Authorizer class. The important thing is that .getIdentityRequest returns a valid Identity object when asked. Each user might talk to two potential Perpective objects. When user 'bob' is attached in to do shell stuff, he could use a Perspective called 'bob_shell', which is part of the Shell service. (I think the perspectivename is scoped to the Service, so this could just be named 'bob', but that would make this description confusing). When he is doing game stuff, he could use a Perspective called 'bob_game', part of the Game service. Presumably bob_shell and bob_game are instances of different subclasses of pb.Perspective, one which offers shell-like remote methods and the other offering game-like methods. The cross-user shared state that represents the communal game world could be stored up in the Game Service object, anything that needs to be shared between both the game and the shell could go in the overall Application object. Now, how are those Perspectives supposed to be created? Do they get built ahead of time (at the same time the Identities are made)? Are they supposed to outlast the client connection? In all the doc/example/ programs, a single Perspective is created ahead of time, and then a single Identity is created from that Perspective, using the .makeIdentity() utility method. The largest example I've been able to find is twisted.words, but as far as I can tell it does the same thing.. I think the words.Participant (subclassed from pb.Perspective) hangs around all the time whether or not the client is attached (it has a .status flag that starts as OFFLINE), and the perspectives are always created ahead of time (tap/words.py does svc.createPerspective(n).makeIdentity(pw)) based upon who is allowed to connect. I can see that the Perspective is kind of an in-server proxy for the remote user: the client can make it do anything they want (well, any perspective_* methods at least), and the perspective can outlast the client's connection (its .attached/.detached are called to let it know when the client comes and goes). But if it isn't supposed to (or doesn't need to) outlive the connection, then must it still be created ahead of time? Is identity.requestPerspectiveForKey() allowed to create new perspective objects on the fly? Sorry for the length. Tell me if I'm on the right track here.. if so, I'll try to put together some kind of multi-Perspective example program (maybe the telnet/game thing I just described) with a big how-it-works writeup, something that explains the concepts I just went over. An example+writeup like that would have helped / will help me figure out this part of Twisted.. maybe it could help others too. thanks much, -Brian, twisting a little bit more each day _______________________________________________ Twisted-Python mailing list Twisted-Python@twistedmatrix.com http://twistedmatrix.com/cgi-bin/mailman/listinfo/twisted-python
participants (2)
-
Brian Warner
-
Sean Riley