Parsing#

pg_grant.parse.get_default_privileges(type: PgObjectType, owner: str) List[Privileges][source]#

Return a list of Privileges objects matching the default privileges for that type.

This can be called when the ACL item from PostgreSQL is NULL to determine the implicit access privileges.

pg_grant.parse.parse_acl(acl: List[str] | Tuple[str, ...], type: PgObjectType | None = None, subname: str | None = None) List[Privileges][source]#
Parameters:
  • acl – ACL, e.g. ['alice=arwdDxt/alice', 'bob=arwdDxt/alice']

  • type – Optional. If passed, all privileges may be reduced to ['ALL'].

  • subname – Optional, e.g. for column privileges.

Returns:

List of Privileges.

See also

This is a simple wrapper; parse_acl_item() is called for each item in acl.

pg_grant.parse.parse_acl_item(acl_item: str, type: PgObjectType | None = None, subname: str | None = None) Privileges[source]#

Port of parseAclItem from dumputils.c

Parameters:
  • acl_item – ACL item, e.g. 'alice=arwdDxt/bob'

  • type – Optional. If passed, all privileges may be reduced to ['ALL'].

  • subname – Optional, e.g. for column privileges. Must be output from psycopg.sql.Identifier() or similar.

Warning

If the privs or privswgo attributes of the returned object will be used to construct an SQL statement, subname must be a valid identifier (e.g. by calling as_string() on psycopg.sql.Identifier) in order to prevent SQL injection attacks.

grant() and revoke() are not vulnerable, because those functions quote the embedded identifier:

>>> from pg_grant import PgObjectType, parse_acl_item
>>> from pg_grant.sql import grant
>>> privs = parse_acl_item("alice=r/bob", subname="user")
>>> privs.privs
['SELECT (user)']
>>> str(grant(privs.privs, PgObjectType.TABLE, "tbl1", "alice"))
'GRANT SELECT ("user") ON TABLE tbl1 TO alice'

Note that "user" was quoted by grant().

In other cases, make sure to quote subname:

>>> import psycopg
>>> from psycopg.sql import Identifier
>>> conn = psycopg.connect(...)
>>> parse_acl_item("alice=r/bob", subname=Identifier("user").as_string(conn))
>>> privs.privs
['SELECT ("user")']
Returns:

Privileges