mirror of
				https://gitee.com/gitea/gitea
				synced 2025-11-04 16:40:24 +08:00 
			
		
		
		
	Move some functions into services/repository (#17677)
This commit is contained in:
		@@ -25,6 +25,7 @@ import (
 | 
				
			|||||||
	"code.gitea.io/gitea/modules/storage"
 | 
						"code.gitea.io/gitea/modules/storage"
 | 
				
			||||||
	auth_service "code.gitea.io/gitea/services/auth"
 | 
						auth_service "code.gitea.io/gitea/services/auth"
 | 
				
			||||||
	"code.gitea.io/gitea/services/auth/source/oauth2"
 | 
						"code.gitea.io/gitea/services/auth/source/oauth2"
 | 
				
			||||||
 | 
						repo_service "code.gitea.io/gitea/services/repository"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"github.com/urfave/cli"
 | 
						"github.com/urfave/cli"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
@@ -612,7 +613,7 @@ func runRegenerateHooks(_ *cli.Context) error {
 | 
				
			|||||||
	if err := initDB(ctx); err != nil {
 | 
						if err := initDB(ctx); err != nil {
 | 
				
			||||||
		return err
 | 
							return err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	return repo_module.SyncRepositoryHooks(graceful.GetManager().ShutdownContext())
 | 
						return repo_service.SyncRepositoryHooks(graceful.GetManager().ShutdownContext())
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func runRegenerateKeys(_ *cli.Context) error {
 | 
					func runRegenerateKeys(_ *cli.Context) error {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -13,9 +13,9 @@ import (
 | 
				
			|||||||
	"code.gitea.io/gitea/models"
 | 
						"code.gitea.io/gitea/models"
 | 
				
			||||||
	"code.gitea.io/gitea/models/unittest"
 | 
						"code.gitea.io/gitea/models/unittest"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/git"
 | 
						"code.gitea.io/gitea/modules/git"
 | 
				
			||||||
	repo_module "code.gitea.io/gitea/modules/repository"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/setting"
 | 
						"code.gitea.io/gitea/modules/setting"
 | 
				
			||||||
	api "code.gitea.io/gitea/modules/structs"
 | 
						api "code.gitea.io/gitea/modules/structs"
 | 
				
			||||||
 | 
						repo_service "code.gitea.io/gitea/services/repository"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"github.com/stretchr/testify/assert"
 | 
						"github.com/stretchr/testify/assert"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
@@ -72,7 +72,7 @@ func testAPIGetContentsList(t *testing.T, u *url.URL) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	// Make a new branch in repo1
 | 
						// Make a new branch in repo1
 | 
				
			||||||
	newBranch := "test_branch"
 | 
						newBranch := "test_branch"
 | 
				
			||||||
	err := repo_module.CreateNewBranch(user2, repo1, repo1.DefaultBranch, newBranch)
 | 
						err := repo_service.CreateNewBranch(user2, repo1, repo1.DefaultBranch, newBranch)
 | 
				
			||||||
	assert.NoError(t, err)
 | 
						assert.NoError(t, err)
 | 
				
			||||||
	// Get the commit ID of the default branch
 | 
						// Get the commit ID of the default branch
 | 
				
			||||||
	gitRepo, err := git.OpenRepository(repo1.RepoPath())
 | 
						gitRepo, err := git.OpenRepository(repo1.RepoPath())
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -12,9 +12,9 @@ import (
 | 
				
			|||||||
	"code.gitea.io/gitea/models"
 | 
						"code.gitea.io/gitea/models"
 | 
				
			||||||
	"code.gitea.io/gitea/models/unittest"
 | 
						"code.gitea.io/gitea/models/unittest"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/git"
 | 
						"code.gitea.io/gitea/modules/git"
 | 
				
			||||||
	repo_module "code.gitea.io/gitea/modules/repository"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/setting"
 | 
						"code.gitea.io/gitea/modules/setting"
 | 
				
			||||||
	api "code.gitea.io/gitea/modules/structs"
 | 
						api "code.gitea.io/gitea/modules/structs"
 | 
				
			||||||
 | 
						repo_service "code.gitea.io/gitea/services/repository"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"github.com/stretchr/testify/assert"
 | 
						"github.com/stretchr/testify/assert"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
@@ -73,7 +73,7 @@ func testAPIGetContents(t *testing.T, u *url.URL) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	// Make a new branch in repo1
 | 
						// Make a new branch in repo1
 | 
				
			||||||
	newBranch := "test_branch"
 | 
						newBranch := "test_branch"
 | 
				
			||||||
	err := repo_module.CreateNewBranch(user2, repo1, repo1.DefaultBranch, newBranch)
 | 
						err := repo_service.CreateNewBranch(user2, repo1, repo1.DefaultBranch, newBranch)
 | 
				
			||||||
	assert.NoError(t, err)
 | 
						assert.NoError(t, err)
 | 
				
			||||||
	// Get the commit ID of the default branch
 | 
						// Get the commit ID of the default branch
 | 
				
			||||||
	gitRepo, err := git.OpenRepository(repo1.RepoPath())
 | 
						gitRepo, err := git.OpenRepository(repo1.RepoPath())
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -24,92 +24,3 @@ func GetBranch(repo *models.Repository, branch string) (*git.Branch, error) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	return gitRepo.GetBranch(branch)
 | 
						return gitRepo.GetBranch(branch)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					 | 
				
			||||||
// GetBranches returns branches from the repository, skipping skip initial branches and
 | 
					 | 
				
			||||||
// returning at most limit branches, or all branches if limit is 0.
 | 
					 | 
				
			||||||
func GetBranches(repo *models.Repository, skip, limit int) ([]*git.Branch, int, error) {
 | 
					 | 
				
			||||||
	return git.GetBranchesByPath(repo.RepoPath(), skip, limit)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// checkBranchName validates branch name with existing repository branches
 | 
					 | 
				
			||||||
func checkBranchName(repo *models.Repository, name string) error {
 | 
					 | 
				
			||||||
	gitRepo, err := git.OpenRepository(repo.RepoPath())
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	defer gitRepo.Close()
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	branches, _, err := GetBranches(repo, 0, 0)
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	for _, branch := range branches {
 | 
					 | 
				
			||||||
		if branch.Name == name {
 | 
					 | 
				
			||||||
			return models.ErrBranchAlreadyExists{
 | 
					 | 
				
			||||||
				BranchName: branch.Name,
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
		} else if (len(branch.Name) < len(name) && branch.Name+"/" == name[0:len(branch.Name)+1]) ||
 | 
					 | 
				
			||||||
			(len(branch.Name) > len(name) && name+"/" == branch.Name[0:len(name)+1]) {
 | 
					 | 
				
			||||||
			return models.ErrBranchNameConflict{
 | 
					 | 
				
			||||||
				BranchName: branch.Name,
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if _, err := gitRepo.GetTag(name); err == nil {
 | 
					 | 
				
			||||||
		return models.ErrTagAlreadyExists{
 | 
					 | 
				
			||||||
			TagName: name,
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// CreateNewBranch creates a new repository branch
 | 
					 | 
				
			||||||
func CreateNewBranch(doer *models.User, repo *models.Repository, oldBranchName, branchName string) (err error) {
 | 
					 | 
				
			||||||
	// Check if branch name can be used
 | 
					 | 
				
			||||||
	if err := checkBranchName(repo, branchName); err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if !git.IsBranchExist(repo.RepoPath(), oldBranchName) {
 | 
					 | 
				
			||||||
		return models.ErrBranchDoesNotExist{
 | 
					 | 
				
			||||||
			BranchName: oldBranchName,
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if err := git.Push(repo.RepoPath(), git.PushOptions{
 | 
					 | 
				
			||||||
		Remote: repo.RepoPath(),
 | 
					 | 
				
			||||||
		Branch: fmt.Sprintf("%s:%s%s", oldBranchName, git.BranchPrefix, branchName),
 | 
					 | 
				
			||||||
		Env:    models.PushingEnvironment(doer, repo),
 | 
					 | 
				
			||||||
	}); err != nil {
 | 
					 | 
				
			||||||
		if git.IsErrPushOutOfDate(err) || git.IsErrPushRejected(err) {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		return fmt.Errorf("Push: %v", err)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// CreateNewBranchFromCommit creates a new repository branch
 | 
					 | 
				
			||||||
func CreateNewBranchFromCommit(doer *models.User, repo *models.Repository, commit, branchName string) (err error) {
 | 
					 | 
				
			||||||
	// Check if branch name can be used
 | 
					 | 
				
			||||||
	if err := checkBranchName(repo, branchName); err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if err := git.Push(repo.RepoPath(), git.PushOptions{
 | 
					 | 
				
			||||||
		Remote: repo.RepoPath(),
 | 
					 | 
				
			||||||
		Branch: fmt.Sprintf("%s:%s%s", commit, git.BranchPrefix, branchName),
 | 
					 | 
				
			||||||
		Env:    models.PushingEnvironment(doer, repo),
 | 
					 | 
				
			||||||
	}); err != nil {
 | 
					 | 
				
			||||||
		if git.IsErrPushOutOfDate(err) || git.IsErrPushRejected(err) {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		return fmt.Errorf("Push: %v", err)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 
 | 
				
			|||||||
@@ -5,19 +5,13 @@
 | 
				
			|||||||
package repository
 | 
					package repository
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
	"context"
 | 
					 | 
				
			||||||
	"fmt"
 | 
						"fmt"
 | 
				
			||||||
	"os"
 | 
						"os"
 | 
				
			||||||
	"path/filepath"
 | 
						"path/filepath"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"code.gitea.io/gitea/models"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/models/db"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/git"
 | 
						"code.gitea.io/gitea/modules/git"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/log"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/setting"
 | 
						"code.gitea.io/gitea/modules/setting"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/util"
 | 
						"code.gitea.io/gitea/modules/util"
 | 
				
			||||||
 | 
					 | 
				
			||||||
	"xorm.io/builder"
 | 
					 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func getHookTemplates() (hookNames, hookTpls, giteaHookTpls []string) {
 | 
					func getHookTemplates() (hookNames, hookTpls, giteaHookTpls []string) {
 | 
				
			||||||
@@ -240,38 +234,3 @@ func CheckDelegateHooks(repoPath string) ([]string, error) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
	return results, nil
 | 
						return results, nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					 | 
				
			||||||
// SyncRepositoryHooks rewrites all repositories' pre-receive, update and post-receive hooks
 | 
					 | 
				
			||||||
// to make sure the binary and custom conf path are up-to-date.
 | 
					 | 
				
			||||||
func SyncRepositoryHooks(ctx context.Context) error {
 | 
					 | 
				
			||||||
	log.Trace("Doing: SyncRepositoryHooks")
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if err := db.Iterate(
 | 
					 | 
				
			||||||
		db.DefaultContext,
 | 
					 | 
				
			||||||
		new(models.Repository),
 | 
					 | 
				
			||||||
		builder.Gt{"id": 0},
 | 
					 | 
				
			||||||
		func(idx int, bean interface{}) error {
 | 
					 | 
				
			||||||
			repo := bean.(*models.Repository)
 | 
					 | 
				
			||||||
			select {
 | 
					 | 
				
			||||||
			case <-ctx.Done():
 | 
					 | 
				
			||||||
				return db.ErrCancelledf("before sync repository hooks for %s", repo.FullName())
 | 
					 | 
				
			||||||
			default:
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
			if err := createDelegateHooks(repo.RepoPath()); err != nil {
 | 
					 | 
				
			||||||
				return fmt.Errorf("SyncRepositoryHook: %v", err)
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
			if repo.HasWiki() {
 | 
					 | 
				
			||||||
				if err := createDelegateHooks(repo.WikiPath()); err != nil {
 | 
					 | 
				
			||||||
					return fmt.Errorf("SyncRepositoryHook: %v", err)
 | 
					 | 
				
			||||||
				}
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
			return nil
 | 
					 | 
				
			||||||
		},
 | 
					 | 
				
			||||||
	); err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	log.Trace("Finished: SyncRepositoryHooks")
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,136 +0,0 @@
 | 
				
			|||||||
// Copyright 2020 The Gitea Authors. All rights reserved.
 | 
					 | 
				
			||||||
// Use of this source code is governed by a MIT-style
 | 
					 | 
				
			||||||
// license that can be found in the LICENSE file.
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
package repository
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
import (
 | 
					 | 
				
			||||||
	"context"
 | 
					 | 
				
			||||||
	"fmt"
 | 
					 | 
				
			||||||
	"strings"
 | 
					 | 
				
			||||||
	"time"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/models"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/models/db"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/git"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/timeutil"
 | 
					 | 
				
			||||||
)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// PushUpdateAddDeleteTags updates a number of added and delete tags
 | 
					 | 
				
			||||||
func PushUpdateAddDeleteTags(repo *models.Repository, gitRepo *git.Repository, addTags, delTags []string) error {
 | 
					 | 
				
			||||||
	return db.WithTx(func(ctx context.Context) error {
 | 
					 | 
				
			||||||
		if err := models.PushUpdateDeleteTagsContext(ctx, repo, delTags); err != nil {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		return pushUpdateAddTags(ctx, repo, gitRepo, addTags)
 | 
					 | 
				
			||||||
	})
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// pushUpdateAddTags updates a number of add tags
 | 
					 | 
				
			||||||
func pushUpdateAddTags(ctx context.Context, repo *models.Repository, gitRepo *git.Repository, tags []string) error {
 | 
					 | 
				
			||||||
	if len(tags) == 0 {
 | 
					 | 
				
			||||||
		return nil
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	lowerTags := make([]string, 0, len(tags))
 | 
					 | 
				
			||||||
	for _, tag := range tags {
 | 
					 | 
				
			||||||
		lowerTags = append(lowerTags, strings.ToLower(tag))
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	releases, err := models.GetReleasesByRepoIDAndNames(ctx, repo.ID, lowerTags)
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return fmt.Errorf("GetReleasesByRepoIDAndNames: %v", err)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	relMap := make(map[string]*models.Release)
 | 
					 | 
				
			||||||
	for _, rel := range releases {
 | 
					 | 
				
			||||||
		relMap[rel.LowerTagName] = rel
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	newReleases := make([]*models.Release, 0, len(lowerTags)-len(relMap))
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	emailToUser := make(map[string]*models.User)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	for i, lowerTag := range lowerTags {
 | 
					 | 
				
			||||||
		tag, err := gitRepo.GetTag(tags[i])
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return fmt.Errorf("GetTag: %v", err)
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		commit, err := tag.Commit()
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return fmt.Errorf("Commit: %v", err)
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		sig := tag.Tagger
 | 
					 | 
				
			||||||
		if sig == nil {
 | 
					 | 
				
			||||||
			sig = commit.Author
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		if sig == nil {
 | 
					 | 
				
			||||||
			sig = commit.Committer
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		var author *models.User
 | 
					 | 
				
			||||||
		var createdAt = time.Unix(1, 0)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		if sig != nil {
 | 
					 | 
				
			||||||
			var ok bool
 | 
					 | 
				
			||||||
			author, ok = emailToUser[sig.Email]
 | 
					 | 
				
			||||||
			if !ok {
 | 
					 | 
				
			||||||
				author, err = models.GetUserByEmailContext(ctx, sig.Email)
 | 
					 | 
				
			||||||
				if err != nil && !models.IsErrUserNotExist(err) {
 | 
					 | 
				
			||||||
					return fmt.Errorf("GetUserByEmail: %v", err)
 | 
					 | 
				
			||||||
				}
 | 
					 | 
				
			||||||
				if author != nil {
 | 
					 | 
				
			||||||
					emailToUser[sig.Email] = author
 | 
					 | 
				
			||||||
				}
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
			createdAt = sig.When
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		commitsCount, err := commit.CommitsCount()
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return fmt.Errorf("CommitsCount: %v", err)
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		rel, has := relMap[lowerTag]
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		if !has {
 | 
					 | 
				
			||||||
			rel = &models.Release{
 | 
					 | 
				
			||||||
				RepoID:       repo.ID,
 | 
					 | 
				
			||||||
				Title:        "",
 | 
					 | 
				
			||||||
				TagName:      tags[i],
 | 
					 | 
				
			||||||
				LowerTagName: lowerTag,
 | 
					 | 
				
			||||||
				Target:       "",
 | 
					 | 
				
			||||||
				Sha1:         commit.ID.String(),
 | 
					 | 
				
			||||||
				NumCommits:   commitsCount,
 | 
					 | 
				
			||||||
				Note:         "",
 | 
					 | 
				
			||||||
				IsDraft:      false,
 | 
					 | 
				
			||||||
				IsPrerelease: false,
 | 
					 | 
				
			||||||
				IsTag:        true,
 | 
					 | 
				
			||||||
				CreatedUnix:  timeutil.TimeStamp(createdAt.Unix()),
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
			if author != nil {
 | 
					 | 
				
			||||||
				rel.PublisherID = author.ID
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
			newReleases = append(newReleases, rel)
 | 
					 | 
				
			||||||
		} else {
 | 
					 | 
				
			||||||
			rel.Sha1 = commit.ID.String()
 | 
					 | 
				
			||||||
			rel.CreatedUnix = timeutil.TimeStamp(createdAt.Unix())
 | 
					 | 
				
			||||||
			rel.NumCommits = commitsCount
 | 
					 | 
				
			||||||
			rel.IsDraft = false
 | 
					 | 
				
			||||||
			if rel.IsTag && author != nil {
 | 
					 | 
				
			||||||
				rel.PublisherID = author.ID
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
			if err = models.UpdateRelease(ctx, rel); err != nil {
 | 
					 | 
				
			||||||
				return fmt.Errorf("Update: %v", err)
 | 
					 | 
				
			||||||
			}
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	if len(newReleases) > 0 {
 | 
					 | 
				
			||||||
		if err = models.InsertReleasesContext(ctx, newReleases); err != nil {
 | 
					 | 
				
			||||||
			return fmt.Errorf("Insert: %v", err)
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
@@ -176,7 +176,7 @@ func CreateBranch(ctx *context.APIContext) {
 | 
				
			|||||||
		opt.OldBranchName = ctx.Repo.Repository.DefaultBranch
 | 
							opt.OldBranchName = ctx.Repo.Repository.DefaultBranch
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	err := repo_module.CreateNewBranch(ctx.User, ctx.Repo.Repository, opt.OldBranchName, opt.BranchName)
 | 
						err := repo_service.CreateNewBranch(ctx.User, ctx.Repo.Repository, opt.OldBranchName, opt.BranchName)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		if models.IsErrBranchDoesNotExist(err) {
 | 
							if models.IsErrBranchDoesNotExist(err) {
 | 
				
			||||||
@@ -257,7 +257,7 @@ func ListBranches(ctx *context.APIContext) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	listOptions := utils.GetListOptions(ctx)
 | 
						listOptions := utils.GetListOptions(ctx)
 | 
				
			||||||
	skip, _ := listOptions.GetStartEnd()
 | 
						skip, _ := listOptions.GetStartEnd()
 | 
				
			||||||
	branches, totalNumOfBranches, err := repo_module.GetBranches(ctx.Repo.Repository, skip, listOptions.PageSize)
 | 
						branches, totalNumOfBranches, err := repo_service.GetBranches(ctx.Repo.Repository, skip, listOptions.PageSize)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		ctx.Error(http.StatusInternalServerError, "GetBranches", err)
 | 
							ctx.Error(http.StatusInternalServerError, "GetBranches", err)
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -25,7 +25,6 @@ import (
 | 
				
			|||||||
	"code.gitea.io/gitea/modules/markup"
 | 
						"code.gitea.io/gitea/modules/markup"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/markup/external"
 | 
						"code.gitea.io/gitea/modules/markup/external"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/notification"
 | 
						"code.gitea.io/gitea/modules/notification"
 | 
				
			||||||
	repo_module "code.gitea.io/gitea/modules/repository"
 | 
					 | 
				
			||||||
	"code.gitea.io/gitea/modules/setting"
 | 
						"code.gitea.io/gitea/modules/setting"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/ssh"
 | 
						"code.gitea.io/gitea/modules/ssh"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/storage"
 | 
						"code.gitea.io/gitea/modules/storage"
 | 
				
			||||||
@@ -45,7 +44,7 @@ import (
 | 
				
			|||||||
	repo_migrations "code.gitea.io/gitea/services/migrations"
 | 
						repo_migrations "code.gitea.io/gitea/services/migrations"
 | 
				
			||||||
	mirror_service "code.gitea.io/gitea/services/mirror"
 | 
						mirror_service "code.gitea.io/gitea/services/mirror"
 | 
				
			||||||
	pull_service "code.gitea.io/gitea/services/pull"
 | 
						pull_service "code.gitea.io/gitea/services/pull"
 | 
				
			||||||
	"code.gitea.io/gitea/services/repository"
 | 
						repo_service "code.gitea.io/gitea/services/repository"
 | 
				
			||||||
	"code.gitea.io/gitea/services/webhook"
 | 
						"code.gitea.io/gitea/services/webhook"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"gitea.com/go-chi/session"
 | 
						"gitea.com/go-chi/session"
 | 
				
			||||||
@@ -73,7 +72,7 @@ func mustInitCtx(ctx context.Context, fn func(ctx context.Context) error) {
 | 
				
			|||||||
func InitGitServices() {
 | 
					func InitGitServices() {
 | 
				
			||||||
	setting.NewServices()
 | 
						setting.NewServices()
 | 
				
			||||||
	mustInit(storage.Init)
 | 
						mustInit(storage.Init)
 | 
				
			||||||
	mustInit(repository.NewContext)
 | 
						mustInit(repo_service.NewContext)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func syncAppPathForGit(ctx context.Context) error {
 | 
					func syncAppPathForGit(ctx context.Context) error {
 | 
				
			||||||
@@ -85,7 +84,7 @@ func syncAppPathForGit(ctx context.Context) error {
 | 
				
			|||||||
		log.Info("AppPath changed from '%s' to '%s'", runtimeState.LastAppPath, setting.AppPath)
 | 
							log.Info("AppPath changed from '%s' to '%s'", runtimeState.LastAppPath, setting.AppPath)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		log.Info("re-sync repository hooks ...")
 | 
							log.Info("re-sync repository hooks ...")
 | 
				
			||||||
		mustInitCtx(ctx, repo_module.SyncRepositoryHooks)
 | 
							mustInitCtx(ctx, repo_service.SyncRepositoryHooks)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		log.Info("re-write ssh public keys ...")
 | 
							log.Info("re-write ssh public keys ...")
 | 
				
			||||||
		mustInit(models.RewriteAllPublicKeys)
 | 
							mustInit(models.RewriteAllPublicKeys)
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -171,7 +171,7 @@ func loadBranches(ctx *context.Context, skip, limit int) ([]*Branch, int) {
 | 
				
			|||||||
		return nil, 0
 | 
							return nil, 0
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	rawBranches, totalNumOfBranches, err := repo_module.GetBranches(ctx.Repo.Repository, skip, limit)
 | 
						rawBranches, totalNumOfBranches, err := repo_service.GetBranches(ctx.Repo.Repository, skip, limit)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		log.Error("GetBranches: %v", err)
 | 
							log.Error("GetBranches: %v", err)
 | 
				
			||||||
		ctx.ServerError("GetBranches", err)
 | 
							ctx.ServerError("GetBranches", err)
 | 
				
			||||||
@@ -350,11 +350,11 @@ func CreateBranch(ctx *context.Context) {
 | 
				
			|||||||
			err = release_service.CreateNewTag(ctx.User, ctx.Repo.Repository, ctx.Repo.BranchName, form.NewBranchName, "")
 | 
								err = release_service.CreateNewTag(ctx.User, ctx.Repo.Repository, ctx.Repo.BranchName, form.NewBranchName, "")
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	} else if ctx.Repo.IsViewBranch {
 | 
						} else if ctx.Repo.IsViewBranch {
 | 
				
			||||||
		err = repo_module.CreateNewBranch(ctx.User, ctx.Repo.Repository, ctx.Repo.BranchName, form.NewBranchName)
 | 
							err = repo_service.CreateNewBranch(ctx.User, ctx.Repo.Repository, ctx.Repo.BranchName, form.NewBranchName)
 | 
				
			||||||
	} else if ctx.Repo.IsViewTag {
 | 
						} else if ctx.Repo.IsViewTag {
 | 
				
			||||||
		err = repo_module.CreateNewBranchFromCommit(ctx.User, ctx.Repo.Repository, ctx.Repo.CommitID, form.NewBranchName)
 | 
							err = repo_service.CreateNewBranchFromCommit(ctx.User, ctx.Repo.Repository, ctx.Repo.CommitID, form.NewBranchName)
 | 
				
			||||||
	} else {
 | 
						} else {
 | 
				
			||||||
		err = repo_module.CreateNewBranchFromCommit(ctx.User, ctx.Repo.Repository, ctx.Repo.BranchName, form.NewBranchName)
 | 
							err = repo_service.CreateNewBranchFromCommit(ctx.User, ctx.Repo.Repository, ctx.Repo.BranchName, form.NewBranchName)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		if models.IsErrTagAlreadyExists(err) {
 | 
							if models.IsErrTagAlreadyExists(err) {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -85,7 +85,7 @@ func registerRepositoryUpdateHook() {
 | 
				
			|||||||
		RunAtStart: false,
 | 
							RunAtStart: false,
 | 
				
			||||||
		Schedule:   "@every 72h",
 | 
							Schedule:   "@every 72h",
 | 
				
			||||||
	}, func(ctx context.Context, _ *models.User, _ Config) error {
 | 
						}, func(ctx context.Context, _ *models.User, _ Config) error {
 | 
				
			||||||
		return repo_module.SyncRepositoryHooks(ctx)
 | 
							return repo_service.SyncRepositoryHooks(ctx)
 | 
				
			||||||
	})
 | 
						})
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -333,7 +333,7 @@ func runSync(ctx context.Context, m *models.Mirror) ([]*mirrorSyncResult, bool)
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("SyncMirrors [repo: %-v]: invalidating mirror branch caches...", m.Repo)
 | 
						log.Trace("SyncMirrors [repo: %-v]: invalidating mirror branch caches...", m.Repo)
 | 
				
			||||||
	branches, _, err := repo_module.GetBranches(m.Repo, 0, 0)
 | 
						branches, _, err := git.GetBranchesByPath(m.Repo.RepoPath(), 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		log.Error("GetBranches: %v", err)
 | 
							log.Error("GetBranches: %v", err)
 | 
				
			||||||
		return nil, false
 | 
							return nil, false
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -6,6 +6,7 @@ package repository
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
	"errors"
 | 
						"errors"
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"code.gitea.io/gitea/models"
 | 
						"code.gitea.io/gitea/models"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/git"
 | 
						"code.gitea.io/gitea/modules/git"
 | 
				
			||||||
@@ -15,6 +16,95 @@ import (
 | 
				
			|||||||
	pull_service "code.gitea.io/gitea/services/pull"
 | 
						pull_service "code.gitea.io/gitea/services/pull"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// CreateNewBranch creates a new repository branch
 | 
				
			||||||
 | 
					func CreateNewBranch(doer *models.User, repo *models.Repository, oldBranchName, branchName string) (err error) {
 | 
				
			||||||
 | 
						// Check if branch name can be used
 | 
				
			||||||
 | 
						if err := checkBranchName(repo, branchName); err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if !git.IsBranchExist(repo.RepoPath(), oldBranchName) {
 | 
				
			||||||
 | 
							return models.ErrBranchDoesNotExist{
 | 
				
			||||||
 | 
								BranchName: oldBranchName,
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if err := git.Push(repo.RepoPath(), git.PushOptions{
 | 
				
			||||||
 | 
							Remote: repo.RepoPath(),
 | 
				
			||||||
 | 
							Branch: fmt.Sprintf("%s:%s%s", oldBranchName, git.BranchPrefix, branchName),
 | 
				
			||||||
 | 
							Env:    models.PushingEnvironment(doer, repo),
 | 
				
			||||||
 | 
						}); err != nil {
 | 
				
			||||||
 | 
							if git.IsErrPushOutOfDate(err) || git.IsErrPushRejected(err) {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return fmt.Errorf("Push: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// GetBranches returns branches from the repository, skipping skip initial branches and
 | 
				
			||||||
 | 
					// returning at most limit branches, or all branches if limit is 0.
 | 
				
			||||||
 | 
					func GetBranches(repo *models.Repository, skip, limit int) ([]*git.Branch, int, error) {
 | 
				
			||||||
 | 
						return git.GetBranchesByPath(repo.RepoPath(), skip, limit)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// checkBranchName validates branch name with existing repository branches
 | 
				
			||||||
 | 
					func checkBranchName(repo *models.Repository, name string) error {
 | 
				
			||||||
 | 
						gitRepo, err := git.OpenRepository(repo.RepoPath())
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						defer gitRepo.Close()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						branches, _, err := GetBranches(repo, 0, 0)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for _, branch := range branches {
 | 
				
			||||||
 | 
							if branch.Name == name {
 | 
				
			||||||
 | 
								return models.ErrBranchAlreadyExists{
 | 
				
			||||||
 | 
									BranchName: branch.Name,
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
							} else if (len(branch.Name) < len(name) && branch.Name+"/" == name[0:len(branch.Name)+1]) ||
 | 
				
			||||||
 | 
								(len(branch.Name) > len(name) && name+"/" == branch.Name[0:len(name)+1]) {
 | 
				
			||||||
 | 
								return models.ErrBranchNameConflict{
 | 
				
			||||||
 | 
									BranchName: branch.Name,
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if _, err := gitRepo.GetTag(name); err == nil {
 | 
				
			||||||
 | 
							return models.ErrTagAlreadyExists{
 | 
				
			||||||
 | 
								TagName: name,
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// CreateNewBranchFromCommit creates a new repository branch
 | 
				
			||||||
 | 
					func CreateNewBranchFromCommit(doer *models.User, repo *models.Repository, commit, branchName string) (err error) {
 | 
				
			||||||
 | 
						// Check if branch name can be used
 | 
				
			||||||
 | 
						if err := checkBranchName(repo, branchName); err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if err := git.Push(repo.RepoPath(), git.PushOptions{
 | 
				
			||||||
 | 
							Remote: repo.RepoPath(),
 | 
				
			||||||
 | 
							Branch: fmt.Sprintf("%s:%s%s", commit, git.BranchPrefix, branchName),
 | 
				
			||||||
 | 
							Env:    models.PushingEnvironment(doer, repo),
 | 
				
			||||||
 | 
						}); err != nil {
 | 
				
			||||||
 | 
							if git.IsErrPushOutOfDate(err) || git.IsErrPushRejected(err) {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return fmt.Errorf("Push: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// RenameBranch rename a branch
 | 
					// RenameBranch rename a branch
 | 
				
			||||||
func RenameBranch(repo *models.Repository, doer *models.User, gitRepo *git.Repository, from, to string) (string, error) {
 | 
					func RenameBranch(repo *models.Repository, doer *models.User, gitRepo *git.Repository, from, to string) (string, error) {
 | 
				
			||||||
	if from == to {
 | 
						if from == to {
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										52
									
								
								services/repository/hooks.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										52
									
								
								services/repository/hooks.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,52 @@
 | 
				
			|||||||
 | 
					// Copyright 2021 The Gitea Authors. All rights reserved.
 | 
				
			||||||
 | 
					// Use of this source code is governed by a MIT-style
 | 
				
			||||||
 | 
					// license that can be found in the LICENSE file.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					package repository
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"context"
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"code.gitea.io/gitea/models"
 | 
				
			||||||
 | 
						"code.gitea.io/gitea/models/db"
 | 
				
			||||||
 | 
						"code.gitea.io/gitea/modules/log"
 | 
				
			||||||
 | 
						repo_module "code.gitea.io/gitea/modules/repository"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"xorm.io/builder"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// SyncRepositoryHooks rewrites all repositories' pre-receive, update and post-receive hooks
 | 
				
			||||||
 | 
					// to make sure the binary and custom conf path are up-to-date.
 | 
				
			||||||
 | 
					func SyncRepositoryHooks(ctx context.Context) error {
 | 
				
			||||||
 | 
						log.Trace("Doing: SyncRepositoryHooks")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if err := db.Iterate(
 | 
				
			||||||
 | 
							db.DefaultContext,
 | 
				
			||||||
 | 
							new(models.Repository),
 | 
				
			||||||
 | 
							builder.Gt{"id": 0},
 | 
				
			||||||
 | 
							func(idx int, bean interface{}) error {
 | 
				
			||||||
 | 
								repo := bean.(*models.Repository)
 | 
				
			||||||
 | 
								select {
 | 
				
			||||||
 | 
								case <-ctx.Done():
 | 
				
			||||||
 | 
									return db.ErrCancelledf("before sync repository hooks for %s", repo.FullName())
 | 
				
			||||||
 | 
								default:
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
								if err := repo_module.CreateDelegateHooks(repo.RepoPath()); err != nil {
 | 
				
			||||||
 | 
									return fmt.Errorf("SyncRepositoryHook: %v", err)
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								if repo.HasWiki() {
 | 
				
			||||||
 | 
									if err := repo_module.CreateDelegateHooks(repo.WikiPath()); err != nil {
 | 
				
			||||||
 | 
										return fmt.Errorf("SyncRepositoryHook: %v", err)
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								return nil
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						); err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						log.Trace("Finished: SyncRepositoryHooks")
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@@ -5,8 +5,10 @@
 | 
				
			|||||||
package repository
 | 
					package repository
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
 | 
						"context"
 | 
				
			||||||
	"errors"
 | 
						"errors"
 | 
				
			||||||
	"fmt"
 | 
						"fmt"
 | 
				
			||||||
 | 
						"strings"
 | 
				
			||||||
	"time"
 | 
						"time"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"code.gitea.io/gitea/models"
 | 
						"code.gitea.io/gitea/models"
 | 
				
			||||||
@@ -20,6 +22,7 @@ import (
 | 
				
			|||||||
	"code.gitea.io/gitea/modules/repofiles"
 | 
						"code.gitea.io/gitea/modules/repofiles"
 | 
				
			||||||
	repo_module "code.gitea.io/gitea/modules/repository"
 | 
						repo_module "code.gitea.io/gitea/modules/repository"
 | 
				
			||||||
	"code.gitea.io/gitea/modules/setting"
 | 
						"code.gitea.io/gitea/modules/setting"
 | 
				
			||||||
 | 
						"code.gitea.io/gitea/modules/timeutil"
 | 
				
			||||||
	pull_service "code.gitea.io/gitea/services/pull"
 | 
						pull_service "code.gitea.io/gitea/services/pull"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -210,7 +213,7 @@ func pushUpdates(optsList []*repo_module.PushUpdateOptions) error {
 | 
				
			|||||||
				}
 | 
									}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
				// Cache for big repository
 | 
									// Cache for big repository
 | 
				
			||||||
				if err := repo_module.CacheRef(graceful.GetManager().HammerContext(), repo, gitRepo, opts.RefFullName); err != nil {
 | 
									if err := CacheRef(graceful.GetManager().HammerContext(), repo, gitRepo, opts.RefFullName); err != nil {
 | 
				
			||||||
					log.Error("repo_module.CacheRef %s/%s failed: %v", repo.ID, branch, err)
 | 
										log.Error("repo_module.CacheRef %s/%s failed: %v", repo.ID, branch, err)
 | 
				
			||||||
				}
 | 
									}
 | 
				
			||||||
			} else {
 | 
								} else {
 | 
				
			||||||
@@ -229,7 +232,7 @@ func pushUpdates(optsList []*repo_module.PushUpdateOptions) error {
 | 
				
			|||||||
			log.Trace("Non-tag and non-branch commits pushed.")
 | 
								log.Trace("Non-tag and non-branch commits pushed.")
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	if err := repo_module.PushUpdateAddDeleteTags(repo, gitRepo, addTags, delTags); err != nil {
 | 
						if err := PushUpdateAddDeleteTags(repo, gitRepo, addTags, delTags); err != nil {
 | 
				
			||||||
		return fmt.Errorf("PushUpdateAddDeleteTags: %v", err)
 | 
							return fmt.Errorf("PushUpdateAddDeleteTags: %v", err)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -240,3 +243,122 @@ func pushUpdates(optsList []*repo_module.PushUpdateOptions) error {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	return nil
 | 
						return nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// PushUpdateAddDeleteTags updates a number of added and delete tags
 | 
				
			||||||
 | 
					func PushUpdateAddDeleteTags(repo *models.Repository, gitRepo *git.Repository, addTags, delTags []string) error {
 | 
				
			||||||
 | 
						return db.WithTx(func(ctx context.Context) error {
 | 
				
			||||||
 | 
							if err := models.PushUpdateDeleteTagsContext(ctx, repo, delTags); err != nil {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return pushUpdateAddTags(ctx, repo, gitRepo, addTags)
 | 
				
			||||||
 | 
						})
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// pushUpdateAddTags updates a number of add tags
 | 
				
			||||||
 | 
					func pushUpdateAddTags(ctx context.Context, repo *models.Repository, gitRepo *git.Repository, tags []string) error {
 | 
				
			||||||
 | 
						if len(tags) == 0 {
 | 
				
			||||||
 | 
							return nil
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						lowerTags := make([]string, 0, len(tags))
 | 
				
			||||||
 | 
						for _, tag := range tags {
 | 
				
			||||||
 | 
							lowerTags = append(lowerTags, strings.ToLower(tag))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						releases, err := models.GetReleasesByRepoIDAndNames(ctx, repo.ID, lowerTags)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return fmt.Errorf("GetReleasesByRepoIDAndNames: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						relMap := make(map[string]*models.Release)
 | 
				
			||||||
 | 
						for _, rel := range releases {
 | 
				
			||||||
 | 
							relMap[rel.LowerTagName] = rel
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						newReleases := make([]*models.Release, 0, len(lowerTags)-len(relMap))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						emailToUser := make(map[string]*models.User)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for i, lowerTag := range lowerTags {
 | 
				
			||||||
 | 
							tag, err := gitRepo.GetTag(tags[i])
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("GetTag: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							commit, err := tag.Commit()
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("Commit: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							sig := tag.Tagger
 | 
				
			||||||
 | 
							if sig == nil {
 | 
				
			||||||
 | 
								sig = commit.Author
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if sig == nil {
 | 
				
			||||||
 | 
								sig = commit.Committer
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							var author *models.User
 | 
				
			||||||
 | 
							var createdAt = time.Unix(1, 0)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							if sig != nil {
 | 
				
			||||||
 | 
								var ok bool
 | 
				
			||||||
 | 
								author, ok = emailToUser[sig.Email]
 | 
				
			||||||
 | 
								if !ok {
 | 
				
			||||||
 | 
									author, err = models.GetUserByEmailContext(ctx, sig.Email)
 | 
				
			||||||
 | 
									if err != nil && !models.IsErrUserNotExist(err) {
 | 
				
			||||||
 | 
										return fmt.Errorf("GetUserByEmail: %v", err)
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
									if author != nil {
 | 
				
			||||||
 | 
										emailToUser[sig.Email] = author
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								createdAt = sig.When
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							commitsCount, err := commit.CommitsCount()
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("CommitsCount: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							rel, has := relMap[lowerTag]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							if !has {
 | 
				
			||||||
 | 
								rel = &models.Release{
 | 
				
			||||||
 | 
									RepoID:       repo.ID,
 | 
				
			||||||
 | 
									Title:        "",
 | 
				
			||||||
 | 
									TagName:      tags[i],
 | 
				
			||||||
 | 
									LowerTagName: lowerTag,
 | 
				
			||||||
 | 
									Target:       "",
 | 
				
			||||||
 | 
									Sha1:         commit.ID.String(),
 | 
				
			||||||
 | 
									NumCommits:   commitsCount,
 | 
				
			||||||
 | 
									Note:         "",
 | 
				
			||||||
 | 
									IsDraft:      false,
 | 
				
			||||||
 | 
									IsPrerelease: false,
 | 
				
			||||||
 | 
									IsTag:        true,
 | 
				
			||||||
 | 
									CreatedUnix:  timeutil.TimeStamp(createdAt.Unix()),
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								if author != nil {
 | 
				
			||||||
 | 
									rel.PublisherID = author.ID
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
								newReleases = append(newReleases, rel)
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								rel.Sha1 = commit.ID.String()
 | 
				
			||||||
 | 
								rel.CreatedUnix = timeutil.TimeStamp(createdAt.Unix())
 | 
				
			||||||
 | 
								rel.NumCommits = commitsCount
 | 
				
			||||||
 | 
								rel.IsDraft = false
 | 
				
			||||||
 | 
								if rel.IsTag && author != nil {
 | 
				
			||||||
 | 
									rel.PublisherID = author.ID
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								if err = models.UpdateRelease(ctx, rel); err != nil {
 | 
				
			||||||
 | 
									return fmt.Errorf("Update: %v", err)
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if len(newReleases) > 0 {
 | 
				
			||||||
 | 
							if err = models.InsertReleasesContext(ctx, newReleases); err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("Insert: %v", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user