def success(self, data): if 'command' in data: command = data['command'] command_type = None if 'type' in command: command_type = command['type'] if command_type == 'ejtpd-client-init': modname = ("module" in command and command["module"]) or '' classname = ("class" in command and command["class"]) or '' args = ("args" in command and command["args"]) or [] kwargs = ("kwargs" in command and command["kwargs"]) or {} logger.info( "Remote client succesfully initialized (%s.%s, %s, %s)", modname, classname, strict(args).export(), strict(kwargs).export()) elif command_type == 'ejtpd-client-destroy': interface = ("interface" in command and command["interface"]) or '' logger.info("Remote client succesfully destroyed (%s)", strict(interface).export()) else: logger.info( "Remote command succesful (Unrecognized command - %r)", command) else: logger.info( "Remote command succesful (daemon did not report details)") self.response_callback(True, data)
def mcp_error(self, content, sender): print "Error from:", sender, ", code", content["code"] print repr(content['msg']) if 'data' in content and content['data']: print strict(content['data']) content['sender'] = sender self.gear.evgrid.happen('recv_error', content)
def mcp_error(self, content, sender): print "Error from:", sender, ", code", content["code"] print repr(content["msg"]) if "data" in content and content["data"]: print strict(content["data"]) content["sender"] = sender self.gear.evgrid.happen("recv_error", content)
def sig_verify(self, obj, signer, sig): ''' Verify a signature. ''' strdata = hashfunc(strict(obj)) return self.encryptor_get(signer).flip().decrypt( sig).toString() == strdata
def rcv_callback(self, msg, client_obj): sender = msg.sender if sender != self.target: # Not the daemon, drop it return data = None try: data = msg.unpack() except: return self.error(sender, 400) if not isinstance(data, dict): return self.error(sender, 401) if not "type" in data: return self.error(sender, 402) mtype = data["type"] try: if mtype == "ejtpd-success": self.success(data) elif mtype == "ejtpd-error": logger.error("Remote error %d %s %s", data['code'], data['msg'], strict(data['details']).export()) self.response_callback(False, data) else: return self.error(sender, 403, command) except Exception as e: logger.error(e) return self.error(sender, 100, data)
def on_ejtp(self, msg, client): try: msg_type = msg.unpack()['type'] except: msg_type = "<could not parse>" logline = "%s : %s" % (strict(msg.sender).export(), msg_type) self.interface.output(logline, 'msglog') self.interface.owner.on_ejtp(msg, client)
def add_participant(self, iface, can_read=True, can_write=True): routes = self.routing striface = strict(iface) if can_read: self.permissions['read'][striface] = True if can_write: self.permissions['write'][striface] = True if not iface in routes: routes[striface] = {}
def error(self, target, code, details=None): msg = errorcodes[code] logger.error("CLIENT ERROR #%d %s %s", code, msg, (details and strict(details) or String()).export()) self.write_json(target, { 'type': 'ejtpd-error', 'code': code, 'msg': msg, 'details': details, })
def str_address(address): ''' Converts address to string, only if it isn't already >>> str_address([0,9]) '[0,9]' >>> str_address("[0,9]") '[0,9]' ''' if isinstance(address, String): return address else: return strict(address)
def routes_to_unfiltered(self, iface): # Does not take read permissions into account. istr = strict(iface) if istr in self.routing and len(self.routing[istr]) > 0: result = set() for target in self.routing[istr]: result.add(target) import json return [json.loads(s) for s in result] else: parts = self.participants if iface in parts: parts.remove(iface) return parts
def py_address(address): ''' Converts address to non-string, only if it isn't already >>> py_address([0,9]) [0, 9] >>> py_address("[0,9]") [0, 9] ''' if isinstance(address, String): return loads(address.export()) elif isinstance(address, list): return address elif isinstance(address, tuple): return loads(strict(address).export()) else: raise ValueError("Can not convert to py_address: %r" % address)
def has_permission(self, iface, name): # If self.permissions does not already exist, will always return false. if "permissions" not in self.root: return False perm = self.permissions[name] return strict(iface) in perm
def strict(self): # The strict string rep of self.value return strict(self.value)
def construct(content): return JSONFrame( RawData('j\x00') + \ RawData(strict(content)) )
def __str__(self): return strict(self.proto())
def _assert(self, expected, value): value = hasher.strict(value) self.assertEqual(RawData(expected), RawData(value))
def __str__(self): return hasher.strict(self.proto())
def test_construct(self): from ejtp.util.hasher import strict self.assertEqual( frame.json.construct((1, 2, 3)), frame.json.JSONFrame(RawData('j\x00') + strict((1, 2, 3))))
def add_permission(self, iface, name): self.permissions[name][strict(iface)] = True
def key(self): return self.keysum(hasher.strict(self.value))
def key(self): return self.keysum(strict(self.value))
def sign(self, obj): ''' Make a signature with this client's interface. ''' strdata = hashfunc(strict(obj)) return self.encryptor_get(self.interface).flip().encrypt(strdata)
def remove_permission(self, iface, name): del self.permissions[name][strict(iface)]
def on_status(client): status = strict(client.status).export() self.assertEqual(expected, status)
def serialize(self): return strict(self.proto())
def do_dinit(self, args): ''' Initialize DEJE interactivity. This command must be used before any of the other d* commands. It reads from a few of the values in variable storage as initialization parameters: * idcache - EJTP identity cache * identity - location of EJTP identity in cache * docname - Name of the document for network sync * docserialized - serialized version of document The dinit command can be run more than once, but it's a bit of a reset, and may cause data loss in the stateful parts of the protocol. But it's also the only way to update the parameters used by the DEJE code - for example, any changes to the 'idcache' variable after initialization will have no effect. ''' try: params = self.get_vars( 'idcache', 'identity', 'docname', 'docserialized' ) except KeyError as e: self.fail('Need to set variable %r' % e.args[0]) cache = IdentityCache() try: cache.deserialize(params['idcache']) except: self.fail('Could not deserialize data in idcache') try: ident = cache.find_by_location(params['identity']) except KeyError: loc_string = strict(params['identity']).export() self.fail('No identity in cache for ' + loc_string) owner = Owner(ident) owner.identities = cache owner.client.rcv_callback = self.on_ejtp self.write_json = owner.client.write_json owner.client.write_json = self.write_json_wrapped if type(params['docname']) != str: json_str = strict(params['docname']).export() self.fail('Not a valid docname: ' + json_str) doc = Document(params['docname'], owner=owner) try: doc.deserialize(params['docserialized']) except Exception as e: self.fail('Failed to deserialize data:\n%r' % e) doc.signals['enact-event'].connect(self.on_event) doc.debug = self.debug # Wait until everything that could fail has gone right self.interface.owner = owner self.interface.document = doc self.output('DEJE initialized')
def __str__(self): return hasher.strict(self.data)
def success(self, data): logger.info("SUCCESFUL COMMAND %s", strict(data).export()) self.write_json(self.controller, { 'type': 'ejtpd-success', 'command': data, })