summaryrefslogtreecommitdiff
path: root/python/qpid
diff options
context:
space:
mode:
authorRafael H. Schloming <rhs@apache.org>2008-05-08 20:52:28 +0000
committerRafael H. Schloming <rhs@apache.org>2008-05-08 20:52:28 +0000
commitfd5ba0c75091336020287825a973c88a07dbe5b4 (patch)
tree5a90ff41987b15e85f254a9266d9c933cd505b9e /python/qpid
parent32613b43c550fec2785299a271b3818db75490c4 (diff)
downloadqpid-python-fd5ba0c75091336020287825a973c88a07dbe5b4.tar.gz
QPID-979: added access to enums through the session so that symbolic constants can be used rather than hard coded ones; also added default loading of the spec
git-svn-id: https://svn.apache.org/repos/asf/incubator/qpid/trunk/qpid@654618 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'python/qpid')
-rw-r--r--python/qpid/connection.py11
-rw-r--r--python/qpid/invoker.py26
-rw-r--r--python/qpid/session.py12
-rw-r--r--python/qpid/spec.py13
-rw-r--r--python/qpid/spec010.py16
5 files changed, 61 insertions, 17 deletions
diff --git a/python/qpid/connection.py b/python/qpid/connection.py
index dc72cd9cb8..39f882e9c3 100644
--- a/python/qpid/connection.py
+++ b/python/qpid/connection.py
@@ -25,7 +25,8 @@ from assembler import Assembler, Segment
from codec010 import StringCodec
from session import Session
from invoker import Invoker
-from spec010 import Control, Command
+from spec010 import Control, Command, load
+from spec import default
from exceptions import *
from logging import getLogger
import delegates
@@ -44,8 +45,10 @@ def server(*args):
class Connection(Assembler):
- def __init__(self, sock, spec, delegate=client):
+ def __init__(self, sock, spec=None, delegate=client):
Assembler.__init__(self, sock)
+ if spec == None:
+ spec = load(default())
self.spec = spec
self.track = self.spec["track"]
@@ -162,9 +165,9 @@ class Channel(Invoker):
def resolve_method(self, name):
inst = self.connection.spec.instructions.get(name)
if inst is not None and isinstance(inst, Control):
- return inst
+ return self.METHOD, inst
else:
- return None
+ return self.ERROR, None
def invoke(self, type, args, kwargs):
ctl = type.new(args, kwargs)
diff --git a/python/qpid/invoker.py b/python/qpid/invoker.py
index 9e6f6943d8..2d9e45179e 100644
--- a/python/qpid/invoker.py
+++ b/python/qpid/invoker.py
@@ -17,16 +17,26 @@
# under the License.
#
+# TODO: need a better naming for this class now that it does the value
+# stuff
class Invoker:
- def resolve_method(self, name):
- pass
-
- def __getattr__(self, name):
- resolved = self.resolve_method(name)
- if resolved == None:
- raise AttributeError("%s instance has no attribute '%s'" %
- (self.__class__.__name__, name))
+ def METHOD(self, name, resolved):
method = lambda *args, **kwargs: self.invoke(resolved, args, kwargs)
self.__dict__[name] = method
return method
+
+ def VALUE(self, name, resolved):
+ self.__dict__[name] = resolved
+ return resolved
+
+ def ERROR(self, name, resolved):
+ raise AttributeError("%s instance has no attribute '%s'" %
+ (self.__class__.__name__, name))
+
+ def resolve_method(self, name):
+ return ERROR, None
+
+ def __getattr__(self, name):
+ disp, resolved = self.resolve_method(name)
+ return disp(name, resolved)
diff --git a/python/qpid/session.py b/python/qpid/session.py
index 11249ca435..f8ac98b96e 100644
--- a/python/qpid/session.py
+++ b/python/qpid/session.py
@@ -112,15 +112,17 @@ class Session(Invoker):
def resolve_method(self, name):
cmd = self.spec.instructions.get(name)
if cmd is not None and cmd.track == self.spec["track.command"].value:
- return cmd
+ return self.METHOD, cmd
else:
# XXX
for st in self.spec.structs.values():
if st.name == name:
- return st
- if self.spec.structs_by_name.has_key(name):
- return self.spec.structs_by_name[name]
- return None
+ return self.METHOD, st
+ if self.spec.structs_by_name.has_key(name):
+ return self.METHOD, self.spec.structs_by_name[name]
+ if self.spec.enums.has_key(name):
+ return self.VALUE, self.spec.enums[name]
+ return self.ERROR, None
def invoke(self, type, args, kwargs):
# XXX
diff --git a/python/qpid/spec.py b/python/qpid/spec.py
index 64a14b0f61..152763b762 100644
--- a/python/qpid/spec.py
+++ b/python/qpid/spec.py
@@ -31,6 +31,19 @@ situations.
import os, mllib, spec08, spec010
+def default():
+ try:
+ specfile = os.environ["AMQP_SPEC"]
+ return specfile
+ except KeyError:
+ try:
+ from AMQP_SPEC import location as specfile
+ return specfile
+ except ImportError:
+ raise Exception("unable to locate the amqp specification, please set "
+ "the AMQP_SPEC environment variable or supply a "
+ "configured AMQP_SPEC.py")
+
def load(specfile, *errata):
for name in (specfile,) + errata:
if not os.path.exists(name):
diff --git a/python/qpid/spec010.py b/python/qpid/spec010.py
index 1668729876..fb625eab65 100644
--- a/python/qpid/spec010.py
+++ b/python/qpid/spec010.py
@@ -166,6 +166,15 @@ class Domain(Type, Lookup):
def decode(self, codec):
return self.type.decode(codec)
+class Enum:
+
+ def __init__(self, name):
+ self.name = name
+
+ def __repr__(self):
+ return "%s(%s)" % (self.name, ", ".join([k for k in self.__dict__.keys()
+ if k != "name"]))
+
class Choice(Named, Node):
def __init__(self, name, value, children):
@@ -177,6 +186,12 @@ class Choice(Named, Node):
Named.register(self, node)
node.choices[self.value] = self
Node.register(self)
+ try:
+ enum = node.spec.enums[node.name]
+ except KeyError:
+ enum = Enum(node.name)
+ node.spec.enums[node.name] = enum
+ setattr(enum, self.name, self.value)
class Composite(Type, Coded):
@@ -450,6 +465,7 @@ class Spec(Node):
self.commands = {}
self.structs = {}
self.structs_by_name = {}
+ self.enums = {}
def encoding(self, klass):
if Spec.ENCODINGS.has_key(klass):