diff options
author | Lauris BH <lauris@nix.lv> | 2017-09-20 08:26:49 +0300 |
---|---|---|
committer | Lunny Xiao <xiaolunwen@gmail.com> | 2017-09-20 13:26:49 +0800 |
commit | 7a0297819d3aececb8b633de5a2995c40b7bfcae (patch) | |
tree | 7aed967ad21f95df2b16359ec1551662d653a1fd /models/release.go | |
parent | 8b6236d67b21f2a3291207ef77d103a3ce7476ba (diff) | |
download | gitea-7a0297819d3aececb8b633de5a2995c40b7bfcae.tar.gz gitea-7a0297819d3aececb8b633de5a2995c40b7bfcae.zip |
Sync releases table with tags on push and for mirrors (#2459)
* Sync releases table with tags on push and for mirrors
* Code style fixes
* Fix api to return only releases
* Optimize release creation and update
Minimize posibility of race conditions
* Fix release lower tag name updating
* handle tag reference update by addionally comparing commit id
Diffstat (limited to 'models/release.go')
-rw-r--r-- | models/release.go | 89 |
1 files changed, 75 insertions, 14 deletions
diff --git a/models/release.go b/models/release.go index f12fc06840..42054131a3 100644 --- a/models/release.go +++ b/models/release.go @@ -34,7 +34,8 @@ type Release struct { NumCommitsBehind int64 `xorm:"-"` Note string `xorm:"TEXT"` IsDraft bool `xorm:"NOT NULL DEFAULT false"` - IsPrerelease bool + IsPrerelease bool `xorm:"NOT NULL DEFAULT false"` + IsTag bool `xorm:"NOT NULL DEFAULT false"` Attachments []*Attachment `xorm:"-"` @@ -139,17 +140,18 @@ func createTag(gitRepo *git.Repository, rel *Release) error { } return err } - } else { - commit, err := gitRepo.GetTagCommit(rel.TagName) - if err != nil { - return fmt.Errorf("GetTagCommit: %v", err) - } + rel.LowerTagName = strings.ToLower(rel.TagName) + } + commit, err := gitRepo.GetTagCommit(rel.TagName) + if err != nil { + return fmt.Errorf("GetTagCommit: %v", err) + } - rel.Sha1 = commit.ID.String() - rel.NumCommits, err = commit.CommitsCount() - if err != nil { - return fmt.Errorf("CommitsCount: %v", err) - } + rel.Sha1 = commit.ID.String() + rel.CreatedUnix = commit.Author.When.Unix() + rel.NumCommits, err = commit.CommitsCount() + if err != nil { + return fmt.Errorf("CommitsCount: %v", err) } } return nil @@ -236,6 +238,7 @@ func GetReleaseByID(id int64) (*Release, error) { // FindReleasesOptions describes the conditions to Find releases type FindReleasesOptions struct { IncludeDrafts bool + IncludeTags bool TagNames []string } @@ -246,6 +249,9 @@ func (opts *FindReleasesOptions) toConds(repoID int64) builder.Cond { if !opts.IncludeDrafts { cond = cond.And(builder.Eq{"is_draft": false}) } + if !opts.IncludeTags { + cond = cond.And(builder.Eq{"is_tag": false}) + } if len(opts.TagNames) > 0 { cond = cond.And(builder.In("tag_name", opts.TagNames)) } @@ -361,6 +367,8 @@ func UpdateRelease(gitRepo *git.Repository, rel *Release, attachmentUUIDs []stri if err = createTag(gitRepo, rel); err != nil { return err } + rel.LowerTagName = strings.ToLower(rel.TagName) + _, err = x.Id(rel.ID).AllCols().Update(rel) if err != nil { return err @@ -397,11 +405,64 @@ func DeleteReleaseByID(id int64, u *User, delTag bool) error { if err != nil && !strings.Contains(stderr, "not found") { return fmt.Errorf("git tag -d: %v - %s", err, stderr) } - } - if _, err = x.Id(rel.ID).Delete(new(Release)); err != nil { - return fmt.Errorf("Delete: %v", err) + if _, err = x.Id(rel.ID).Delete(new(Release)); err != nil { + return fmt.Errorf("Delete: %v", err) + } + } else { + rel.IsTag = true + rel.IsDraft = false + rel.IsPrerelease = false + rel.Title = "" + rel.Note = "" + + if _, err = x.Id(rel.ID).AllCols().Update(rel); err != nil { + return fmt.Errorf("Update: %v", err) + } } return nil } + +// SyncReleasesWithTags synchronizes release table with repository tags +func SyncReleasesWithTags(repo *Repository, gitRepo *git.Repository) error { + existingRelTags := make(map[string]struct{}) + opts := FindReleasesOptions{IncludeDrafts: true, IncludeTags: true} + for page := 1; ; page++ { + rels, err := GetReleasesByRepoID(repo.ID, opts, page, 100) + if err != nil { + return fmt.Errorf("GetReleasesByRepoID: %v", err) + } + if len(rels) == 0 { + break + } + for _, rel := range rels { + if rel.IsDraft { + continue + } + commitID, err := gitRepo.GetTagCommitID(rel.TagName) + if err != nil { + return fmt.Errorf("GetTagCommitID: %v", err) + } + if !gitRepo.IsTagExist(rel.TagName) || commitID != rel.Sha1 { + if err := pushUpdateDeleteTag(repo, gitRepo, rel.TagName); err != nil { + return fmt.Errorf("pushUpdateDeleteTag: %v", err) + } + } else { + existingRelTags[strings.ToLower(rel.TagName)] = struct{}{} + } + } + } + tags, err := gitRepo.GetTags() + if err != nil { + return fmt.Errorf("GetTags: %v", err) + } + for _, tagName := range tags { + if _, ok := existingRelTags[strings.ToLower(tagName)]; !ok { + if err := pushUpdateAddTag(repo, gitRepo, tagName); err != nil { + return fmt.Errorf("pushUpdateAddTag: %v", err) + } + } + } + return nil +} |