Refactor Rego filters WRT organizations (#10387)

This changes how filters are defined in Rego rules in two major ways:

* Instead of reverse polish notation, filters are now combined by using
  Lisp-like prefix notation: `[foo, bar, "|", baz, "|"]` is now `["|",
  foo, bar, baz]`. Subjectively, I find this more readable, especially in
  complex expressions, because it's easier to see which operands
  correspond to which operator. It also makes it easier to combine an
  arbitrary amount of filters using Rego (it's just
  `array.concat([op], filters)`), which enables the second change:

* Instead of manually writing out filters that check that a resource
  belongs to an organization, add a generic function,
  `add_organization_filter`, that automatically adds the necessary filters
  given the list of organization ID lookups. This eliminates a lot of
  duplicate logic.
This commit is contained in:
Roman Donchenko
2026-03-20 16:00:33 +02:00
committed by GitHub
parent 18bf10228e
commit 766cfb67a7
23 changed files with 298 additions and 381 deletions
+3
View File
@@ -21,6 +21,9 @@ rules:
# Mainly a style preference
# https://docs.styra.com/regal/rules/style/avoid-get-and-list-prefix
level: ignore
external-reference:
# https://docs.styra.com/regal/rules/style/external-reference
level: ignore
opa-fmt:
# https://docs.styra.com/regal/rules/style/opa-fmt
level: ignore
@@ -0,0 +1,5 @@
### Changed
- The format for filters in Rego policy files has changed; if you have
added custom policy files, you may need to update them
(<https://github.com/cvat-ai/cvat/pull/10387>)
@@ -50,9 +50,7 @@ allow if {
utils.is_resource_owner
}
q_user_is_owner(user) := [
{"owner_id": user.id},
]
q_user_is_owner(user) := {"owner_id": user.id}
# Django Q object to filter list of entries
filter := q_user_is_owner(input.auth.user)
@@ -57,48 +57,33 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"task__project__organization": org.id}, "|",
]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [
qobject := ["|",
{"task__owner_id": user.id},
{"task__assignee_id": user.id}, "|",
{"task__project__owner_id": user.id}, "|",
{"task__project__assignee_id": user.id}, "|",
{"task__assignee_id": user.id},
{"task__project__owner_id": user.id},
{"task__project__assignee_id": user.id},
]
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"task__project__organization": org.id}, "|",
]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"task__project__organization": org.id}, "|",
qobject := ["|",
{"task__owner_id": user.id},
{"task__assignee_id": user.id}, "|",
{"task__project__owner_id": user.id}, "|",
{"task__project__assignee_id": user.id}, "|",
"&"
{"task__assignee_id": user.id},
{"task__project__owner_id": user.id},
{"task__project__assignee_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"task__organization",
"task__project__organization",
])
+6 -9
View File
@@ -59,24 +59,21 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
qobject := [ {"organization": input.auth.organization.id} ]
} else := qobject if {
} else := {} if {
utils.has_perm(utils.USER)
organizations.has_perm(organizations.SUPERVISOR)
qobject := [ {"organization": input.auth.organization.id} ]
} else := qobject if {
utils.is_sandbox
qobject := [ {"owner": input.auth.user.id} ]
qobject := {"owner": input.auth.user.id}
} else := qobject if {
utils.is_organization
qobject := [ {"owner": input.auth.user.id}, {"organization": input.auth.organization.id}, "&" ]
qobject := {"owner": input.auth.user.id}
}
filter := utils.add_organization_filter(base_filter, ["organization"])
allow if {
input.scope in {utils.VIEW, utils.LIST_CONTENT}
utils.is_sandbox
+23 -35
View File
@@ -164,57 +164,45 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := [
{"issue__job__segment__task__organization": org.id},
{"issue__job__segment__task__project__organization": org.id}, "|"
]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [
qobject := ["|",
{"owner": user.id},
{"issue__owner": user.id}, "|",
{"issue__assignee": user.id}, "|",
{"issue__job__assignee": user.id}, "|",
{"issue__job__segment__task__owner": user.id}, "|",
{"issue__job__segment__task__assignee": user.id}, "|",
{"issue__job__segment__task__project__owner": user.id}, "|",
{"issue__job__segment__task__project__assignee": user.id}, "|"
{"issue__owner": user.id},
{"issue__assignee": user.id},
{"issue__job__assignee": user.id},
{"issue__job__segment__task__owner": user.id},
{"issue__job__segment__task__assignee": user.id},
{"issue__job__segment__task__project__owner": user.id},
{"issue__job__segment__task__project__assignee": user.id},
]
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := [
{"issue__job__segment__task__organization": org.id},
{"issue__job__segment__task__project__organization": org.id}, "|"
]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
org := input.auth.organization
qobject := [
qobject := ["|",
{"owner": user.id},
{"issue__owner": user.id}, "|",
{"issue__assignee": user.id}, "|",
{"issue__job__assignee": user.id}, "|",
{"issue__job__segment__task__owner": user.id}, "|",
{"issue__job__segment__task__assignee": user.id}, "|",
{"issue__job__segment__task__project__owner": user.id}, "|",
{"issue__job__segment__task__project__assignee": user.id}, "|",
{"issue__job__segment__task__organization": org.id},
{"issue__job__segment__task__project__organization": org.id}, "|", "&"
{"issue__owner": user.id},
{"issue__assignee": user.id},
{"issue__job__assignee": user.id},
{"issue__job__segment__task__owner": user.id},
{"issue__job__segment__task__assignee": user.id},
{"issue__job__segment__task__project__owner": user.id},
{"issue__job__segment__task__project__assignee": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"issue__job__segment__task__organization",
"issue__job__segment__task__project__organization",
])
allow if {
input.scope == utils.VIEW
utils.is_sandbox
+23 -33
View File
@@ -157,53 +157,43 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := [
{"job__segment__task__organization": org.id},
{"job__segment__task__project__organization": org.id}, "|"
]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [
{"owner": user.id}, {"assignee": user.id}, "|",
{"job__assignee": user.id}, "|",
{"job__segment__task__owner": user.id}, "|",
{"job__segment__task__assignee": user.id}, "|",
{"job__segment__task__project__owner": user.id}, "|",
{"job__segment__task__project__assignee": user.id}, "|"
qobject := ["|",
{"owner": user.id},
{"assignee": user.id},
{"job__assignee": user.id},
{"job__segment__task__owner": user.id},
{"job__segment__task__assignee": user.id},
{"job__segment__task__project__owner": user.id},
{"job__segment__task__project__assignee": user.id},
]
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := [
{"job__segment__task__organization": org.id},
{"job__segment__task__project__organization": org.id}, "|"
]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
org := input.auth.organization
qobject := [
{"owner": user.id}, {"assignee": user.id}, "|",
{"job__assignee": user.id}, "|",
{"job__segment__task__owner": user.id}, "|",
{"job__segment__task__assignee": user.id}, "|",
{"job__segment__task__project__owner": user.id}, "|",
{"job__segment__task__project__assignee": user.id}, "|",
{"job__segment__task__organization": org.id},
{"job__segment__task__project__organization": org.id}, "|", "&"
qobject := ["|",
{"owner": user.id},
{"assignee": user.id},
{"job__assignee": user.id},
{"job__segment__task__owner": user.id},
{"job__segment__task__assignee": user.id},
{"job__segment__task__project__owner": user.id},
{"job__segment__task__project__assignee": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"job__segment__task__organization",
"job__segment__task__project__organization",
])
allow if {
input.scope == utils.VIEW
utils.is_sandbox
+19 -24
View File
@@ -125,44 +125,39 @@ allow if {
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
qobject := [
{"segment__task__organization": input.auth.organization.id},
{"segment__task__project__organization": input.auth.organization.id}, "|" ]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [
qobject := ["|",
{"assignee_id": user.id},
{"segment__task__owner_id": user.id}, "|",
{"segment__task__assignee_id": user.id}, "|",
{"segment__task__project__owner_id": user.id}, "|",
{"segment__task__project__assignee_id": user.id}, "|"]
} else := qobject if {
{"segment__task__owner_id": user.id},
{"segment__task__assignee_id": user.id},
{"segment__task__project__owner_id": user.id},
{"segment__task__project__assignee_id": user.id},
]
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
qobject := [
{"segment__task__organization": input.auth.organization.id},
{"segment__task__project__organization": input.auth.organization.id}, "|"]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
qobject := [
qobject := ["|",
{"assignee_id": user.id},
{"segment__task__owner_id": user.id}, "|",
{"segment__task__assignee_id": user.id}, "|",
{"segment__task__project__owner_id": user.id}, "|",
{"segment__task__project__assignee_id": user.id}, "|",
{"segment__task__organization": input.auth.organization.id},
{"segment__task__project__organization": input.auth.organization.id}, "|", "&"]
{"segment__task__owner_id": user.id},
{"segment__task__assignee_id": user.id},
{"segment__task__project__owner_id": user.id},
{"segment__task__project__assignee_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"segment__task__organization",
"segment__task__project__organization",
])
allow if {
input.scope in {utils.CREATE, utils.DELETE}
utils.has_perm(utils.USER)
+15 -24
View File
@@ -57,42 +57,33 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"project__organization": org.id}, "|",
]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [
qobject := ["|",
{"task__owner_id": user.id},
{"task__assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|",
{"project__assignee_id": user.id}, "|",
{"task__assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"project__organization": org.id}, "|",
]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
qobject := [
qobject := ["|",
{"task__owner_id": user.id},
{"task__assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|",
{"project__assignee_id": user.id}, "|",
{"task__assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"task__organization",
"project__organization",
])
+6 -11
View File
@@ -86,29 +86,24 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
qobject := [ {"organization": input.auth.organization.id} ]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"assignee_id": user.id}, "|" ]
} else := qobject if {
qobject := ["|", {"owner_id": user.id}, {"assignee_id": user.id}]
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
qobject := [ {"organization": input.auth.organization.id} ]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"assignee_id": user.id}, "|",
{"organization": input.auth.organization.id}, "&" ]
qobject := ["|", {"owner_id": user.id}, {"assignee_id": user.id}]
}
filter := utils.add_organization_filter(base_filter, ["organization"])
allow if {
input.scope == utils.VIEW
utils.is_sandbox
+17 -18
View File
@@ -152,34 +152,33 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
qobject := [ {"organization": input.auth.organization.id},
{"project__organization": input.auth.organization.id}, "|"]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|", {"project__assignee_id": user.id}, "|"]
} else := qobject if {
utils.is_organization
utils.has_perm(utils.USER)
qobject := ["|",
{"owner_id": user.id},
{"assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
} else := {} if {
organizations.has_perm(organizations.MAINTAINER)
qobject := [ {"organization": input.auth.organization.id},
{"project__organization": input.auth.organization.id}, "|"]
utils.has_perm(utils.USER)
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|", {"project__assignee_id": user.id}, "|",
{"organization": input.auth.organization.id},
{"project__organization": input.auth.organization.id}, "|", "&"]
qobject := ["|",
{"owner_id": user.id},
{"assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, ["organization", "project__organization"])
allow if {
input.scope in {
utils.VIEW, utils.VIEW_ANNOTATIONS, utils.EXPORT_DATASET, utils.VIEW_METADATA,
+6 -6
View File
@@ -46,17 +46,17 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_sandbox
qobject := [ {"id": input.auth.user.id} ]
} else := qobject if {
org_id := input.auth.organization.id
qobject := [ {"memberships__organization": org_id} ]
qobject := {"id": input.auth.user.id}
} else := {} if {
utils.is_organization
}
filter := utils.add_organization_filter(base_filter, ["memberships__organization"])
allow if {
input.scope == utils.VIEW
input.resource.id == input.auth.user.id
+6 -10
View File
@@ -55,24 +55,20 @@ allow if {
}
filter := [] if {
base_filter := {} if {
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
qobject := [ {"org_id": input.auth.organization.id} ]
} else := qobject if {
utils.is_sandbox
qobject := [ {"user_id": input.auth.user.id} ]
} else := qobject if {
qobject := {"user_id": input.auth.user.id}
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
qobject := [ {"org_id": input.auth.organization.id} ]
} else := qobject if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.WORKER)
qobject := [ {"user_id": input.auth.user.id}, {"org_id": input.auth.organization.id} ]
qobject := {"user_id": input.auth.user.id}
}
filter := utils.add_organization_filter(base_filter, ["org_id"])
+18 -19
View File
@@ -9,7 +9,7 @@ import operator
from abc import ABCMeta, abstractmethod
from collections.abc import Sequence
from enum import Enum
from functools import cached_property
from functools import cached_property, reduce
from pathlib import Path
from typing import TYPE_CHECKING, Any, TypeAlias, TypeVar
@@ -241,33 +241,32 @@ class OpenPolicyAgentPermission(metaclass=ABCMeta):
with make_requests_session() as session:
r = session.post(url, json=self.payload).json()["result"]
q_objects = []
ops_dict = {
binary_ops_dict = {
"|": operator.or_,
"&": operator.and_,
"~": operator.not_,
}
for item in r:
if isinstance(item, str):
val1 = q_objects.pop()
if item == "~":
q_objects.append(ops_dict[item](val1))
else:
val2 = q_objects.pop()
q_objects.append(ops_dict[item](val1, val2))
else:
q_objects.append(Q(**item))
if q_objects:
assert len(q_objects) == 1
else:
q_objects.append(Q())
def parse_filter(expr):
match expr:
case ["~", arg]:
return ~parse_filter(arg)
case [op, *args]:
return reduce(binary_ops_dict[op], map(parse_filter, args))
case {} if not expr:
# Empty Q() exhibits some bizarre behavior when used in expressions
# (e.g. ~Q() works the same as Q()), so we use this as a more predictable
# "always true" filter.
return ~Q(pk__in=[])
case {}:
return Q(**expr)
case _:
assert False, "unknown expression type"
# By default, a QuerySet will not eliminate duplicate rows. If your
# query spans multiple tables (e.g. members__user_id, owner_id), it's
# possible to get duplicate results when a QuerySet is evaluated.
# That's when you'd use distinct().
return queryset.filter(q_objects[0]).distinct()
return queryset.filter(parse_filter(r)).distinct()
@classmethod
def get_per_field_update_scopes(cls, request, scopes_per_field):
+13
View File
@@ -101,3 +101,16 @@ is_sandbox if {
is_organization if {
input.auth.organization != null
}
add_organization_filter(base_filter, organization_fields) := base_filter if is_sandbox
add_organization_filter(base_filter, organization_fields) := qobject if {
is_organization
qobject := ["&", base_filter, make_organization_filter(organization_fields)]
}
make_organization_filter(organization_fields) := qobject if {
is_array(organization_fields)
count(organization_fields) > 0
qobject := array.concat(["|"], [{f: input.auth.organization.id} | some f in organization_fields])
}
+19 -16
View File
@@ -43,30 +43,33 @@ allow if {
utils.has_perm(utils.WORKER)
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
qobject := [ {"organization": input.auth.organization.id},
{"project__organization": input.auth.organization.id}, "|"]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|", {"project__assignee_id": user.id}, "|"]
} else := qobject if {
qobject := ["|",
{"owner_id": user.id},
{"assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
qobject := [ {"organization": input.auth.organization.id},
{"project__organization": input.auth.organization.id}, "|"]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|", {"project__assignee_id": user.id}, "|",
{"organization": input.auth.organization.id},
{"project__organization": input.auth.organization.id}, "|", "&"]
qobject := ["|",
{"owner_id": user.id},
{"assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"organization",
"project__organization",
])
+12 -12
View File
@@ -46,30 +46,30 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
utils.is_sandbox
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [ {"owner": user.id}, {"membership__user": user.id}, "|" ]
} else := qobject if {
utils.is_organization
utils.is_admin
qobject := [ {"membership__organization": input.auth.organization.id} ]
} else := qobject if {
qobject := ["|",
{"owner": user.id},
{"membership__user": user.id},
]
} else := {} if {
utils.is_organization
organizations.is_staff
utils.has_perm(utils.USER)
qobject := [ {"membership__organization": input.auth.organization.id} ]
} else := qobject if {
utils.is_organization
user := input.auth.user
org_id := input.auth.organization.id
qobject := [ {"owner": user.id}, {"membership__user": user.id}, "|",
{"membership__organization": org_id}, "&" ]
qobject := ["|",
{"owner": user.id},
{"membership__user": user.id},
]
}
filter := utils.add_organization_filter(base_filter, ["membership__organization"])
allow if {
input.scope == utils.CREATE
input.auth.organization.id == input.resource.organization.id
+9 -12
View File
@@ -46,25 +46,22 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_sandbox
qobject := [ {"user": input.auth.user.id}, {"is_active": true}, "&" ]
} else := qobject if {
utils.is_admin
org_id := input.auth.organization.id
qobject := [ {"organization": org_id} ]
} else := qobject if {
qobject := ["&",
{"user": input.auth.user.id},
{"is_active": true},
]
} else := {} if {
organizations.is_staff
org_id := input.auth.organization.id
qobject := [ {"organization": org_id} ]
} else := qobject if {
org_id := input.auth.organization.id
qobject := [ {"organization": org_id}, {"is_active": true}, "&" ]
qobject := {"is_active": true}
}
filter := utils.add_organization_filter(base_filter, ["organization"])
allow if {
input.scope == utils.VIEW
input.resource.is_active
@@ -69,11 +69,17 @@ allow if {
utils.has_perm(utils.USER)
}
filter := [] if { # Django Q object to filter list of entries
filter := {} if { # Django Q object to filter list of entries
utils.is_admin
} else := qobject if {
user := input.auth.user
qobject := [{"members__user_id": user.id}, {"members__is_active": true}, "&", {"owner_id": user.id}, "|" ]
qobject := ["|",
["&",
{"members__user_id": user.id},
{"members__is_active": true},
],
{"owner_id": user.id},
]
}
allow if {
+21 -33
View File
@@ -58,51 +58,39 @@ allow if {
}
q_user_is_maintainer(user) := [
q_user_is_maintainer(user) := ["|",
{"report__job__segment__task__owner_id": user.id},
{"report__job__segment__task__assignee_id": user.id}, "|",
{"report__job__segment__task__project__owner_id": user.id}, "|",
{"report__job__segment__task__project__assignee_id": user.id}, "|",
{"report__task__owner_id": user.id}, "|",
{"report__task__assignee_id": user.id}, "|",
{"report__task__project__owner_id": user.id}, "|",
{"report__task__project__assignee_id": user.id}, "|",
{"report__project__owner_id": user.id}, "|",
{"report__project__assignee_id": user.id}, "|",
{"report__job__segment__task__assignee_id": user.id},
{"report__job__segment__task__project__owner_id": user.id},
{"report__job__segment__task__project__assignee_id": user.id},
{"report__task__owner_id": user.id},
{"report__task__assignee_id": user.id},
{"report__task__project__owner_id": user.id},
{"report__task__project__assignee_id": user.id},
{"report__project__owner_id": user.id},
{"report__project__assignee_id": user.id},
]
q_object_has_org(org) := [
{"report__job__segment__task__organization": org.id},
{"report__job__segment__task__project__organization": org.id}, "|",
{"report__task__organization": org.id}, "|",
{"report__task__project__organization": org.id}, "|",
{"report__project__organization": org.id}, "|",
]
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := q_object_has_org(org)
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := q_user_is_maintainer(user)
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := q_object_has_org(org)
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
org := input.auth.organization
qobject := array.concat(
array.concat(q_object_has_org(org), q_user_is_maintainer(user)),
["&"]
)
qobject := q_user_is_maintainer(user)
}
filter := utils.add_organization_filter(base_filter, [
"report__job__segment__task__organization",
"report__job__segment__task__project__organization",
"report__task__organization",
"report__task__project__organization",
"report__project__organization",
])
@@ -88,54 +88,39 @@ allow if {
}
q_user_is_maintainer(user) := [
q_user_is_maintainer(user) := ["|",
{"job__segment__task__owner_id": user.id},
{"job__segment__task__assignee_id": user.id}, "|",
{"job__segment__task__project__owner_id": user.id}, "|",
{"job__segment__task__project__assignee_id": user.id}, "|",
{"task__owner_id": user.id}, "|",
{"task__assignee_id": user.id}, "|",
{"task__project__owner_id": user.id}, "|",
{"task__project__assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|",
{"project__assignee_id": user.id}, "|",
{"job__segment__task__assignee_id": user.id},
{"job__segment__task__project__owner_id": user.id},
{"job__segment__task__project__assignee_id": user.id},
{"task__owner_id": user.id},
{"task__assignee_id": user.id},
{"task__project__owner_id": user.id},
{"task__project__assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
q_object_has_org(org) := [
{"job__segment__task__organization": org.id},
{"job__segment__task__project__organization": org.id}, "|",
{"task__organization": org.id}, "|",
{"task__project__organization": org.id}, "|",
{"project__organization": org.id}, "|",
]
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := q_object_has_org(org)
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := q_user_is_maintainer(user)
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := q_object_has_org(org)
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
org := input.auth.organization
qobject := array.concat(
array.concat(
q_object_has_org(org),
q_user_is_maintainer(user),
),
["&"]
)
qobject := q_user_is_maintainer(user)
}
filter := utils.add_organization_filter(base_filter, [
"job__segment__task__organization",
"job__segment__task__project__organization",
"task__organization",
"task__project__organization",
"project__organization",
])
@@ -57,55 +57,38 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"task__project__organization": org.id}, "|",
{"project__organization": org.id}, "|",
]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [
qobject := ["|",
{"task__owner_id": user.id},
{"task__assignee_id": user.id}, "|",
{"task__project__owner_id": user.id}, "|",
{"task__project__assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|",
{"project__assignee_id": user.id}, "|",
{"task__assignee_id": user.id},
{"task__project__owner_id": user.id},
{"task__project__assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
} else := qobject if {
} else := {} if {
utils.is_organization
utils.has_perm(utils.USER)
organizations.has_perm(organizations.MAINTAINER)
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"task__project__organization": org.id}, "|",
{"project__organization": org.id}, "|",
]
} else := qobject if {
organizations.has_perm(organizations.WORKER)
user := input.auth.user
org := input.auth.organization
qobject := [
{"task__organization": org.id},
{"task__project__organization": org.id}, "|",
{"project__organization": org.id}, "|",
qobject := ["|",
{"task__owner_id": user.id},
{"task__assignee_id": user.id}, "|",
{"task__project__owner_id": user.id}, "|",
{"task__project__assignee_id": user.id}, "|",
{"project__owner_id": user.id}, "|",
{"project__assignee_id": user.id}, "|",
"&"
{"task__assignee_id": user.id},
{"task__project__owner_id": user.id},
{"task__project__assignee_id": user.id},
{"project__owner_id": user.id},
{"project__assignee_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, [
"task__organization",
"task__project__organization",
"project__organization",
])
+12 -11
View File
@@ -65,31 +65,32 @@ allow if {
organizations.is_member
}
filter := [] if { # Django Q object to filter list of entries
base_filter := {} if { # Django Q object to filter list of entries
utils.is_admin
utils.is_sandbox
} else := qobject if {
utils.is_admin
utils.is_organization
qobject := [ {"organization": input.auth.organization.id} ]
} else := qobject if {
utils.is_sandbox
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"project__owner_id": user.id}, "|" ]
} else := qobject if {
qobject := ["|",
{"owner_id": user.id},
{"project__owner_id": user.id},
]
} else := {} if {
utils.is_organization
utils.has_perm(utils.WORKER)
organizations.has_perm(organizations.MAINTAINER)
qobject := [ {"organization": input.auth.organization.id} ]
} else := qobject if {
utils.is_organization
utils.has_perm(utils.WORKER)
organizations.has_perm(organizations.WORKER)
user := input.auth.user
qobject := [ {"owner_id": user.id}, {"project__owner_id": user.id},
"|", {"organization": input.auth.organization.id}, "&"]
qobject := ["|",
{"owner_id": user.id},
{"project__owner_id": user.id},
]
}
filter := utils.add_organization_filter(base_filter, ["organization"])
allow if {
input.scope == utils.VIEW