Skip to content

Commit 68f6847

Browse files
authored
fix: Handle bad input before checking permission (#5502)
1 parent 54131af commit 68f6847

3 files changed

Lines changed: 54 additions & 10 deletions

File tree

.github/workflows/conventional-commit.yml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,9 @@ name: Conventional Commit
22

33
on:
44
pull_request:
5-
types: [opened, synchronize, reopened, ready_for_review]
5+
types:
6+
- edited
7+
- opened
68

79
jobs:
810
conventional-commit:

api/features/feature_segments/permissions.py

Lines changed: 14 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
from contextlib import suppress
2-
31
from common.environments.permissions import (
42
MANAGE_SEGMENT_OVERRIDES,
53
)
@@ -22,13 +20,20 @@ def has_permission(self, request, view): # type: ignore[no-untyped-def]
2220
return True
2321

2422
if view.action == "create":
25-
with suppress(Environment.DoesNotExist, ValueError):
26-
environment = request.data.get("environment")
27-
environment = Environment.objects.get(id=int(environment))
28-
29-
return request.user.has_environment_permission(
30-
MANAGE_SEGMENT_OVERRIDES, environment
31-
)
23+
try:
24+
# Validate here because this evaluates prior to the serializer layer
25+
environment_pk = int(request.data.get("environment"))
26+
except (TypeError, ValueError):
27+
return False
28+
29+
try:
30+
environment = Environment.objects.get(pk=environment_pk)
31+
except Environment.DoesNotExist:
32+
return False
33+
34+
return request.user.has_environment_permission(
35+
MANAGE_SEGMENT_OVERRIDES, environment
36+
)
3237

3338
return False
3439

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
from typing import Any, Callable
2+
3+
import pytest
4+
from pytest_mock import MockerFixture
5+
6+
from environments.models import Environment
7+
from features.feature_segments import permissions
8+
9+
10+
@pytest.mark.parametrize(
11+
"get_payload, expected",
12+
[
13+
(lambda environment: {}, False),
14+
(lambda environment: {"environment": "invalid"}, False),
15+
(lambda environment: {"environment": 10_000_000}, False), # Please don't exist
16+
(lambda environment: {"environment": environment.pk}, True),
17+
],
18+
)
19+
def test_FeatureSegmentPermissions_has_permission__create_action__handles_environment_arg(
20+
environment: Environment,
21+
expected: bool,
22+
mocker: MockerFixture,
23+
get_payload: Callable[[Environment], dict[str, Any]],
24+
) -> None:
25+
# Given
26+
view = mocker.Mock(action="create", detail=False)
27+
request = mocker.Mock(data=get_payload(environment))
28+
request.user.has_environment_permission.return_value = True
29+
30+
# When
31+
permission = mocker.Mock(spec=permissions.FeatureSegmentPermissions)
32+
result = permissions.FeatureSegmentPermissions.has_permission( # type: ignore[no-untyped-call]
33+
permission, request, view
34+
)
35+
36+
# Then
37+
assert result is expected

0 commit comments

Comments
 (0)