Repository: Kinto/kinto

Issue:
BackendError: Postgresql syntax error at or near ")" LINE 4:
```
BackendError: ProgrammingError: (psycopg2.ProgrammingError) syntax error at or near ")"
LINE 4:             ),
                    ^
 [SQL: "\n            WITH required_perms AS (\n              VALUES \n            ),\n            user_principals AS (\n              VALUES ('system.Authenticated'),('system.Everyone'),('basicauth:d5c74eef7e3040364a6eccbbb6a58f5bfe0c144c58c4f22f4e2d1098a57f5498'),('basicauth_d5c74eef7e3040364a6eccbbb6a58f5bfe0c144c58c4f22f4e2d1098a57f5498')\n            ),\n            potential_objects AS (\n              SELECT object_id, permission, required_perms.column1 AS pattern\n                FROM access_control_entries\n                JOIN user_principals\n                  ON (principal = user_principals.column1)\n                JOIN required_perms\n                  ON (permission = required_perms.column2)\n            )\n            SELECT object_id, permission\n              FROM potential_objects\n             WHERE object_id ~ pattern;\n
```
BackendError: Postgresql syntax error at or near ")" LINE 4:
```
BackendError: ProgrammingError: (psycopg2.ProgrammingError) syntax error at or near ")"
LINE 4:             ),
                    ^
 [SQL: "\n            WITH required_perms AS (\n              VALUES \n            ),\n            user_principals AS (\n              VALUES ('system.Authenticated'),('system.Everyone'),('basicauth:d5c74eef7e3040364a6eccbbb6a58f5bfe0c144c58c4f22f4e2d1098a57f5498'),('basicauth_d5c74eef7e3040364a6eccbbb6a58f5bfe0c144c58c4f22f4e2d1098a57f5498')\n            ),\n            potential_objects AS (\n              SELECT object_id, permission, required_perms.column1 AS pattern\n                FROM access_control_entries\n                JOIN user_principals\n                  ON (principal = user_principals.column1)\n                JOIN required_perms\n                  ON (permission = required_perms.column2)\n            )\n            SELECT object_id, permission\n              FROM potential_objects\n             WHERE object_id ~ pattern;\n
```


Discussion:
Don't have more context?

From what I see in the code, this could happen in `get_accessible_objects()` when `bound_permissions` is an empty list.

The context is that the request.path was having a prefix that was not recognized by Kinto so that no route where matching. I [fixed the fcgi script](https://github.com/Natim/auto-kinto-alwaysdata/commit/9347f726bd4be78ec5790fc7e6cc32d19cfc0079#diff-689de1db7b74ca115de1227b6cd8e179)

Don't have more context?

From what I see in the code, this could happen in `get_accessible_objects()` when `bound_permissions` is an empty list.

The context is that the request.path was having a prefix that was not recognized by Kinto so that no route where matching. I [fixed the fcgi script](https://github.com/Natim/auto-kinto-alwaysdata/commit/9347f726bd4be78ec5790fc7e6cc32d19cfc0079#diff-689de1db7b74ca115de1227b6cd8e179)


Resolving patch:
diff --git a/kinto/core/permission/postgresql/__init__.py b/kinto/core/permission/postgresql/__init__.py
--- a/kinto/core/permission/postgresql/__init__.py
+++ b/kinto/core/permission/postgresql/__init__.py
@@ -203,6 +203,9 @@ def get_authorized_principals(self, bound_permissions):
     def get_accessible_objects(self, principals, bound_permissions=None):
         principals_values = ','.join(["('%s')" % p for p in principals])
         if bound_permissions is None:
+            # Return all objects on which the specified principals have some
+            # permissions.
+            # (e.g. permissions endpoint which lists everything)
             query = """
             WITH user_principals AS (
               VALUES %(principals)s
@@ -212,6 +215,11 @@ def get_accessible_objects(self, principals, bound_permissions=None):
               JOIN user_principals
                 ON (principal = user_principals.column1);
             """ % dict(principals=principals_values)
+        elif len(bound_permissions) == 0:
+            # If the list of object permissions to filter on is empty, then
+            # do not bother querying the backend. The result will be empty.
+            # (e.g. root object /buckets)
+            return {}
         else:
             perms = [(o.replace('*', '.*'), p) for (o, p) in bound_permissions]
             perms_values = ','.join(["('%s', '%s')" % p for p in perms])


Test patch:
diff --git a/kinto/core/permission/testing.py b/kinto/core/permission/testing.py
--- a/kinto/core/permission/testing.py
+++ b/kinto/core/permission/testing.py
@@ -288,6 +288,10 @@ def test_accessible_objects(self):
                           set(['write', 'record:create']))
         self.assertEquals(per_object_ids['id2'], set(['read']))
 
+    def test_accessible_objects_supports_empty_list(self):
+        per_object_ids = self.permission.get_accessible_objects(['user1', 'group'], [])
+        self.assertEquals(per_object_ids, {})
+
     def test_accessible_objects_from_permission(self):
         self.permission.add_principal_to_ace('id1', 'write', 'user1')
         self.permission.add_principal_to_ace('id1', 'read', 'user1')