mirror of
				https://codeberg.org/forgejo/forgejo.git
				synced 2025-11-02 23:41:05 +00:00 
			
		
		
		
	This PR replaces all string refName as a type `git.RefName` to make the code more maintainable. Fix #15367 Replaces #23070 It also fixed a bug that tags are not sync because `git remote --prune origin` will not remove local tags if remote removed. We in fact should use `git fetch --prune --tags origin` but not `git remote update origin` to do the sync. Some answer from ChatGPT as ref. > If the git fetch --prune --tags command is not working as expected, there could be a few reasons why. Here are a few things to check: > >Make sure that you have the latest version of Git installed on your system. You can check the version by running git --version in your terminal. If you have an outdated version, try updating Git and see if that resolves the issue. > >Check that your Git repository is properly configured to track the remote repository's tags. You can check this by running git config --get-all remote.origin.fetch and verifying that it includes +refs/tags/*:refs/tags/*. If it does not, you can add it by running git config --add remote.origin.fetch "+refs/tags/*:refs/tags/*". > >Verify that the tags you are trying to prune actually exist on the remote repository. You can do this by running git ls-remote --tags origin to list all the tags on the remote repository. > >Check if any local tags have been created that match the names of tags on the remote repository. If so, these local tags may be preventing the git fetch --prune --tags command from working properly. You can delete local tags using the git tag -d command. --------- Co-authored-by: delvh <dev.lh@web.de>
		
			
				
	
	
		
			143 lines
		
	
	
	
		
			4.8 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
			
		
		
	
	
			143 lines
		
	
	
	
		
			4.8 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
// Copyright 2019 The Gitea Authors. All rights reserved.
 | 
						|
// SPDX-License-Identifier: MIT
 | 
						|
 | 
						|
package private
 | 
						|
 | 
						|
import (
 | 
						|
	"context"
 | 
						|
	"fmt"
 | 
						|
	"net/url"
 | 
						|
	"strconv"
 | 
						|
	"time"
 | 
						|
 | 
						|
	"code.gitea.io/gitea/modules/git"
 | 
						|
	"code.gitea.io/gitea/modules/setting"
 | 
						|
)
 | 
						|
 | 
						|
// Git environment variables
 | 
						|
const (
 | 
						|
	GitAlternativeObjectDirectories = "GIT_ALTERNATE_OBJECT_DIRECTORIES"
 | 
						|
	GitObjectDirectory              = "GIT_OBJECT_DIRECTORY"
 | 
						|
	GitQuarantinePath               = "GIT_QUARANTINE_PATH"
 | 
						|
	GitPushOptionCount              = "GIT_PUSH_OPTION_COUNT"
 | 
						|
)
 | 
						|
 | 
						|
// GitPushOptions is a wrapper around a map[string]string
 | 
						|
type GitPushOptions map[string]string
 | 
						|
 | 
						|
// GitPushOptions keys
 | 
						|
const (
 | 
						|
	GitPushOptionRepoPrivate  = "repo.private"
 | 
						|
	GitPushOptionRepoTemplate = "repo.template"
 | 
						|
)
 | 
						|
 | 
						|
// Bool checks for a key in the map and parses as a boolean
 | 
						|
func (g GitPushOptions) Bool(key string, def bool) bool {
 | 
						|
	if val, ok := g[key]; ok {
 | 
						|
		if b, err := strconv.ParseBool(val); err == nil {
 | 
						|
			return b
 | 
						|
		}
 | 
						|
	}
 | 
						|
	return def
 | 
						|
}
 | 
						|
 | 
						|
// HookOptions represents the options for the Hook calls
 | 
						|
type HookOptions struct {
 | 
						|
	OldCommitIDs                    []string
 | 
						|
	NewCommitIDs                    []string
 | 
						|
	RefFullNames                    []git.RefName
 | 
						|
	UserID                          int64
 | 
						|
	UserName                        string
 | 
						|
	GitObjectDirectory              string
 | 
						|
	GitAlternativeObjectDirectories string
 | 
						|
	GitQuarantinePath               string
 | 
						|
	GitPushOptions                  GitPushOptions
 | 
						|
	PullRequestID                   int64
 | 
						|
	DeployKeyID                     int64 // if the pusher is a DeployKey, then UserID is the repo's org user.
 | 
						|
	IsWiki                          bool
 | 
						|
	ActionPerm                      int
 | 
						|
}
 | 
						|
 | 
						|
// SSHLogOption ssh log options
 | 
						|
type SSHLogOption struct {
 | 
						|
	IsError bool
 | 
						|
	Message string
 | 
						|
}
 | 
						|
 | 
						|
// HookPostReceiveResult represents an individual result from PostReceive
 | 
						|
type HookPostReceiveResult struct {
 | 
						|
	Results      []HookPostReceiveBranchResult
 | 
						|
	RepoWasEmpty bool
 | 
						|
	Err          string
 | 
						|
}
 | 
						|
 | 
						|
// HookPostReceiveBranchResult represents an individual branch result from PostReceive
 | 
						|
type HookPostReceiveBranchResult struct {
 | 
						|
	Message bool
 | 
						|
	Create  bool
 | 
						|
	Branch  string
 | 
						|
	URL     string
 | 
						|
}
 | 
						|
 | 
						|
// HookProcReceiveResult represents an individual result from ProcReceive
 | 
						|
type HookProcReceiveResult struct {
 | 
						|
	Results []HookProcReceiveRefResult
 | 
						|
	Err     string
 | 
						|
}
 | 
						|
 | 
						|
// HookProcReceiveRefResult represents an individual result from ProcReceive
 | 
						|
type HookProcReceiveRefResult struct {
 | 
						|
	OldOID       string
 | 
						|
	NewOID       string
 | 
						|
	Ref          string
 | 
						|
	OriginalRef  git.RefName
 | 
						|
	IsForcePush  bool
 | 
						|
	IsNotMatched bool
 | 
						|
	Err          string
 | 
						|
}
 | 
						|
 | 
						|
// HookPreReceive check whether the provided commits are allowed
 | 
						|
func HookPreReceive(ctx context.Context, ownerName, repoName string, opts HookOptions) ResponseExtra {
 | 
						|
	reqURL := setting.LocalURL + fmt.Sprintf("api/internal/hook/pre-receive/%s/%s", url.PathEscape(ownerName), url.PathEscape(repoName))
 | 
						|
	req := newInternalRequest(ctx, reqURL, "POST", opts)
 | 
						|
	req.SetReadWriteTimeout(time.Duration(60+len(opts.OldCommitIDs)) * time.Second)
 | 
						|
	_, extra := requestJSONResp(req, &responseText{})
 | 
						|
	return extra
 | 
						|
}
 | 
						|
 | 
						|
// HookPostReceive updates services and users
 | 
						|
func HookPostReceive(ctx context.Context, ownerName, repoName string, opts HookOptions) (*HookPostReceiveResult, ResponseExtra) {
 | 
						|
	reqURL := setting.LocalURL + fmt.Sprintf("api/internal/hook/post-receive/%s/%s", url.PathEscape(ownerName), url.PathEscape(repoName))
 | 
						|
	req := newInternalRequest(ctx, reqURL, "POST", opts)
 | 
						|
	req.SetReadWriteTimeout(time.Duration(60+len(opts.OldCommitIDs)) * time.Second)
 | 
						|
	return requestJSONResp(req, &HookPostReceiveResult{})
 | 
						|
}
 | 
						|
 | 
						|
// HookProcReceive proc-receive hook
 | 
						|
func HookProcReceive(ctx context.Context, ownerName, repoName string, opts HookOptions) (*HookProcReceiveResult, ResponseExtra) {
 | 
						|
	reqURL := setting.LocalURL + fmt.Sprintf("api/internal/hook/proc-receive/%s/%s", url.PathEscape(ownerName), url.PathEscape(repoName))
 | 
						|
 | 
						|
	req := newInternalRequest(ctx, reqURL, "POST", opts)
 | 
						|
	req.SetReadWriteTimeout(time.Duration(60+len(opts.OldCommitIDs)) * time.Second)
 | 
						|
	return requestJSONResp(req, &HookProcReceiveResult{})
 | 
						|
}
 | 
						|
 | 
						|
// SetDefaultBranch will set the default branch to the provided branch for the provided repository
 | 
						|
func SetDefaultBranch(ctx context.Context, ownerName, repoName, branch string) ResponseExtra {
 | 
						|
	reqURL := setting.LocalURL + fmt.Sprintf("api/internal/hook/set-default-branch/%s/%s/%s",
 | 
						|
		url.PathEscape(ownerName),
 | 
						|
		url.PathEscape(repoName),
 | 
						|
		url.PathEscape(branch),
 | 
						|
	)
 | 
						|
	req := newInternalRequest(ctx, reqURL, "POST")
 | 
						|
	_, extra := requestJSONResp(req, &responseText{})
 | 
						|
	return extra
 | 
						|
}
 | 
						|
 | 
						|
// SSHLog sends ssh error log response
 | 
						|
func SSHLog(ctx context.Context, isErr bool, msg string) error {
 | 
						|
	reqURL := setting.LocalURL + "api/internal/ssh/log"
 | 
						|
	req := newInternalRequest(ctx, reqURL, "POST", &SSHLogOption{IsError: isErr, Message: msg})
 | 
						|
	_, extra := requestJSONResp(req, &responseText{})
 | 
						|
	return extra.Error
 | 
						|
}
 |