Skip to content

Commit

Permalink
fix(stats): hide stats if no project access (#80447)
Browse files Browse the repository at this point in the history
Hide stats, session stats, transaction stats, and options in project
serialization if a user does not have access to the project.

This aligns with the behavior of OrganizationStatsEndpointV2 endpoint:

https://github.com/getsentry/sentry/blob/0b9d9f8ddcd27ea00b97bd66bc6380f9fddf360e/src/sentry/api/endpoints/organization_stats_v2.py#L202

These stats are used only by projectCard.tsx in the list of projects:
<img width="472" alt="image"
src="https://github.com/user-attachments/assets/00afa358-e256-423f-b34e-161d31945109">
Which are not visible when there is no access to a project, so it should
be a safe change.
  • Loading branch information
oioki authored Nov 12, 2024
1 parent 37db654 commit aecb53c
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 8 deletions.
18 changes: 10 additions & 8 deletions src/sentry/api/serializers/models/project.py
Original file line number Diff line number Diff line change
Expand Up @@ -770,14 +770,16 @@ def serialize(
)
if not self._collapse(LATEST_DEPLOYS_KEY):
context[LATEST_DEPLOYS_KEY] = attrs["deploys"]
if "stats" in attrs:
context.update(stats=attrs["stats"])
if "transactionStats" in attrs:
context.update(transactionStats=attrs["transactionStats"])
if "sessionStats" in attrs:
context.update(sessionStats=attrs["sessionStats"])
if "options" in attrs:
context.update(options=attrs["options"])

if attrs["has_access"]:
if "stats" in attrs:
context.update(stats=attrs["stats"])
if "transactionStats" in attrs:
context.update(transactionStats=attrs["transactionStats"])
if "sessionStats" in attrs:
context.update(sessionStats=attrs["sessionStats"])
if "options" in attrs:
context.update(options=attrs["options"])

return context

Expand Down
23 changes: 23 additions & 0 deletions tests/sentry/api/endpoints/test_organization_projects.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,29 @@ def test_with_stats(self):
self.organization.slug, qs_params={"statsPeriod": "48h"}, status_code=400
)

def test_no_stats_if_no_project_access(self):
projects = [self.create_project(teams=[self.team])]

# disable Open Membership
self.organization.flags.allow_joinleave = False
self.organization.save()

# user has no access to the first project
user_no_team = self.create_user(is_superuser=False)
self.create_member(
user=user_no_team, organization=self.organization, role="member", teams=[]
)
self.login_as(user_no_team)

response = self.get_success_response(
self.organization.slug, qs_params={"statsPeriod": "24h"}
)
self.check_valid_response(response, projects)

assert "stats" not in response.data[0]
assert "transactionStats" not in response.data[0]
assert "sessionStats" not in response.data[0]

def test_search(self):
project = self.create_project(teams=[self.team], name="bar", slug="bar")

Expand Down

0 comments on commit aecb53c

Please sign in to comment.