From 2026d885d6c11793e6fd68d06f163de90440e52d Mon Sep 17 00:00:00 2001
From: Lunny Xiao <xiaolunwen@gmail.com>
Date: Sun, 23 Aug 2020 01:12:40 +0800
Subject: [PATCH] Fix bug on migration 147 (#12565)

---
 models/migrations/v147.go | 98 +++++++++++++++++++++++++++++------------------
 1 file changed, 60 insertions(+), 38 deletions(-)

diff --git a/models/migrations/v147.go b/models/migrations/v147.go
index 9716d6e83b..a39b224039 100644
--- a/models/migrations/v147.go
+++ b/models/migrations/v147.go
@@ -82,51 +82,73 @@ func createReviewsForCodeComments(x *xorm.Engine) error {
 	if err := x.Sync2(new(Review), new(Comment)); err != nil {
 		return err
 	}
-	sess := x.NewSession()
-	defer sess.Close()
-	if err := sess.Begin(); err != nil {
-		return err
-	}
-	if err := sess.Where("review_id = 0 and type = 21").Iterate(new(Comment), func(idx int, bean interface{}) error {
-		comment := bean.(*Comment)
-
-		review := &Review{
-			Type:             ReviewTypeComment,
-			ReviewerID:       comment.PosterID,
-			IssueID:          comment.IssueID,
-			Official:         false,
-			CommitID:         comment.CommitSHA,
-			Stale:            comment.Invalidated,
-			OriginalAuthor:   comment.OriginalAuthor,
-			OriginalAuthorID: comment.OriginalAuthorID,
-			CreatedUnix:      comment.CreatedUnix,
-			UpdatedUnix:      comment.CreatedUnix,
-		}
-		if _, err := sess.NoAutoTime().Insert(review); err != nil {
+
+	var updateComment = func(comments []*Comment) error {
+		sess := x.NewSession()
+		defer sess.Close()
+		if err := sess.Begin(); err != nil {
 			return err
 		}
 
-		reviewComment := &Comment{
-			Type:             22,
-			PosterID:         comment.PosterID,
-			Content:          "",
-			IssueID:          comment.IssueID,
-			ReviewID:         review.ID,
-			OriginalAuthor:   comment.OriginalAuthor,
-			OriginalAuthorID: comment.OriginalAuthorID,
-			CreatedUnix:      comment.CreatedUnix,
-			UpdatedUnix:      comment.CreatedUnix,
+		for _, comment := range comments {
+			review := &Review{
+				Type:             ReviewTypeComment,
+				ReviewerID:       comment.PosterID,
+				IssueID:          comment.IssueID,
+				Official:         false,
+				CommitID:         comment.CommitSHA,
+				Stale:            comment.Invalidated,
+				OriginalAuthor:   comment.OriginalAuthor,
+				OriginalAuthorID: comment.OriginalAuthorID,
+				CreatedUnix:      comment.CreatedUnix,
+				UpdatedUnix:      comment.CreatedUnix,
+			}
+			if _, err := sess.NoAutoTime().Insert(review); err != nil {
+				return err
+			}
+
+			reviewComment := &Comment{
+				Type:             22,
+				PosterID:         comment.PosterID,
+				Content:          "",
+				IssueID:          comment.IssueID,
+				ReviewID:         review.ID,
+				OriginalAuthor:   comment.OriginalAuthor,
+				OriginalAuthorID: comment.OriginalAuthorID,
+				CreatedUnix:      comment.CreatedUnix,
+				UpdatedUnix:      comment.CreatedUnix,
+			}
+			if _, err := sess.NoAutoTime().Insert(reviewComment); err != nil {
+				return err
+			}
+
+			comment.ReviewID = review.ID
+			if _, err := sess.ID(comment.ID).Cols("review_id").NoAutoTime().Update(comment); err != nil {
+				return err
+			}
+		}
+
+		return sess.Commit()
+	}
+
+	var start = 0
+	var batchSize = 100
+	for {
+		var comments = make([]*Comment, 0, batchSize)
+		if err := x.Where("review_id = 0 and type = 21").Limit(batchSize, start).Find(&comments); err != nil {
+			return err
 		}
-		if _, err := sess.NoAutoTime().Insert(reviewComment); err != nil {
+
+		if err := updateComment(comments); err != nil {
 			return err
 		}
 
-		comment.ReviewID = review.ID
-		_, err := sess.ID(comment.ID).Cols("review_id").NoAutoTime().Update(comment)
-		return err
-	}); err != nil {
-		return err
+		start += len(comments)
+
+		if len(comments) < batchSize {
+			break
+		}
 	}
 
-	return sess.Commit()
+	return nil
 }