Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(issue-view-sharing): Add migration to create new groupsearchviewstarred table #86065

Merged
merged 6 commits into from
Feb 28, 2025

Conversation

MichaelSun48
Copy link
Member

This PR creates a new table, groupsearchviewstarred. More details on why we are doing this can be found in this tech spec (internal only).

TL;DR — Previously we could make the assumption that all views in the original groupsearchview table were visible (starred) in the UI, so we could assign each row a position column. Now, that isn't the case, AND you can have a view in your UI that doesn't belong to you. Hence why we need a new table to keep track of which views are visible for each member, and what position they occupy.

The position column in the original groupsearchview table will be dropped once the data is migrated over and endpoint logic is reconfigured to use this new table.

@github-actions github-actions bot added the Scope: Backend Automatically applied to PRs that change backend components label Feb 27, 2025
@MichaelSun48 MichaelSun48 marked this pull request as ready for review February 27, 2025 21:26
@MichaelSun48 MichaelSun48 requested a review from a team as a code owner February 27, 2025 21:26
@MichaelSun48 MichaelSun48 requested a review from a team February 27, 2025 21:26
Copy link
Contributor

github-actions bot commented Feb 27, 2025

This PR has a migration; here is the generated SQL for src/sentry/migrations/0836_create_groupsearchviewstarred_table.py ()

--
-- Create model GroupSearchViewStarred
--
CREATE TABLE "sentry_groupsearchviewstarred" ("id" bigint NOT NULL PRIMARY KEY GENERATED BY DEFAULT AS IDENTITY, "date_updated" timestamp with time zone NOT NULL, "date_added" timestamp with time zone NOT NULL, "user_id" bigint NOT NULL, "position" smallint NOT NULL CHECK ("position" >= 0), "group_search_view_id" bigint NOT NULL, "organization_id" bigint NOT NULL, CONSTRAINT "sentry_groupsearchviewstarred_unique_view_position_per_org_user" UNIQUE ("user_id", "organization_id", "position") DEFERRABLE INITIALLY DEFERRED);
ALTER TABLE "sentry_groupsearchviewstarred" ADD CONSTRAINT "sentry_groupsearchvi_group_search_view_id_9bd8a20c_fk_sentry_gr" FOREIGN KEY ("group_search_view_id") REFERENCES "sentry_groupsearchview" ("id") DEFERRABLE INITIALLY DEFERRED NOT VALID;
ALTER TABLE "sentry_groupsearchviewstarred" VALIDATE CONSTRAINT "sentry_groupsearchvi_group_search_view_id_9bd8a20c_fk_sentry_gr";
ALTER TABLE "sentry_groupsearchviewstarred" ADD CONSTRAINT "sentry_groupsearchvi_organization_id_130afeb8_fk_sentry_or" FOREIGN KEY ("organization_id") REFERENCES "sentry_organization" ("id") DEFERRABLE INITIALLY DEFERRED NOT VALID;
ALTER TABLE "sentry_groupsearchviewstarred" VALIDATE CONSTRAINT "sentry_groupsearchvi_organization_id_130afeb8_fk_sentry_or";
CREATE INDEX CONCURRENTLY "sentry_groupsearchviewstarred_user_id_d8550c0c" ON "sentry_groupsearchviewstarred" ("user_id");
CREATE INDEX CONCURRENTLY "sentry_groupsearchviewstarred_group_search_view_id_9bd8a20c" ON "sentry_groupsearchviewstarred" ("group_search_view_id");
CREATE INDEX CONCURRENTLY "sentry_groupsearchviewstarred_organization_id_130afeb8" ON "sentry_groupsearchviewstarred" ("organization_id");

Copy link

codecov bot commented Feb 27, 2025

Codecov Report

All modified and coverable lines are covered by tests ✅

✅ All tests successful. No failed tests found.

Additional details and impacted files
@@             Coverage Diff             @@
##           master   #86065       +/-   ##
===========================================
+ Coverage   42.23%   87.89%   +45.65%     
===========================================
  Files        9675     9706       +31     
  Lines      548727   550387     +1660     
  Branches    21419    21419               
===========================================
+ Hits       231770   483753   +251983     
+ Misses     316576    66253   -250323     
  Partials      381      381               


user_id = HybridCloudForeignKey("sentry.User", on_delete="CASCADE")
organization = FlexibleForeignKey("sentry.Organization")
group_search_view = FlexibleForeignKey("sentry.GroupSearchView")
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Question: There shouldn't be any challenges for adding an index to this column in the future, right? It's not within the scope of this project, but I could see a future where we want to know who/how many people have starred a shared view.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

no, super easy

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Foreign keys make indexes as part of the constraint creation.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

https://stackoverflow.com/a/970605

i don't think group_search_view is unique, so i didn't think the foreign key created an index?

Comment on lines +14 to +15
user_id = HybridCloudForeignKey("sentry.User", on_delete="CASCADE")
organization = FlexibleForeignKey("sentry.Organization")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why can't we use OrganizationMember instead here?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Consistency with the original groupsearchview table. I don't like it either, but otherwise we're going to have to convert between them when trying to sync the tables.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what happens to the view when the user leaves the organization?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

also -- curious what this behavior today is too

Copy link
Member Author

@MichaelSun48 MichaelSun48 Feb 27, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Currently, I supposed their views just stay put, and if they ever rejoin then they'll still be there. Not great.

This makes me want to eventually replace the user_id/org columns with a member column

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can also imagine the case where someone creates a critical view that everyone at the company uses. then when that person leaves, that view gets nuked and everyone is sad. may be worth making the user / member column nullable as well, and when a user leaves an organization, allowing for views with no owner.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Currently, I supposed their views just stay put, and if they ever rejoin then they'll still be there. Not great.

This seems like a good thing though. If you have a member leave/return they get to keep their stuff.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Its definitely convenient, but we'd slowly build up dead records (though probably to any damaging scale)

Copy link
Member

@markstory markstory left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Schema looks good to me.

Comment on lines +14 to +15
user_id = HybridCloudForeignKey("sentry.User", on_delete="CASCADE")
organization = FlexibleForeignKey("sentry.Organization")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Currently, I supposed their views just stay put, and if they ever rejoin then they'll still be there. Not great.

This seems like a good thing though. If you have a member leave/return they get to keep their stuff.


user_id = HybridCloudForeignKey("sentry.User", on_delete="CASCADE")
organization = FlexibleForeignKey("sentry.Organization")
group_search_view = FlexibleForeignKey("sentry.GroupSearchView")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Foreign keys make indexes as part of the constraint creation.

@MichaelSun48 MichaelSun48 merged commit e68102b into master Feb 28, 2025
49 checks passed
@MichaelSun48 MichaelSun48 deleted the msun/sharedViews/createSharedTable branch February 28, 2025 20:00
MichaelSun48 added a commit that referenced this pull request Mar 1, 2025
#86153)

This PR updates the `PUT` `/group-search-views/` endpoint to double
write the positions parameter to the new table created in [this
PR](#86065). This is necessary
to ensure the tables stay in sync before backfilling.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Scope: Backend Automatically applied to PRs that change backend components
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants