comparison src/core/sat_main.py @ 1622:5b24d6bf5d15

core, bridge: actionsGet: - added a new mechanism to keep actions until they are answered (or timeout-ed) - keep_id must be explicitly used on actionNew - actionsGet is used to retrive these actions - the mechanism is used in deferXMLUI
author Goffi <goffi@goffi.org>
date Tue, 17 Nov 2015 21:28:58 +0100
parents 2b82d846848e
children 7e749e8eefd0
comparison
equal deleted inserted replaced
1621:a17a91531fbe 1622:5b24d6bf5d15
100 self.bridge.register("addContact", self._addContact) 100 self.bridge.register("addContact", self._addContact)
101 self.bridge.register("updateContact", self._updateContact) 101 self.bridge.register("updateContact", self._updateContact)
102 self.bridge.register("delContact", self._delContact) 102 self.bridge.register("delContact", self._delContact)
103 self.bridge.register("isConnected", self.isConnected) 103 self.bridge.register("isConnected", self.isConnected)
104 self.bridge.register("launchAction", self.launchCallback) 104 self.bridge.register("launchAction", self.launchCallback)
105 self.bridge.register("actionsGet", self.actionsGet)
105 self.bridge.register("confirmationAnswer", self.confirmationAnswer) 106 self.bridge.register("confirmationAnswer", self.confirmationAnswer)
106 self.bridge.register("progressGet", self._progressGet) 107 self.bridge.register("progressGet", self._progressGet)
107 self.bridge.register("progressGetAll", self._progressGetAll) 108 self.bridge.register("progressGetAll", self._progressGetAll)
108 self.bridge.register("getMenus", self.getMenus) 109 self.bridge.register("getMenus", self.getMenus)
109 self.bridge.register("getMenuHelp", self.getMenuHelp) 110 self.bridge.register("getMenuHelp", self.getMenuHelp)
783 else: 784 else:
784 cb = client._waiting_conf[conf_id][-1] 785 cb = client._waiting_conf[conf_id][-1]
785 del client._waiting_conf[conf_id] 786 del client._waiting_conf[conf_id]
786 cb(conf_id, accepted, data, profile) 787 cb(conf_id, accepted, data, profile)
787 788
788 def actionNew(self, action_data, security_limit=C.NO_SECURITY_LIMIT, profile=C.PROF_KEY_NONE): 789 def _killAction(self, keep_id, client):
789 """Shortcut to bridge.actionNew which generate and id 790 log.debug(u"Killing action {} for timeout".format(keep_id))
791 client.actions[keep_id]
792
793 def actionNew(self, action_data, security_limit=C.NO_SECURITY_LIMIT, keep_id=None, profile=C.PROF_KEY_NONE):
794 """Shortcut to bridge.actionNew which generate and id and keep for retrieval
790 795
791 @param action_data(dict): action data (see bridge documentation) 796 @param action_data(dict): action data (see bridge documentation)
792 @param security_limit: %(doc_security_limit)s 797 @param security_limit: %(doc_security_limit)s
798 @param keep_id(None, unicode): if not None, used to keep action for differed retrieval
799 must be set to the callback_id
800 action will be deleted after 30 min.
793 @param profile: %(doc_profile)s 801 @param profile: %(doc_profile)s
794 """ 802 """
795 id_ = unicode(uuid.uuid4()) 803 id_ = unicode(uuid.uuid4())
804 if keep_id is not None:
805 client = self.getClient(profile)
806 action_timer = reactor.callLater(60*30, self._killAction)
807 client.actions[keep_id] = (action_data, id_, security_limit, action_timer)
808
796 self.bridge.actionNew(action_data, id_, security_limit, profile) 809 self.bridge.actionNew(action_data, id_, security_limit, profile)
810
811 def actionsGet(self, profile):
812 """Return current non answered actions
813
814 @param profile: %(doc_profile)s
815 """
816 client = self.getClient(profile)
817 return [action_tuple[:-1] for action_tuple in client.actions.itervalues()]
797 818
798 def registerProgressCb(self, progress_id, callback, profile): 819 def registerProgressCb(self, progress_id, callback, profile):
799 """Register a callback called when progress is requested for id""" 820 """Register a callback called when progress is requested for id"""
800 client = self.getClient(profile) 821 client = self.getClient(profile)
801 if progress_id in client._progress_cb: 822 if progress_id in client._progress_cb:
902 - xmlui: a XMLUI need to be displayed 923 - xmlui: a XMLUI need to be displayed
903 - validated: if present, can be used to launch a callback, it can have the values 924 - validated: if present, can be used to launch a callback, it can have the values
904 - C.BOOL_TRUE 925 - C.BOOL_TRUE
905 - C.BOOL_FALSE 926 - C.BOOL_FALSE
906 """ 927 """
907 profile = self.memory.getProfileName(profile_key) 928 client = self.getClient(profile_key)
908 if not profile: 929 try:
909 raise exceptions.ProfileUnknownError(_('trying to launch action with a non-existant profile')) 930 action_tuple = client.actions[callback_id]
931 except KeyError:
932 pass
933 else:
934 action_tuple[-1].cancel() # the last item is the action timer
910 935
911 try: 936 try:
912 callback, args, kwargs = self._cb_map[callback_id] 937 callback, args, kwargs = self._cb_map[callback_id]
913 except KeyError: 938 except KeyError:
914 raise exceptions.DataError(u"Unknown callback id {}".format(callback_id)) 939 raise exceptions.DataError(u"Unknown callback id {}".format(callback_id))
916 if kwargs.get("with_data", False): 941 if kwargs.get("with_data", False):
917 if data is None: 942 if data is None:
918 raise exceptions.DataError("Required data for this callback is missing") 943 raise exceptions.DataError("Required data for this callback is missing")
919 args,kwargs=list(args)[:],kwargs.copy() # we don't want to modify the original (kw)args 944 args,kwargs=list(args)[:],kwargs.copy() # we don't want to modify the original (kw)args
920 args.insert(0, data) 945 args.insert(0, data)
921 kwargs["profile"] = profile 946 kwargs["profile"] = client.profile
922 del kwargs["with_data"] 947 del kwargs["with_data"]
923 948
924 if kwargs.pop('one_shot', False): 949 if kwargs.pop('one_shot', False):
925 self.removeCallback(callback_id) 950 self.removeCallback(callback_id)
926 951