Skip to content

Commit 08507e2

Browse files
authored
Don't use subselect in DeleteIssuesByRepoID (#27332)
Part of https://codeberg.org/forgejo/discussions/issues/61 This is workaround for a bug in MariaDB
1 parent 2b06c10 commit 08507e2

File tree

1 file changed

+79
-64
lines changed

1 file changed

+79
-64
lines changed

models/issues/issue_update.go

+79-64
Original file line numberDiff line numberDiff line change
@@ -685,85 +685,100 @@ func UpdateReactionsMigrationsByType(ctx context.Context, gitServiceType api.Git
685685

686686
// DeleteIssuesByRepoID deletes issues by repositories id
687687
func DeleteIssuesByRepoID(ctx context.Context, repoID int64) (attachmentPaths []string, err error) {
688-
deleteCond := builder.Select("id").From("issue").Where(builder.Eq{"issue.repo_id": repoID})
689-
688+
// MariaDB has a performance bug: https://jira.mariadb.org/browse/MDEV-16289
689+
// so here it uses "DELETE ... WHERE IN" with pre-queried IDs.
690690
sess := db.GetEngine(ctx)
691-
// Delete content histories
692-
if _, err = sess.In("issue_id", deleteCond).
693-
Delete(&ContentHistory{}); err != nil {
694-
return nil, err
695-
}
696691

697-
// Delete comments and attachments
698-
if _, err = sess.In("issue_id", deleteCond).
699-
Delete(&Comment{}); err != nil {
700-
return nil, err
701-
}
692+
for {
693+
issueIDs := make([]int64, 0, db.DefaultMaxInSize)
702694

703-
// Dependencies for issues in this repository
704-
if _, err = sess.In("issue_id", deleteCond).
705-
Delete(&IssueDependency{}); err != nil {
706-
return nil, err
707-
}
695+
err := sess.Table(&Issue{}).Where("repo_id = ?", repoID).OrderBy("id").Limit(db.DefaultMaxInSize).Cols("id").Find(&issueIDs)
696+
if err != nil {
697+
return nil, err
698+
}
708699

709-
// Delete dependencies for issues in other repositories
710-
if _, err = sess.In("dependency_id", deleteCond).
711-
Delete(&IssueDependency{}); err != nil {
712-
return nil, err
713-
}
700+
if len(issueIDs) == 0 {
701+
break
702+
}
714703

715-
if _, err = sess.In("issue_id", deleteCond).
716-
Delete(&IssueUser{}); err != nil {
717-
return nil, err
718-
}
704+
// Delete content histories
705+
_, err = sess.In("issue_id", issueIDs).Delete(&ContentHistory{})
706+
if err != nil {
707+
return nil, err
708+
}
719709

720-
if _, err = sess.In("issue_id", deleteCond).
721-
Delete(&Reaction{}); err != nil {
722-
return nil, err
723-
}
710+
// Delete comments and attachments
711+
_, err = sess.In("issue_id", issueIDs).Delete(&Comment{})
712+
if err != nil {
713+
return nil, err
714+
}
724715

725-
if _, err = sess.In("issue_id", deleteCond).
726-
Delete(&IssueWatch{}); err != nil {
727-
return nil, err
728-
}
716+
// Dependencies for issues in this repository
717+
_, err = sess.In("issue_id", issueIDs).Delete(&IssueDependency{})
718+
if err != nil {
719+
return nil, err
720+
}
729721

730-
if _, err = sess.In("issue_id", deleteCond).
731-
Delete(&Stopwatch{}); err != nil {
732-
return nil, err
733-
}
722+
// Delete dependencies for issues in other repositories
723+
_, err = sess.In("dependency_id", issueIDs).Delete(&IssueDependency{})
724+
if err != nil {
725+
return nil, err
726+
}
734727

735-
if _, err = sess.In("issue_id", deleteCond).
736-
Delete(&TrackedTime{}); err != nil {
737-
return nil, err
738-
}
728+
_, err = sess.In("issue_id", issueIDs).Delete(&IssueUser{})
729+
if err != nil {
730+
return nil, err
731+
}
739732

740-
if _, err = sess.In("issue_id", deleteCond).
741-
Delete(&project_model.ProjectIssue{}); err != nil {
742-
return nil, err
743-
}
733+
_, err = sess.In("issue_id", issueIDs).Delete(&Reaction{})
734+
if err != nil {
735+
return nil, err
736+
}
744737

745-
if _, err = sess.In("dependent_issue_id", deleteCond).
746-
Delete(&Comment{}); err != nil {
747-
return nil, err
748-
}
738+
_, err = sess.In("issue_id", issueIDs).Delete(&IssueWatch{})
739+
if err != nil {
740+
return nil, err
741+
}
749742

750-
var attachments []*repo_model.Attachment
751-
if err = sess.In("issue_id", deleteCond).
752-
Find(&attachments); err != nil {
753-
return nil, err
754-
}
743+
_, err = sess.In("issue_id", issueIDs).Delete(&Stopwatch{})
744+
if err != nil {
745+
return nil, err
746+
}
755747

756-
for j := range attachments {
757-
attachmentPaths = append(attachmentPaths, attachments[j].RelativePath())
758-
}
748+
_, err = sess.In("issue_id", issueIDs).Delete(&TrackedTime{})
749+
if err != nil {
750+
return nil, err
751+
}
759752

760-
if _, err = sess.In("issue_id", deleteCond).
761-
Delete(&repo_model.Attachment{}); err != nil {
762-
return nil, err
763-
}
753+
_, err = sess.In("issue_id", issueIDs).Delete(&project_model.ProjectIssue{})
754+
if err != nil {
755+
return nil, err
756+
}
764757

765-
if _, err = db.DeleteByBean(ctx, &Issue{RepoID: repoID}); err != nil {
766-
return nil, err
758+
_, err = sess.In("dependent_issue_id", issueIDs).Delete(&Comment{})
759+
if err != nil {
760+
return nil, err
761+
}
762+
763+
var attachments []*repo_model.Attachment
764+
err = sess.In("issue_id", issueIDs).Find(&attachments)
765+
if err != nil {
766+
return nil, err
767+
}
768+
769+
for j := range attachments {
770+
attachmentPaths = append(attachmentPaths, attachments[j].RelativePath())
771+
}
772+
773+
_, err = sess.In("issue_id", issueIDs).Delete(&repo_model.Attachment{})
774+
if err != nil {
775+
return nil, err
776+
}
777+
778+
_, err = sess.In("id", issueIDs).Delete(&Issue{})
779+
if err != nil {
780+
return nil, err
781+
}
767782
}
768783

769784
return attachmentPaths, err

0 commit comments

Comments
 (0)