# HG changeset patch # User Goffi # Date 1702128654 -3600 # Node ID b86912d3fd33f252bb26e922725475f2b253ae13 # Parent 3b95704ab77762700103910221dfee5a3d9943f3 plugin IP: fix use of legacy URL + coroutine use: An https:/salut-a-toi.org URL was used to retrieve external IP, but it's not valid anymore, resulting in an exception. This feature is currently disabled. Also moved several methods from legacy inline callbacks to coroutines. diff -r 3b95704ab777 -r b86912d3fd33 libervia/backend/plugins/plugin_misc_ip.py --- a/libervia/backend/plugins/plugin_misc_ip.py Sat Dec 09 14:05:02 2023 +0100 +++ b/libervia/backend/plugins/plugin_misc_ip.py Sat Dec 09 14:30:54 2023 +0100 @@ -200,8 +200,7 @@ p.transport.loseConnection() return local_ip - @defer.inlineCallbacks - def get_local_i_ps(self, client): + async def get_local_ips(self, client): """Try do discover local area network IPs @return (deferred): list of lan IP addresses @@ -210,7 +209,7 @@ """ # TODO: manage permission requesting (e.g. for UMTS link) if self._local_ip_cache is not None: - defer.returnValue(self._local_ip_cache) + return self._local_ip_cache addresses = [] localhost = ["127.0.0.1"] @@ -232,51 +231,50 @@ ip = client.xmlstream.transport.getHost().host if self._filter_addresse(ip): self._insert_first(addresses, ip) - defer.returnValue(addresses) + return addresses # if server is local, we try with NAT-Port if self._nat is not None: - nat_ip = yield self._nat.get_ip(local=True) + nat_ip = await self._nat.get_ip(local=True) if nat_ip is not None: self._insert_first(addresses, nat_ip) - defer.returnValue(addresses) + return addresses if addresses: - defer.returnValue(addresses) + return addresses # still not luck, we need to contact external website - allow_get_ip = yield self._external_allowed(client) + allow_get_ip = await self._external_allowed(client) if not allow_get_ip: - defer.returnValue(addresses or localhost) + return addresses or localhost try: - local_ip = yield defer.ensureDeferred(self._get_ip_from_external(GET_IP_PAGE)) + local_ip = await defer.ensureDeferred(self._get_ip_from_external(GET_IP_PAGE)) except (internet_error.DNSLookupError, internet_error.TimeoutError): log.warning("Can't access Domain Name System") else: if local_ip is not None: self._insert_first(addresses, local_ip) - defer.returnValue(addresses or localhost) + return addresses or localhost - @defer.inlineCallbacks - def get_external_ip(self, client): + async def get_external_ip(self, client): """Try to discover external IP @return (deferred): external IP address or None if it can't be discovered """ if self._external_ip_cache is not None: - defer.returnValue(self._external_ip_cache) + return self._external_ip_cache # we first try with XEP-0279 - ip_check = yield self.host.hasFeature(client, NS_IP_CHECK) + ip_check = await self.host.hasFeature(client, NS_IP_CHECK) if ip_check: log.debug("Server IP Check available, we use it to retrieve our IP") iq_elt = client.IQ("get") iq_elt.addElement((NS_IP_CHECK, "address")) try: - result_elt = yield iq_elt.send() + result_elt = await iq_elt.send() address_elt = next(result_elt.elements(NS_IP_CHECK, "address")) ip_elt = next(address_elt.elements(NS_IP_CHECK, "ip")) except StopIteration: @@ -291,33 +289,37 @@ external_ip = str(ip_elt) log.debug("External IP found: {}".format(external_ip)) self._external_ip_cache = external_ip - defer.returnValue(self._external_ip_cache) + return self._external_ip_cache # then with NAT-Port if self._nat is not None: - nat_ip = yield self._nat.get_ip() + nat_ip = await self._nat.get_ip() if nat_ip is not None: self._external_ip_cache = nat_ip - defer.returnValue(nat_ip) + return nat_ip # and finally by requesting external website - allow_get_ip = yield self._external_allowed(client) - try: - ip = ((yield webclient.getPage(GET_IP_PAGE.encode('utf-8'))) - if allow_get_ip else None) - except (internet_error.DNSLookupError, internet_error.TimeoutError): - log.warning("Can't access Domain Name System") - ip = None - except web_error.Error as e: - log.warning( - "Error while retrieving IP on {url}: {message}".format( - url=GET_IP_PAGE, message=e - ) - ) - ip = None - else: - self._external_ip_cache = ip - defer.returnValue(ip) + allow_get_ip = await self._external_allowed(client) + + ip = None + + # FIXME: following code is deprecated, check it + # try: + # ip = ((await webclient.getPage(GET_IP_PAGE.encode('utf-8'))) + # if allow_get_ip else None) + # except (internet_error.DNSLookupError, internet_error.TimeoutError): + # log.warning("Can't access Domain Name System") + # ip = None + # except web_error.Error as e: + # log.warning( + # "Error while retrieving IP on {url}: {message}".format( + # url=GET_IP_PAGE, message=e + # ) + # ) + # ip = None + # else: + # self._external_ip_cache = ip + return ip @implementer(iwokkel.IDisco) diff -r 3b95704ab777 -r b86912d3fd33 libervia/backend/plugins/plugin_xep_0065.py --- a/libervia/backend/plugins/plugin_xep_0065.py Sat Dec 09 14:05:02 2023 +0100 +++ b/libervia/backend/plugins/plugin_xep_0065.py Sat Dec 09 14:30:54 2023 +0100 @@ -784,8 +784,7 @@ ) return self._server_factory - @defer.inlineCallbacks - def get_proxy(self, client, local_jid): + async def get_proxy(self, client, local_jid): """Return the proxy available for this profile cache is used between clients using the same server @@ -802,12 +801,12 @@ server = client.host if client.is_component else client.jid.host try: - defer.returnValue(self._cache_proxies[server]) + return self._cache_proxies[server] except KeyError: pass try: proxy = ( - yield self.host.find_service_entities(client, "proxy", "bytestreams") + await self.host.find_service_entities(client, "proxy", "bytestreams") ).pop() except (defer.CancelledError, StopIteration, KeyError): notFound(server) @@ -817,7 +816,7 @@ iq_elt.addElement((NS_BS, "query")) try: - result_elt = yield iq_elt.send() + result_elt = await iq_elt.send() except jabber_error.StanzaError as failure: log.warning( "Error while requesting proxy info on {jid}: {error}".format( @@ -841,10 +840,9 @@ proxy_infos = self._cache_proxies[server] = ProxyInfos(host, jid_, port) log.info("Proxy found: {}".format(proxy_infos)) - defer.returnValue(proxy_infos) + return proxy_infos - @defer.inlineCallbacks - def _get_network_data(self, client): + async def _get_network_data(self, client): """Retrieve information about network @param client: %(doc_client)s @@ -852,8 +850,8 @@ """ self.get_socks_5_server_factory() local_port = self._server_factory_port - external_ip = yield self._ip.get_external_ip(client) - local_ips = yield self._ip.get_local_i_ps(client) + external_ip = await self._ip.get_external_ip(client) + local_ips = await self._ip.get_local_ips(client) if external_ip is not None and self._external_port is None: if external_ip != local_ips[0]: @@ -861,7 +859,7 @@ if self._np is None: log.warning("NAT port plugin not available, we can't map port") else: - ext_port = yield self._np.map_port( + ext_port = await self._np.map_port( local_port, desc="SaT socks5 stream" ) if ext_port is None: @@ -869,10 +867,9 @@ else: self._external_port = ext_port - defer.returnValue((local_port, self._external_port, local_ips, external_ip)) + return (local_port, self._external_port, local_ips, external_ip) - @defer.inlineCallbacks - def get_candidates(self, client, local_jid): + async def get_candidates(self, client, local_jid): """Return a list of our stream candidates @param local_jid(jid.JID): jid to use as local jid @@ -881,10 +878,10 @@ client.jid would be file.example.net) @return (D(list[Candidate])): list of candidates, ordered by priority """ - server_factory = yield self.get_socks_5_server_factory() - local_port, ext_port, local_ips, external_ip = yield self._get_network_data(client) + server_factory = self.get_socks_5_server_factory() + local_port, ext_port, local_ips, external_ip = await self._get_network_data(client) try: - proxy = yield self.get_proxy(client, local_jid) + proxy = await self.get_proxy(client, local_jid) except exceptions.NotFound: proxy = None @@ -948,7 +945,7 @@ # should be already sorted, but just in case the priorities get weird candidates.sort(key=lambda c: c.priority, reverse=True) - defer.returnValue(candidates) + return candidates def _add_connector(self, connector, candidate): """Add connector used to connect to candidate, and return client factory's connection Deferred @@ -1164,7 +1161,7 @@ args = [client, session_data, local_jid] d.addCallbacks(self._iq_negotiation_cb, self._iq_negotiation_eb, args, None, args) - self.get_candidates(client, local_jid).addCallback(got_candidates) + defer.ensureDeferred(self.get_candidates(client, local_jid)).addCallback(got_candidates) return session_data[DEFER_KEY] def _iq_negotiation_cb(self, iq_elt, client, session_data, local_jid): diff -r 3b95704ab777 -r b86912d3fd33 libervia/backend/plugins/plugin_xep_0260.py --- a/libervia/backend/plugins/plugin_xep_0260.py Sat Dec 09 14:05:02 2023 +0100 +++ b/libervia/backend/plugins/plugin_xep_0260.py Sat Dec 09 14:30:54 2023 +0100 @@ -134,8 +134,7 @@ candidate_elt["type"] = candidate.type return transport_elt - @defer.inlineCallbacks - def jingle_session_init(self, client, session, content_name): + async def jingle_session_init(self, client, session, content_name): content_data = session["contents"][content_name] transport_data = content_data["transport_data"] sid = transport_data["sid"] = str(uuid.uuid4()) @@ -146,14 +145,14 @@ session["peer_jid"], session["local_jid"], sid ) # requester and target are inversed for peer candidates transport_data["stream_d"] = self._s5b.register_hash(client, session_hash, None) - candidates = transport_data["candidates"] = yield self._s5b.get_candidates( + candidates = transport_data["candidates"] = await self._s5b.get_candidates( client, session["local_jid"]) mode = "tcp" # XXX: we only manage tcp for now transport_elt = self._build_candidates( session, candidates, sid, session_hash, client, mode ) - defer.returnValue(transport_elt) + return transport_elt def _proxy_activated_cb(self, iq_result_elt, client, candidate, session, content_name): """Called when activation confirmation has been received from proxy @@ -398,8 +397,7 @@ else: activation_d.errback(ProxyError()) - @defer.inlineCallbacks - def jingle_handler(self, client, action, session, content_name, transport_elt): + async def jingle_handler(self, client, action, session, content_name, transport_elt): content_data = session["contents"][content_name] transport_data = content_data["transport_data"] @@ -451,7 +449,7 @@ d.addCallback( self._found_peer_candidate, session, transport_data, content_name, client ) - candidates = yield self._s5b.get_candidates(client, session["local_jid"]) + candidates = await self._s5b.get_candidates(client, session["local_jid"]) # we remove duplicate candidates candidates = [ candidate for candidate in candidates if candidate not in peer_candidates @@ -493,7 +491,7 @@ else: log.warning("FIXME: unmanaged action {}".format(action)) - defer.returnValue(transport_elt) + return transport_elt def jingle_terminate(self, client, action, session, content_name, reason_elt): if reason_elt.decline: