Revision 11bab021 ncclient/operations/rpc.py
b/ncclient/operations/rpc.py | ||
---|---|---|
105 | 105 |
|
106 | 106 |
"""Represents an *<rpc-error>*. It is a type of :exc:`OperationError` |
107 | 107 |
and can be raised like any other exception.""" |
108 |
|
|
108 |
|
|
109 |
tag_to_attr = { |
|
110 |
qualify("error-type"): "_type", |
|
111 |
qualify("error-tag"): "_tag", |
|
112 |
qualify("error-severity"): "_severity", |
|
113 |
qualify("error-info"): "_info", |
|
114 |
qualify("error-path"): "_path", |
|
115 |
qualify("error-message"): "_message" |
|
116 |
} |
|
117 |
|
|
109 | 118 |
def __init__(self, err): |
110 |
self._type = None |
|
111 |
self._tag = None |
|
112 |
self._severity = None |
|
113 |
self._info = None |
|
114 |
self._path = None |
|
115 |
self._message = None |
|
119 |
for attr in tag_to_attr.values(): |
|
120 |
setattr(self, attr, None) |
|
116 | 121 |
for subele in err: |
117 |
if subele.tag == qualify("error-type"): |
|
118 |
self._type = subele.text |
|
119 |
elif subele.tag == qualify("error-tag"): |
|
120 |
self._tag = subele.text |
|
121 |
elif subele.tag == qualify("error-severity"): |
|
122 |
self._severity = subele.text |
|
123 |
elif subele.tag == qualify("error-info"): |
|
124 |
self._info = subele.text |
|
125 |
elif subele.tag == qualify("error-path"): |
|
126 |
self._path = subele.text |
|
127 |
elif subele.tag == qualify("error-message"): |
|
128 |
self._message = subele.text |
|
122 |
attr = tag_to_attr.get(subele.tag, None) |
|
123 |
if attr is not None: |
|
124 |
setattr(self, attr, subele.text) |
|
129 | 125 |
if self.message is not None: |
130 | 126 |
OperationError.__init__(self, self.message) |
131 | 127 |
else: |
132 | 128 |
OperationError.__init__(self, self.to_dict()) |
133 | 129 |
|
134 | 130 |
def to_dict(self): |
135 |
return { |
|
136 |
'type': self.type, |
|
137 |
'tag': self.tag, |
|
138 |
'severity': self.severity, |
|
139 |
'path': self.path, |
|
140 |
'message': self.message, |
|
141 |
'info': self.info |
|
142 |
} |
|
131 |
return dict([ (attr[1:], gettattr(self, attr)) for attr in tag_to_attr.values() ]) |
|
143 | 132 |
|
144 | 133 |
@property |
145 | 134 |
def type(self): |
... | ... | |
160 | 149 |
def path(self): |
161 | 150 |
"`string` or :const:`None`; representing text of *error-path* element" |
162 | 151 |
return self._path |
163 |
|
|
152 |
|
|
164 | 153 |
@property |
165 | 154 |
def message(self): |
166 | 155 |
"`string` or :const:`None`; representing text of *error-message* element" |
167 | 156 |
return self._message |
168 |
|
|
157 |
|
|
169 | 158 |
@property |
170 | 159 |
def info(self): |
171 | 160 |
"`string` (XML) or :const:`None`, representing *error-info* element" |
172 | 161 |
return self._info |
173 | 162 |
|
174 | 163 |
|
175 |
class RPCReplyListener(SessionListener): |
|
176 |
|
|
177 |
# internal use
|
|
178 |
|
|
164 |
class RPCReplyListener(SessionListener): # internal use
|
|
165 |
|
|
166 |
creation_lock = Lock()
|
|
167 |
|
|
179 | 168 |
# one instance per session -- maybe there is a better way?? |
180 | 169 |
def __new__(cls, session): |
181 |
instance = session.get_listener_instance(cls) |
|
182 |
if instance is None: |
|
183 |
instance = object.__new__(cls) |
|
184 |
instance._lock = Lock() |
|
185 |
instance._id2rpc = {} |
|
186 |
#instance._pipelined = session.can_pipeline |
|
187 |
session.add_listener(instance) |
|
188 |
return instance |
|
170 |
with creation_lock: |
|
171 |
instance = session.get_listener_instance(cls) |
|
172 |
if instance is None: |
|
173 |
instance = object.__new__(cls) |
|
174 |
instance._lock = Lock() |
|
175 |
instance._id2rpc = {} |
|
176 |
#instance._pipelined = session.can_pipeline |
|
177 |
session.add_listener(instance) |
|
178 |
return instance |
|
189 | 179 |
|
190 | 180 |
def register(self, id, rpc): |
191 | 181 |
with self._lock: |
... | ... | |
199 | 189 |
if key == "message-id": # if we found msgid attr |
200 | 190 |
id = attrs[key] # get the msgid |
201 | 191 |
with self._lock: |
202 |
try:
|
|
192 |
try: |
|
203 | 193 |
rpc = self._id2rpc[id] # the corresponding rpc |
204 | 194 |
logger.debug("Delivering to %r" % rpc) |
205 | 195 |
rpc.deliver_reply(raw) |
206 | 196 |
except KeyError: |
207 |
raise OperationError("Unknown message-id: %s", id)
|
|
197 |
raise OperationError("Unknown 'message-id': %s", id)
|
|
208 | 198 |
# no catching other exceptions, fail loudly if must |
209 | 199 |
else: |
210 | 200 |
# if no error delivering, can del the reference to the RPC |
Also available in: Unified diff