IDOR in sentry error tracking leaks issues from project maintainers other sentry projects
**[HackerOne report #1546138](https://hackerone.com/reports/1546138)** by `joaxcar` on 2022-04-20, assigned to @ngeorge1:
[Report](#report) | [How To Reproduce](#how-to-reproduce)
## Report
#### Summary
Maintainers of any project can activate "Sentry error tracking" ([documentation](https://docs.gitlab.com/ee/operations/error_tracking.html)) by going to
https://gitlab.com/GROUPNAME/PROJECCTNAME/-/settings/operations
and expand the `error tracking` tab.
This enables users with access to the project to view a list of `error reports` synced from a connected Sentry server `project` by visiting
https://gitlab.com/GROUPNAME/PROJECTNAME/-/error_tracking .
And `error details` by visiting https://gitlab.com/GROUPNAME/PROJECTNAME/-/error_tracking/ID/details where ID is an integer value (this is important for reproducibility of the attack)
The way GitLab handles this functionality is by requesting the maintainer to enter three values
1. Sentry API URL
2. Auth Token (to the Sentry server)
3. Project (from a list which is polled by the backend from the Sentry server using the above credentials)
The `project` name will be of the form `username | projectname`
When a user visits the `/-/error_tracking` page the GitLab backend makes a request towards the Sentry sever like so
```
https://sentry.example.com/api/0/projects/USER/PROJECT/issues/
```
where `USER` and `PROJECT` is filled from the `project` configured above.
Which returns a list of all `errors` related to the Sentry `project`
When clicking on one of these errors in the UI the user is redirected to `/-/error_tracking/ID/details` where the ID is taken from the clicked error. The backend will make a request like so
```
https://sentry.example.com/api/0/issues/ID
```
This request does not contain any check as to which `project` this (error)issue is related. This allows an attacker to enumerate all issues that the Sentry user have access to by replacing ID in `/-/error_tracking/ID/details` with an incrementing value.
If the Sentry server is a cloud user on sentry.io this will result in a lot of bad requests as the issue ID is an incrementing value shared by all users on the platform. It makes leaking issues a bit harder, but not impossible. A worse scenario is if the configured sentry server is self-hosted (not uncommon). Then the amount of issues on the server will be way fewer and the user will probably have access to a lot higher percentage of the issues.
GitLab will present the attacker with a full detail view of the issue with `ID` injected in the URL. More than this, the issue(error) can also be `resolved` and/or `ignored` by the attacker by clicking `resolve` or `ignore` in the UI. This will remove the error from the issue list in the project where the issue belongs! Thus, this issue also have an integrity impact.
The attacker needs to be at least a `Reporter` in the project to view the `Error tracker`. (Resolving and ignoring error is also possible as a `Reporter`, is this by design? Seems a bit too strong for a reporter...)
The leaked data contains both information about the issue but also stack traces from source code, one called!
#### Steps to reproduce
Make sure to have a Sentry sever, or an account on sentry.io ([GitLab guide to sentry integration](https://docs.gitlab.com/ee/operations/error_tracking.html#enabling-sentry))
Make sure to generate an Auth token here https://sentry.io/settings/account/api/auth-tokens/
1. Login to sentry.io and go to `projects` https://sentry.io/organizations/USERNAME/projects/
2. Create two projects, one called `private` and one called `public`
3. Go into both projects and click the `generate sample event` button
4. Click on `issues` in the left menu of sentry.io and click on the event. Take a note of the event ID shown in the URL
5. Switch to the other project and go to `issues` again and take a note of the other issue ID
You shall now have two event IDs, one in each project. Go over to GitLab
6. Login to GitLab as a victim user
7. Create a new project and go to https://gitlab.com/GROUPNAME/PROJECTNAME/-/settings/operations
8. Expand `error tracking` and fill out the form with https://sentry.io and your `Auth token`
9. Click `connect`
10. Pick the project `USERNAME | public` in the project dropdown
11. Save
12. Go to https://gitlab.com/GROUPNAME/PROJECTNAME/-/project_members
13. Invite another user as `Reporter`
14. Log out and log in as the other user
15. Now go to https://gitlab.com/GROUPNAME/PROJECTNAME/-/error_tracking
16. There should be one event in the list
17. Click the event and the event details will be shown
18. Now swap the ID number in the URL for the issue from the other project, click enter
19. Details for the other issue will be shown. Info leak
20. Click the buttons `resolve` and `ignore`
Go back to sentry.io
18. Open the private project and go to the issue list
19. notice that the private issue is now `resolved` and `ignored`. Integrity impact
#### Impact
An attacker can enumerate issues from all sentry project of the maintainer of the project. The attacker can also `resolve` and `ignore` the issues
#### What is the current *bug* behavior?
GitLab uses Sentry issue ID directly from attacker supplied URL without checking which sentry project it belongs to.
#### What is the expected *correct* behavior?
Only issues from the configured sentry project should be shown
#### Output of checks
This bug happens on GitLab.com
#### Impact
An attacker can enumerate issues from all sentry project of the maintainer of the project. The attacker can also `resolve` and `ignore` the issues
## How To Reproduce
Please add [reproducibility information] to this section:
1.
1.
1.
[reproducibility information]: https://about.gitlab.com/handbook/engineering/security/#reproducibility-on-security-issues
issue