summary refs log tree commit diff
path: root/synapse/appservice/api.py
diff options
context:
space:
mode:
authorPaul "LeoNerd" Evans <paul@matrix.org>2016-08-18 17:33:56 +0100
committerPaul "LeoNerd" Evans <paul@matrix.org>2016-08-18 17:33:56 +0100
commit65201631a407b71087bb52da8b591e0975c463ec (patch)
treee7077e567fddbc9a0ac30204e19dc1f0bc9e74e2 /synapse/appservice/api.py
parentMore warnings about invalid results from AS 3PE query (diff)
downloadsynapse-65201631a407b71087bb52da8b591e0975c463ec.tar.xz
Move validation logic for AS 3PE query response into ApplicationServiceApi class, to keep the handler logic neater
Diffstat (limited to 'synapse/appservice/api.py')
-rw-r--r--synapse/appservice/api.py43
1 files changed, 42 insertions, 1 deletions
diff --git a/synapse/appservice/api.py b/synapse/appservice/api.py
index dd5e762e0d..066127b666 100644
--- a/synapse/appservice/api.py
+++ b/synapse/appservice/api.py
@@ -25,6 +25,28 @@ import urllib
 logger = logging.getLogger(__name__)
 
 
+def _is_valid_3pe_result(r, field):
+    if not isinstance(r, dict):
+        return False
+
+    for k in (field, "protocol"):
+        if k not in r:
+            return False
+        if not isinstance(r[k], str):
+            return False
+
+    if "fields" not in r:
+        return False
+    fields = r["fields"]
+    if not isinstance(fields, dict):
+        return False
+    for k in fields.keys():
+        if not isinstance(fields[k], str):
+            return False
+
+    return True
+
+
 class ApplicationServiceApi(SimpleHttpClient):
     """This class manages HS -> AS communications, including querying and
     pushing.
@@ -76,8 +98,10 @@ class ApplicationServiceApi(SimpleHttpClient):
     def query_3pe(self, service, kind, protocol, fields):
         if kind == ThirdPartyEntityKind.USER:
             uri = "%s/3pu/%s" % (service.url, urllib.quote(protocol))
+            required_field = "userid"
         elif kind == ThirdPartyEntityKind.LOCATION:
             uri = "%s/3pl/%s" % (service.url, urllib.quote(protocol))
+            required_field = "alias"
         else:
             raise ValueError(
                 "Unrecognised 'kind' argument %r to query_3pe()", kind
@@ -85,7 +109,24 @@ class ApplicationServiceApi(SimpleHttpClient):
 
         try:
             response = yield self.get_json(uri, fields)
-            defer.returnValue(response)
+            if not isinstance(response, list):
+                logger.warning(
+                    "query_3pe to %s returned an invalid response %r",
+                    uri, response
+                )
+                defer.returnValue([])
+
+            ret = []
+            for r in response:
+                if _is_valid_3pe_result(r, field=required_field):
+                    ret.append(r)
+                else:
+                    logger.warning(
+                        "query_3pe to %s returned an invalid result %r",
+                        uri, r
+                    )
+
+            defer.returnValue(ret)
         except Exception as ex:
             logger.warning("query_3pe to %s threw exception %s", uri, ex)
             defer.returnValue([])