mirror of
				https://github.com/go-gitea/gitea.git
				synced 2025-10-25 17:44:32 +02:00 
			
		
		
		
	Merge branch 'main' of https://github.com/go-gitea/gitea into workflow_job_webhook_bp
This commit is contained in:
		
						commit
						dec1a104ea
					
				| @ -336,7 +336,7 @@ module.exports = { | ||||
|     '@typescript-eslint/no-unsafe-unary-minus': [2], | ||||
|     '@typescript-eslint/no-unused-expressions': [0], | ||||
|     '@typescript-eslint/no-unused-vars': [2, {vars: 'all', args: 'all', caughtErrors: 'all', ignoreRestSiblings: false, argsIgnorePattern: '^_', varsIgnorePattern: '^_', caughtErrorsIgnorePattern: '^_', destructuredArrayIgnorePattern: '^_'}], | ||||
|     '@typescript-eslint/no-use-before-define': [0], | ||||
|     '@typescript-eslint/no-use-before-define': [2, {functions: false, classes: true, variables: true, allowNamedExports: true, typedefs: false, enums: false, ignoreTypeReferences: true}], | ||||
|     '@typescript-eslint/no-useless-constructor': [0], | ||||
|     '@typescript-eslint/no-useless-empty-export': [0], | ||||
|     '@typescript-eslint/no-wrapper-object-types': [2], | ||||
| @ -693,7 +693,7 @@ module.exports = { | ||||
|     'no-unused-labels': [2], | ||||
|     'no-unused-private-class-members': [2], | ||||
|     'no-unused-vars': [0], // handled by @typescript-eslint/no-unused-vars
 | ||||
|     'no-use-before-define': [2, {functions: false, classes: true, variables: true, allowNamedExports: true}], | ||||
|     'no-use-before-define': [0], // handled by @typescript-eslint/no-use-before-define
 | ||||
|     'no-use-extend-native/no-use-extend-native': [2], | ||||
|     'no-useless-backreference': [2], | ||||
|     'no-useless-call': [2], | ||||
|  | ||||
							
								
								
									
										10
									
								
								.github/labeler.yml
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										10
									
								
								.github/labeler.yml
									
									
									
									
										vendored
									
									
								
							| @ -41,7 +41,7 @@ modifies/internal: | ||||
|           - ".dockerignore" | ||||
|           - "docker/**" | ||||
|           - ".editorconfig" | ||||
|           - ".eslintrc.yaml" | ||||
|           - ".eslintrc.cjs" | ||||
|           - ".golangci.yml" | ||||
|           - ".gitpod.yml" | ||||
|           - ".markdownlint.yaml" | ||||
| @ -49,7 +49,7 @@ modifies/internal: | ||||
|           - "stylelint.config.js" | ||||
|           - ".yamllint.yaml" | ||||
|           - ".github/**" | ||||
|           - ".gitea/" | ||||
|           - ".gitea/**" | ||||
|           - ".devcontainer/**" | ||||
|           - "build.go" | ||||
|           - "build/**" | ||||
| @ -73,9 +73,9 @@ modifies/go: | ||||
| modifies/frontend: | ||||
|   - changed-files: | ||||
|       - any-glob-to-any-file: | ||||
|           - "**/*.js" | ||||
|           - "**/*.ts" | ||||
|           - "**/*.vue" | ||||
|           - "*.js" | ||||
|           - "*.ts" | ||||
|           - "web_src/**" | ||||
| 
 | ||||
| docs-update-needed: | ||||
|   - changed-files: | ||||
|  | ||||
							
								
								
									
										8
									
								
								.github/workflows/files-changed.yml
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										8
									
								
								.github/workflows/files-changed.yml
									
									
									
									
										vendored
									
									
								
							| @ -51,14 +51,16 @@ jobs: | ||||
|               - "options/locale/locale_en-US.ini" | ||||
| 
 | ||||
|             frontend: | ||||
|               - "**/*.js" | ||||
|               - "*.js" | ||||
|               - "*.ts" | ||||
|               - "web_src/**" | ||||
|               - "tools/*.js" | ||||
|               - "tools/*.ts" | ||||
|               - "assets/emoji.json" | ||||
|               - "package.json" | ||||
|               - "package-lock.json" | ||||
|               - "Makefile" | ||||
|               - ".eslintrc.yaml" | ||||
|               - "stylelint.config.js" | ||||
|               - ".eslintrc.cjs" | ||||
|               - ".npmrc" | ||||
| 
 | ||||
|             docs: | ||||
|  | ||||
							
								
								
									
										2
									
								
								.github/workflows/pull-compliance.yml
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										2
									
								
								.github/workflows/pull-compliance.yml
									
									
									
									
										vendored
									
									
								
							| @ -95,7 +95,7 @@ jobs: | ||||
|           go-version-file: go.mod | ||||
|           check-latest: true | ||||
|       - run: make deps-backend deps-tools | ||||
|       - run: make lint-go-windows lint-go-vet | ||||
|       - run: make lint-go-windows lint-go-gitea-vet | ||||
|         env: | ||||
|           TAGS: bindata sqlite sqlite_unlock_notify | ||||
|           GOOS: windows | ||||
|  | ||||
							
								
								
									
										6
									
								
								.github/workflows/pull-db-tests.yml
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										6
									
								
								.github/workflows/pull-db-tests.yml
									
									
									
									
										vendored
									
									
								
							| @ -202,12 +202,10 @@ jobs: | ||||
|   test-mssql: | ||||
|     if: needs.files-changed.outputs.backend == 'true' || needs.files-changed.outputs.actions == 'true' | ||||
|     needs: files-changed | ||||
|     # specifying the version of ubuntu in use as mssql fails on newer kernels | ||||
|     # pending resolution from vendor | ||||
|     runs-on: ubuntu-20.04 | ||||
|     runs-on: ubuntu-latest | ||||
|     services: | ||||
|       mssql: | ||||
|         image: mcr.microsoft.com/mssql/server:2017-latest | ||||
|         image: mcr.microsoft.com/mssql/server:2019-latest | ||||
|         env: | ||||
|           ACCEPT_EULA: Y | ||||
|           MSSQL_PID: Standard | ||||
|  | ||||
							
								
								
									
										15
									
								
								Makefile
									
									
									
									
									
								
							
							
						
						
									
										15
									
								
								Makefile
									
									
									
									
									
								
							| @ -73,6 +73,7 @@ EXTRA_GOFLAGS ?= | ||||
| MAKE_VERSION := $(shell "$(MAKE)" -v | cat | head -n 1) | ||||
| MAKE_EVIDENCE_DIR := .make_evidence | ||||
| 
 | ||||
| GOTESTFLAGS ?= -vet=off | ||||
| ifeq ($(RACE_ENABLED),true) | ||||
| 	GOFLAGS += -race | ||||
| 	GOTESTFLAGS += -race | ||||
| @ -311,10 +312,10 @@ lint-frontend: lint-js lint-css ## lint frontend files | ||||
| lint-frontend-fix: lint-js-fix lint-css-fix ## lint frontend files and fix issues
 | ||||
| 
 | ||||
| .PHONY: lint-backend | ||||
| lint-backend: lint-go lint-go-vet lint-go-gopls lint-editorconfig ## lint backend files
 | ||||
| lint-backend: lint-go lint-go-gitea-vet lint-go-gopls lint-editorconfig ## lint backend files
 | ||||
| 
 | ||||
| .PHONY: lint-backend-fix | ||||
| lint-backend-fix: lint-go-fix lint-go-vet lint-editorconfig ## lint backend files and fix issues
 | ||||
| lint-backend-fix: lint-go-fix lint-go-gitea-vet lint-editorconfig ## lint backend files and fix issues
 | ||||
| 
 | ||||
| .PHONY: lint-js | ||||
| lint-js: node_modules ## lint js files
 | ||||
| @ -365,9 +366,9 @@ lint-go-windows: | ||||
| 	@GOOS= GOARCH= $(GO) install $(GOLANGCI_LINT_PACKAGE) | ||||
| 	golangci-lint run | ||||
| 
 | ||||
| .PHONY: lint-go-vet | ||||
| lint-go-vet: ## lint go files with vet
 | ||||
| 	@echo "Running go vet..." | ||||
| .PHONY: lint-go-gitea-vet | ||||
| lint-go-gitea-vet: ## lint go files with gitea-vet
 | ||||
| 	@echo "Running gitea-vet..." | ||||
| 	@GOOS= GOARCH= $(GO) build code.gitea.io/gitea-vet | ||||
| 	@$(GO) vet -vettool=gitea-vet ./... | ||||
| 
 | ||||
| @ -470,7 +471,9 @@ tidy-check: tidy | ||||
| go-licenses: $(GO_LICENSE_FILE) ## regenerate go licenses
 | ||||
| 
 | ||||
| $(GO_LICENSE_FILE): go.mod go.sum | ||||
| 	-$(GO) run $(GO_LICENSES_PACKAGE) save . --force --save_path=$(GO_LICENSE_TMP_DIR) 2>/dev/null | ||||
| 	@rm -rf $(GO_LICENSE_FILE) | ||||
| 	$(GO) install $(GO_LICENSES_PACKAGE) | ||||
| 	-GOOS=linux CGO_ENABLED=1 go-licenses save . --force --save_path=$(GO_LICENSE_TMP_DIR) 2>/dev/null | ||||
| 	$(GO) run build/generate-go-licenses.go $(GO_LICENSE_TMP_DIR) $(GO_LICENSE_FILE) | ||||
| 	@rm -rf $(GO_LICENSE_TMP_DIR) | ||||
| 
 | ||||
|  | ||||
| @ -316,7 +316,7 @@ func runHookPostReceive(c *cli.Context) error { | ||||
| 	setup(ctx, c.Bool("debug")) | ||||
| 
 | ||||
| 	// First of all run update-server-info no matter what | ||||
| 	if _, _, err := git.NewCommand(ctx, "update-server-info").RunStdString(nil); err != nil { | ||||
| 	if _, _, err := git.NewCommand("update-server-info").RunStdString(ctx, nil); err != nil { | ||||
| 		return fmt.Errorf("Failed to call 'git update-server-info': %w", err) | ||||
| 	} | ||||
| 
 | ||||
|  | ||||
							
								
								
									
										8
									
								
								go.mod
									
									
									
									
									
								
							
							
						
						
									
										8
									
								
								go.mod
									
									
									
									
									
								
							| @ -8,7 +8,7 @@ go 1.24 | ||||
| godebug x509negativeserial=1 | ||||
| 
 | ||||
| require ( | ||||
| 	code.gitea.io/actions-proto-go v0.4.0 | ||||
| 	code.gitea.io/actions-proto-go v0.4.1 | ||||
| 	code.gitea.io/gitea-vet v0.2.3 | ||||
| 	code.gitea.io/sdk/gitea v0.20.0 | ||||
| 	codeberg.org/gusted/mcaptcha v0.0.0-20220723083913-4f3072e1d570 | ||||
| @ -24,7 +24,7 @@ require ( | ||||
| 	github.com/Azure/azure-sdk-for-go/sdk/azcore v1.17.0 | ||||
| 	github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v1.6.0 | ||||
| 	github.com/Azure/go-ntlmssp v0.0.0-20221128193559-754e69321358 | ||||
| 	github.com/ProtonMail/go-crypto v1.1.5 | ||||
| 	github.com/ProtonMail/go-crypto v1.1.6 | ||||
| 	github.com/PuerkitoBio/goquery v1.10.2 | ||||
| 	github.com/SaveTheRbtz/zstd-seekable-format-go/pkg v0.7.3 | ||||
| 	github.com/alecthomas/chroma/v2 v2.15.0 | ||||
| @ -119,7 +119,7 @@ require ( | ||||
| 	gitlab.com/gitlab-org/api/client-go v0.123.0 | ||||
| 	golang.org/x/crypto v0.35.0 | ||||
| 	golang.org/x/image v0.24.0 | ||||
| 	golang.org/x/net v0.35.0 | ||||
| 	golang.org/x/net v0.36.0 | ||||
| 	golang.org/x/oauth2 v0.27.0 | ||||
| 	golang.org/x/sync v0.11.0 | ||||
| 	golang.org/x/sys v0.30.0 | ||||
| @ -318,7 +318,7 @@ replace github.com/hashicorp/go-version => github.com/6543/go-version v1.3.1 | ||||
| 
 | ||||
| replace github.com/shurcooL/vfsgen => github.com/lunny/vfsgen v0.0.0-20220105142115-2c99e1ffdfa0 | ||||
| 
 | ||||
| replace github.com/nektos/act => gitea.com/gitea/act v0.261.3 | ||||
| replace github.com/nektos/act => gitea.com/gitea/act v0.261.4 | ||||
| 
 | ||||
| // TODO: the only difference is in `PutObject`: the fork doesn't use `NewVerifyingReader(r, sha256.New(), oid, expectedSize)`, need to figure out why | ||||
| replace github.com/charmbracelet/git-lfs-transfer => gitea.com/gitea/git-lfs-transfer v0.2.0 | ||||
|  | ||||
							
								
								
									
										16
									
								
								go.sum
									
									
									
									
									
								
							
							
						
						
									
										16
									
								
								go.sum
									
									
									
									
									
								
							| @ -1,7 +1,7 @@ | ||||
| cloud.google.com/go/compute/metadata v0.6.0 h1:A6hENjEsCDtC1k8byVsgwvVcioamEHvZ4j01OwKxG9I= | ||||
| cloud.google.com/go/compute/metadata v0.6.0/go.mod h1:FjyFAW1MW0C203CEOMDTu3Dk1FlqW3Rga40jzHL4hfg= | ||||
| code.gitea.io/actions-proto-go v0.4.0 h1:OsPBPhodXuQnsspG1sQ4eRE1PeoZyofd7+i73zCwnsU= | ||||
| code.gitea.io/actions-proto-go v0.4.0/go.mod h1:mn7Wkqz6JbnTOHQpot3yDeHx+O5C9EGhMEE+htvHBas= | ||||
| code.gitea.io/actions-proto-go v0.4.1 h1:l0EYhjsgpUe/1VABo2eK7zcoNX2W44WOnb0MSLrKfls= | ||||
| code.gitea.io/actions-proto-go v0.4.1/go.mod h1:mn7Wkqz6JbnTOHQpot3yDeHx+O5C9EGhMEE+htvHBas= | ||||
| code.gitea.io/gitea-vet v0.2.3 h1:gdFmm6WOTM65rE8FUBTRzeQZYzXePKSSB1+r574hWwI= | ||||
| code.gitea.io/gitea-vet v0.2.3/go.mod h1:zcNbT/aJEmivCAhfmkHOlT645KNOf9W2KnkLgFjGGfE= | ||||
| code.gitea.io/sdk/gitea v0.20.0 h1:Zm/QDwwZK1awoM4AxdjeAQbxolzx2rIP8dDfmKu+KoU= | ||||
| @ -16,8 +16,8 @@ filippo.io/edwards25519 v1.1.0 h1:FNf4tywRC1HmFuKW5xopWpigGjJKiJSV0Cqo0cJWDaA= | ||||
| filippo.io/edwards25519 v1.1.0/go.mod h1:BxyFTGdWcka3PhytdK4V28tE5sGfRvvvRV7EaN4VDT4= | ||||
| git.sr.ht/~mariusor/go-xsd-duration v0.0.0-20220703122237-02e73435a078 h1:cliQ4HHsCo6xi2oWZYKWW4bly/Ory9FuTpFPRxj/mAg= | ||||
| git.sr.ht/~mariusor/go-xsd-duration v0.0.0-20220703122237-02e73435a078/go.mod h1:g/V2Hjas6Z1UHUp4yIx6bATpNzJ7DYtD0FG3+xARWxs= | ||||
| gitea.com/gitea/act v0.261.3 h1:BhiYpGJQKGq0XMYYICCYAN4KnsEWHyLbA6dxhZwFcV4= | ||||
| gitea.com/gitea/act v0.261.3/go.mod h1:Pg5C9kQY1CEA3QjthjhlrqOC/QOT5NyWNjOjRHw23Ok= | ||||
| gitea.com/gitea/act v0.261.4 h1:Tf9eLlvsYFtKcpuxlMvf9yT3g4Hshb2Beqw6C1STuH8= | ||||
| gitea.com/gitea/act v0.261.4/go.mod h1:Pg5C9kQY1CEA3QjthjhlrqOC/QOT5NyWNjOjRHw23Ok= | ||||
| gitea.com/gitea/git-lfs-transfer v0.2.0 h1:baHaNoBSRaeq/xKayEXwiDQtlIjps4Ac/Ll4KqLMB40= | ||||
| gitea.com/gitea/git-lfs-transfer v0.2.0/go.mod h1:UrXUCm3xLQkq15fu7qlXHUMlrhdlXHoi13KH2Dfiits= | ||||
| gitea.com/go-chi/binding v0.0.0-20240430071103-39a851e106ed h1:EZZBtilMLSZNWtHHcgq2mt6NSGhJSZBuduAlinMEmso= | ||||
| @ -71,8 +71,8 @@ github.com/Masterminds/sprig/v3 v3.3.0/go.mod h1:Zy1iXRYNqNLUolqCpL4uhk6SHUMAOSC | ||||
| github.com/Microsoft/go-winio v0.5.2/go.mod h1:WpS1mjBmmwHBEWmogvA2mj8546UReBk4v8QkMxJ6pZY= | ||||
| github.com/Microsoft/go-winio v0.6.2 h1:F2VQgta7ecxGYO8k3ZZz3RS8fVIXVxONVUPlNERoyfY= | ||||
| github.com/Microsoft/go-winio v0.6.2/go.mod h1:yd8OoFMLzJbo9gZq8j5qaps8bJ9aShtEA8Ipt1oGCvU= | ||||
| github.com/ProtonMail/go-crypto v1.1.5 h1:eoAQfK2dwL+tFSFpr7TbOaPNUbPiJj4fLYwwGE1FQO4= | ||||
| github.com/ProtonMail/go-crypto v1.1.5/go.mod h1:rA3QumHc/FZ8pAHreoekgiAbzpNsfQAosU5td4SnOrE= | ||||
| github.com/ProtonMail/go-crypto v1.1.6 h1:ZcV+Ropw6Qn0AX9brlQLAUXfqLBc7Bl+f/DmNxpLfdw= | ||||
| github.com/ProtonMail/go-crypto v1.1.6/go.mod h1:rA3QumHc/FZ8pAHreoekgiAbzpNsfQAosU5td4SnOrE= | ||||
| github.com/PuerkitoBio/goquery v1.10.2 h1:7fh2BdHcG6VFZsK7toXBT/Bh1z5Wmy8Q9MV9HqT2AM8= | ||||
| github.com/PuerkitoBio/goquery v1.10.2/go.mod h1:0guWGjcLu9AYC7C1GHnpysHy056u9aEkUHwhdnePMCU= | ||||
| github.com/RoaringBitmap/roaring v0.4.23/go.mod h1:D0gp8kJQgE1A4LQ5wFLggQEyvDi06Mq5mKs52e1TwOo= | ||||
| @ -867,8 +867,8 @@ golang.org/x/net v0.15.0/go.mod h1:idbUs1IY1+zTqbi8yxTbhexhEEk5ur9LInksu6HrEpk= | ||||
| golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44= | ||||
| golang.org/x/net v0.25.0/go.mod h1:JkAGAh7GEvH74S6FOH42FLoXpXbE/aqXSrIQjXgsiwM= | ||||
| golang.org/x/net v0.33.0/go.mod h1:HXLR5J+9DxmrqMwG9qjGCxZ+zKXxBru04zlTvWlWuN4= | ||||
| golang.org/x/net v0.35.0 h1:T5GQRQb2y08kTAByq9L4/bz8cipCdA8FbRTXewonqY8= | ||||
| golang.org/x/net v0.35.0/go.mod h1:EglIi67kWsHKlRzzVMUD93VMSWGFOMSZgxFjparz1Qk= | ||||
| golang.org/x/net v0.36.0 h1:vWF2fRbw4qslQsQzgFqZff+BItCvGFQqKzKIzx1rmoA= | ||||
| golang.org/x/net v0.36.0/go.mod h1:bFmbeoIPfrw4sMHNhb4J9f6+tPziuGjq7Jk/38fxi1I= | ||||
| golang.org/x/oauth2 v0.27.0 h1:da9Vo7/tDv5RH/7nZDz1eMGS/q1Vv1N/7FCrBhI9I3M= | ||||
| golang.org/x/oauth2 v0.27.0/go.mod h1:onh5ek6nERTohokkhCD/y2cV4Do3fxFHFuAejCkRWT8= | ||||
| golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= | ||||
|  | ||||
| @ -337,3 +337,17 @@ func FixRunnersWithoutBelongingRepo(ctx context.Context) (int64, error) { | ||||
| 	} | ||||
| 	return res.RowsAffected() | ||||
| } | ||||
| 
 | ||||
| func CountWrongRepoLevelRunners(ctx context.Context) (int64, error) { | ||||
| 	var result int64 | ||||
| 	_, err := db.GetEngine(ctx).SQL("SELECT count(`id`) FROM `action_runner` WHERE `repo_id` > 0 AND `owner_id` > 0").Get(&result) | ||||
| 	return result, err | ||||
| } | ||||
| 
 | ||||
| func UpdateWrongRepoLevelRunners(ctx context.Context) (int64, error) { | ||||
| 	result, err := db.GetEngine(ctx).Exec("UPDATE `action_runner` SET `owner_id` = 0 WHERE `repo_id` > 0 AND `owner_id` > 0") | ||||
| 	if err != nil { | ||||
| 		return 0, err | ||||
| 	} | ||||
| 	return result.RowsAffected() | ||||
| } | ||||
|  | ||||
| @ -43,15 +43,12 @@ func init() { | ||||
| // GetSchedulesMapByIDs returns the schedules by given id slice. | ||||
| func GetSchedulesMapByIDs(ctx context.Context, ids []int64) (map[int64]*ActionSchedule, error) { | ||||
| 	schedules := make(map[int64]*ActionSchedule, len(ids)) | ||||
| 	if len(ids) == 0 { | ||||
| 		return schedules, nil | ||||
| 	} | ||||
| 	return schedules, db.GetEngine(ctx).In("id", ids).Find(&schedules) | ||||
| } | ||||
| 
 | ||||
| // GetReposMapByIDs returns the repos by given id slice. | ||||
| func GetReposMapByIDs(ctx context.Context, ids []int64) (map[int64]*repo_model.Repository, error) { | ||||
| 	repos := make(map[int64]*repo_model.Repository, len(ids)) | ||||
| 	return repos, db.GetEngine(ctx).In("id", ids).Find(&repos) | ||||
| } | ||||
| 
 | ||||
| // CreateScheduleTask creates new schedule task. | ||||
| func CreateScheduleTask(ctx context.Context, rows []*ActionSchedule) error { | ||||
| 	// Return early if there are no rows to insert | ||||
|  | ||||
| @ -32,7 +32,7 @@ func (specs SpecList) LoadSchedules(ctx context.Context) error { | ||||
| 	} | ||||
| 
 | ||||
| 	repoIDs := specs.GetRepoIDs() | ||||
| 	repos, err := GetReposMapByIDs(ctx, repoIDs) | ||||
| 	repos, err := repo_model.GetRepositoriesMapByIDs(ctx, repoIDs) | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
|  | ||||
| @ -147,3 +147,17 @@ func GetVariablesOfRun(ctx context.Context, run *ActionRun) (map[string]string, | ||||
| 
 | ||||
| 	return variables, nil | ||||
| } | ||||
| 
 | ||||
| func CountWrongRepoLevelVariables(ctx context.Context) (int64, error) { | ||||
| 	var result int64 | ||||
| 	_, err := db.GetEngine(ctx).SQL("SELECT count(`id`) FROM `action_variable` WHERE `repo_id` > 0 AND `owner_id` > 0").Get(&result) | ||||
| 	return result, err | ||||
| } | ||||
| 
 | ||||
| func UpdateWrongRepoLevelVariables(ctx context.Context) (int64, error) { | ||||
| 	result, err := db.GetEngine(ctx).Exec("UPDATE `action_variable` SET `owner_id` = 0 WHERE `repo_id` > 0 AND `owner_id` > 0") | ||||
| 	if err != nil { | ||||
| 		return 0, err | ||||
| 	} | ||||
| 	return result.RowsAffected() | ||||
| } | ||||
|  | ||||
| @ -25,7 +25,7 @@ func (err ErrKeyUnableVerify) Error() string { | ||||
| } | ||||
| 
 | ||||
| // ErrKeyIsPrivate is returned when the provided key is a private key not a public key | ||||
| var ErrKeyIsPrivate = util.NewSilentWrapErrorf(util.ErrInvalidArgument, "the provided key is a private key") | ||||
| var ErrKeyIsPrivate = util.ErrorWrap(util.ErrInvalidArgument, "the provided key is a private key") | ||||
| 
 | ||||
| // ErrKeyNotExist represents a "KeyNotExist" kind of error. | ||||
| type ErrKeyNotExist struct { | ||||
|  | ||||
| @ -5,6 +5,7 @@ package auth | ||||
| 
 | ||||
| import ( | ||||
| 	"fmt" | ||||
| 	"slices" | ||||
| 	"strings" | ||||
| 
 | ||||
| 	"code.gitea.io/gitea/models/perm" | ||||
| @ -14,7 +15,7 @@ import ( | ||||
| type AccessTokenScopeCategory int | ||||
| 
 | ||||
| const ( | ||||
| 	AccessTokenScopeCategoryActivityPub = iota | ||||
| 	AccessTokenScopeCategoryActivityPub AccessTokenScopeCategory = iota | ||||
| 	AccessTokenScopeCategoryAdmin | ||||
| 	AccessTokenScopeCategoryMisc // WARN: this is now just a placeholder, don't remove it which will change the following values | ||||
| 	AccessTokenScopeCategoryNotification | ||||
| @ -193,6 +194,14 @@ var accessTokenScopes = map[AccessTokenScopeLevel]map[AccessTokenScopeCategory]A | ||||
| 	}, | ||||
| } | ||||
| 
 | ||||
| func GetAccessTokenCategories() (res []string) { | ||||
| 	for _, cat := range accessTokenScopes[Read] { | ||||
| 		res = append(res, strings.TrimPrefix(string(cat), "read:")) | ||||
| 	} | ||||
| 	slices.Sort(res) | ||||
| 	return res | ||||
| } | ||||
| 
 | ||||
| // GetRequiredScopes gets the specific scopes for a given level and categories | ||||
| func GetRequiredScopes(level AccessTokenScopeLevel, scopeCategories ...AccessTokenScopeCategory) []AccessTokenScope { | ||||
| 	scopes := make([]AccessTokenScope, 0, len(scopeCategories)) | ||||
| @ -270,6 +279,9 @@ func (s AccessTokenScope) parse() (accessTokenScopeBitmap, error) { | ||||
| 
 | ||||
| // StringSlice returns the AccessTokenScope as a []string | ||||
| func (s AccessTokenScope) StringSlice() []string { | ||||
| 	if s == "" { | ||||
| 		return nil | ||||
| 	} | ||||
| 	return strings.Split(string(s), ",") | ||||
| } | ||||
| 
 | ||||
|  | ||||
| @ -17,6 +17,7 @@ type scopeTestNormalize struct { | ||||
| } | ||||
| 
 | ||||
| func TestAccessTokenScope_Normalize(t *testing.T) { | ||||
| 	assert.Equal(t, []string{"activitypub", "admin", "issue", "misc", "notification", "organization", "package", "repository", "user"}, GetAccessTokenCategories()) | ||||
| 	tests := []scopeTestNormalize{ | ||||
| 		{"", "", nil}, | ||||
| 		{"write:misc,write:notification,read:package,write:notification,public-only", "public-only,write:misc,write:notification,read:package", nil}, | ||||
| @ -25,7 +26,7 @@ func TestAccessTokenScope_Normalize(t *testing.T) { | ||||
| 		{"write:activitypub,write:admin,write:misc,write:notification,write:organization,write:package,write:issue,write:repository,write:user,public-only", "public-only,all", nil}, | ||||
| 	} | ||||
| 
 | ||||
| 	for _, scope := range []string{"activitypub", "admin", "misc", "notification", "organization", "package", "issue", "repository", "user"} { | ||||
| 	for _, scope := range GetAccessTokenCategories() { | ||||
| 		tests = append(tests, | ||||
| 			scopeTestNormalize{AccessTokenScope(fmt.Sprintf("read:%s", scope)), AccessTokenScope(fmt.Sprintf("read:%s", scope)), nil}, | ||||
| 			scopeTestNormalize{AccessTokenScope(fmt.Sprintf("write:%s", scope)), AccessTokenScope(fmt.Sprintf("write:%s", scope)), nil}, | ||||
| @ -59,7 +60,7 @@ func TestAccessTokenScope_HasScope(t *testing.T) { | ||||
| 		{"public-only", "read:issue", false, nil}, | ||||
| 	} | ||||
| 
 | ||||
| 	for _, scope := range []string{"activitypub", "admin", "misc", "notification", "organization", "package", "issue", "repository", "user"} { | ||||
| 	for _, scope := range GetAccessTokenCategories() { | ||||
| 		tests = append(tests, | ||||
| 			scopeTestHasScope{ | ||||
| 				AccessTokenScope(fmt.Sprintf("read:%s", scope)), | ||||
|  | ||||
| @ -289,6 +289,9 @@ func FindIDs(ctx context.Context, tableName, idCol string, cond builder.Cond) ([ | ||||
| // DecrByIDs decreases the given column for entities of the "bean" type with one of the given ids by one | ||||
| // Timestamps of the entities won't be updated | ||||
| func DecrByIDs(ctx context.Context, ids []int64, decrCol string, bean any) error { | ||||
| 	if len(ids) == 0 { | ||||
| 		return nil | ||||
| 	} | ||||
| 	_, err := GetEngine(ctx).Decr(decrCol).In("id", ids).NoAutoCondition().NoAutoTime().Update(bean) | ||||
| 	return err | ||||
| } | ||||
|  | ||||
| @ -77,7 +77,7 @@ func (err ErrNameCharsNotAllowed) Unwrap() error { | ||||
| func IsUsableName(reservedNames, reservedPatterns []string, name string) error { | ||||
| 	name = strings.TrimSpace(strings.ToLower(name)) | ||||
| 	if utf8.RuneCountInString(name) == 0 { | ||||
| 		return util.SilentWrap{Message: "name is empty", Err: util.ErrInvalidArgument} | ||||
| 		return util.NewInvalidArgumentErrorf("name is empty") | ||||
| 	} | ||||
| 
 | ||||
| 	for i := range reservedNames { | ||||
|  | ||||
| @ -595,6 +595,9 @@ func GetIssueByID(ctx context.Context, id int64) (*Issue, error) { | ||||
| // If keepOrder is true, the order of the returned issues will be the same as the given IDs. | ||||
| func GetIssuesByIDs(ctx context.Context, issueIDs []int64, keepOrder ...bool) (IssueList, error) { | ||||
| 	issues := make([]*Issue, 0, len(issueIDs)) | ||||
| 	if len(issueIDs) == 0 { | ||||
| 		return issues, nil | ||||
| 	} | ||||
| 
 | ||||
| 	if err := db.GetEngine(ctx).In("id", issueIDs).Find(&issues); err != nil { | ||||
| 		return nil, err | ||||
|  | ||||
| @ -299,6 +299,9 @@ func GetLabelByID(ctx context.Context, labelID int64) (*Label, error) { | ||||
| // GetLabelsByIDs returns a list of labels by IDs | ||||
| func GetLabelsByIDs(ctx context.Context, labelIDs []int64, cols ...string) ([]*Label, error) { | ||||
| 	labels := make([]*Label, 0, len(labelIDs)) | ||||
| 	if len(labelIDs) == 0 { | ||||
| 		return labels, nil | ||||
| 	} | ||||
| 	return labels, db.GetEngine(ctx).Table("label"). | ||||
| 		In("id", labelIDs). | ||||
| 		Asc("name"). | ||||
| @ -375,6 +378,9 @@ func BuildLabelNamesIssueIDsCondition(labelNames []string) *builder.Builder { | ||||
| // it silently ignores label IDs that do not belong to the repository. | ||||
| func GetLabelsInRepoByIDs(ctx context.Context, repoID int64, labelIDs []int64) ([]*Label, error) { | ||||
| 	labels := make([]*Label, 0, len(labelIDs)) | ||||
| 	if len(labelIDs) == 0 { | ||||
| 		return labels, nil | ||||
| 	} | ||||
| 	return labels, db.GetEngine(ctx). | ||||
| 		Where("repo_id = ?", repoID). | ||||
| 		In("id", labelIDs). | ||||
| @ -447,6 +453,9 @@ func GetLabelInOrgByID(ctx context.Context, orgID, labelID int64) (*Label, error | ||||
| // it silently ignores label IDs that do not belong to the organization. | ||||
| func GetLabelsInOrgByIDs(ctx context.Context, orgID int64, labelIDs []int64) ([]*Label, error) { | ||||
| 	labels := make([]*Label, 0, len(labelIDs)) | ||||
| 	if len(labelIDs) == 0 { | ||||
| 		return labels, nil | ||||
| 	} | ||||
| 	return labels, db.GetEngine(ctx). | ||||
| 		Where("org_id = ?", orgID). | ||||
| 		In("id", labelIDs). | ||||
|  | ||||
| @ -28,11 +28,16 @@ type PullRequestsOptions struct { | ||||
| 	Labels      []int64 | ||||
| 	MilestoneID int64 | ||||
| 	PosterID    int64 | ||||
| 	BaseBranch  string | ||||
| } | ||||
| 
 | ||||
| func listPullRequestStatement(ctx context.Context, baseRepoID int64, opts *PullRequestsOptions) *xorm.Session { | ||||
| 	sess := db.GetEngine(ctx).Where("pull_request.base_repo_id=?", baseRepoID) | ||||
| 
 | ||||
| 	if opts.BaseBranch != "" { | ||||
| 		sess.And("pull_request.base_branch=?", opts.BaseBranch) | ||||
| 	} | ||||
| 
 | ||||
| 	sess.Join("INNER", "issue", "pull_request.issue_id = issue.id") | ||||
| 	switch opts.State { | ||||
| 	case "closed", "open": | ||||
| @ -56,7 +61,7 @@ func listPullRequestStatement(ctx context.Context, baseRepoID int64, opts *PullR | ||||
| } | ||||
| 
 | ||||
| // GetUnmergedPullRequestsByHeadInfo returns all pull requests that are open and has not been merged | ||||
| func GetUnmergedPullRequestsByHeadInfo(ctx context.Context, repoID int64, branch string) ([]*PullRequest, error) { | ||||
| func GetUnmergedPullRequestsByHeadInfo(ctx context.Context, repoID int64, branch string) (PullRequestList, error) { | ||||
| 	prs := make([]*PullRequest, 0, 2) | ||||
| 	sess := db.GetEngine(ctx). | ||||
| 		Join("INNER", "issue", "issue.id = pull_request.issue_id"). | ||||
| @ -111,7 +116,7 @@ func HasUnmergedPullRequestsByHeadInfo(ctx context.Context, repoID int64, branch | ||||
| 
 | ||||
| // GetUnmergedPullRequestsByBaseInfo returns all pull requests that are open and has not been merged | ||||
| // by given base information (repo and branch). | ||||
| func GetUnmergedPullRequestsByBaseInfo(ctx context.Context, repoID int64, branch string) ([]*PullRequest, error) { | ||||
| func GetUnmergedPullRequestsByBaseInfo(ctx context.Context, repoID int64, branch string) (PullRequestList, error) { | ||||
| 	prs := make([]*PullRequest, 0, 2) | ||||
| 	return prs, db.GetEngine(ctx). | ||||
| 		Where("base_repo_id=? AND base_branch=? AND has_merged=? AND issue.is_closed=?", | ||||
|  | ||||
| @ -16,11 +16,11 @@ import ( | ||||
| func TestPullRequestList_LoadAttributes(t *testing.T) { | ||||
| 	assert.NoError(t, unittest.PrepareTestDatabase()) | ||||
| 
 | ||||
| 	prs := []*issues_model.PullRequest{ | ||||
| 	prs := issues_model.PullRequestList{ | ||||
| 		unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1}), | ||||
| 		unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2}), | ||||
| 	} | ||||
| 	assert.NoError(t, issues_model.PullRequestList(prs).LoadAttributes(db.DefaultContext)) | ||||
| 	assert.NoError(t, prs.LoadAttributes(db.DefaultContext)) | ||||
| 	for _, pr := range prs { | ||||
| 		assert.NotNil(t, pr.Issue) | ||||
| 		assert.Equal(t, pr.IssueID, pr.Issue.ID) | ||||
| @ -32,11 +32,11 @@ func TestPullRequestList_LoadAttributes(t *testing.T) { | ||||
| func TestPullRequestList_LoadReviewCommentsCounts(t *testing.T) { | ||||
| 	assert.NoError(t, unittest.PrepareTestDatabase()) | ||||
| 
 | ||||
| 	prs := []*issues_model.PullRequest{ | ||||
| 	prs := issues_model.PullRequestList{ | ||||
| 		unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1}), | ||||
| 		unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2}), | ||||
| 	} | ||||
| 	reviewComments, err := issues_model.PullRequestList(prs).LoadReviewCommentsCounts(db.DefaultContext) | ||||
| 	reviewComments, err := prs.LoadReviewCommentsCounts(db.DefaultContext) | ||||
| 	assert.NoError(t, err) | ||||
| 	assert.Len(t, reviewComments, 2) | ||||
| 	for _, pr := range prs { | ||||
| @ -47,11 +47,11 @@ func TestPullRequestList_LoadReviewCommentsCounts(t *testing.T) { | ||||
| func TestPullRequestList_LoadReviews(t *testing.T) { | ||||
| 	assert.NoError(t, unittest.PrepareTestDatabase()) | ||||
| 
 | ||||
| 	prs := []*issues_model.PullRequest{ | ||||
| 	prs := issues_model.PullRequestList{ | ||||
| 		unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1}), | ||||
| 		unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2}), | ||||
| 	} | ||||
| 	reviewList, err := issues_model.PullRequestList(prs).LoadReviews(db.DefaultContext) | ||||
| 	reviewList, err := prs.LoadReviews(db.DefaultContext) | ||||
| 	assert.NoError(t, err) | ||||
| 	// 1, 7, 8, 9, 10, 22 | ||||
| 	assert.Len(t, reviewList, 6) | ||||
|  | ||||
| @ -374,6 +374,7 @@ func prepareMigrationTasks() []*migration { | ||||
| 		// Gitea 1.23.0-rc0 ends at migration ID number 311 (database version 312) | ||||
| 		newMigration(312, "Add DeleteBranchAfterMerge to AutoMerge", v1_24.AddDeleteBranchAfterMergeForAutoMerge), | ||||
| 		newMigration(313, "Move PinOrder from issue table to a new table issue_pin", v1_24.MovePinOrderToTableIssuePin), | ||||
| 		newMigration(314, "Update OwnerID as zero for repository level action tables", v1_24.UpdateOwnerIDOfRepoLevelActionsTables), | ||||
| 	} | ||||
| 	return preparedMigrations | ||||
| } | ||||
|  | ||||
| @ -82,17 +82,17 @@ func FixMergeBase(x *xorm.Engine) error { | ||||
| 
 | ||||
| 			if !pr.HasMerged { | ||||
| 				var err error | ||||
| 				pr.MergeBase, _, err = git.NewCommand(git.DefaultContext, "merge-base").AddDashesAndList(pr.BaseBranch, gitRefName).RunStdString(&git.RunOpts{Dir: repoPath}) | ||||
| 				pr.MergeBase, _, err = git.NewCommand("merge-base").AddDashesAndList(pr.BaseBranch, gitRefName).RunStdString(git.DefaultContext, &git.RunOpts{Dir: repoPath}) | ||||
| 				if err != nil { | ||||
| 					var err2 error | ||||
| 					pr.MergeBase, _, err2 = git.NewCommand(git.DefaultContext, "rev-parse").AddDynamicArguments(git.BranchPrefix + pr.BaseBranch).RunStdString(&git.RunOpts{Dir: repoPath}) | ||||
| 					pr.MergeBase, _, err2 = git.NewCommand("rev-parse").AddDynamicArguments(git.BranchPrefix+pr.BaseBranch).RunStdString(git.DefaultContext, &git.RunOpts{Dir: repoPath}) | ||||
| 					if err2 != nil { | ||||
| 						log.Error("Unable to get merge base for PR ID %d, Index %d in %s/%s. Error: %v & %v", pr.ID, pr.Index, baseRepo.OwnerName, baseRepo.Name, err, err2) | ||||
| 						continue | ||||
| 					} | ||||
| 				} | ||||
| 			} else { | ||||
| 				parentsString, _, err := git.NewCommand(git.DefaultContext, "rev-list", "--parents", "-n", "1").AddDynamicArguments(pr.MergedCommitID).RunStdString(&git.RunOpts{Dir: repoPath}) | ||||
| 				parentsString, _, err := git.NewCommand("rev-list", "--parents", "-n", "1").AddDynamicArguments(pr.MergedCommitID).RunStdString(git.DefaultContext, &git.RunOpts{Dir: repoPath}) | ||||
| 				if err != nil { | ||||
| 					log.Error("Unable to get parents for merged PR ID %d, Index %d in %s/%s. Error: %v", pr.ID, pr.Index, baseRepo.OwnerName, baseRepo.Name, err) | ||||
| 					continue | ||||
| @ -104,9 +104,9 @@ func FixMergeBase(x *xorm.Engine) error { | ||||
| 
 | ||||
| 				refs := append([]string{}, parents[1:]...) | ||||
| 				refs = append(refs, gitRefName) | ||||
| 				cmd := git.NewCommand(git.DefaultContext, "merge-base").AddDashesAndList(refs...) | ||||
| 				cmd := git.NewCommand("merge-base").AddDashesAndList(refs...) | ||||
| 
 | ||||
| 				pr.MergeBase, _, err = cmd.RunStdString(&git.RunOpts{Dir: repoPath}) | ||||
| 				pr.MergeBase, _, err = cmd.RunStdString(git.DefaultContext, &git.RunOpts{Dir: repoPath}) | ||||
| 				if err != nil { | ||||
| 					log.Error("Unable to get merge base for merged PR ID %d, Index %d in %s/%s. Error: %v", pr.ID, pr.Index, baseRepo.OwnerName, baseRepo.Name, err) | ||||
| 					continue | ||||
|  | ||||
| @ -79,7 +79,7 @@ func RefixMergeBase(x *xorm.Engine) error { | ||||
| 
 | ||||
| 			gitRefName := fmt.Sprintf("refs/pull/%d/head", pr.Index) | ||||
| 
 | ||||
| 			parentsString, _, err := git.NewCommand(git.DefaultContext, "rev-list", "--parents", "-n", "1").AddDynamicArguments(pr.MergedCommitID).RunStdString(&git.RunOpts{Dir: repoPath}) | ||||
| 			parentsString, _, err := git.NewCommand("rev-list", "--parents", "-n", "1").AddDynamicArguments(pr.MergedCommitID).RunStdString(git.DefaultContext, &git.RunOpts{Dir: repoPath}) | ||||
| 			if err != nil { | ||||
| 				log.Error("Unable to get parents for merged PR ID %d, Index %d in %s/%s. Error: %v", pr.ID, pr.Index, baseRepo.OwnerName, baseRepo.Name, err) | ||||
| 				continue | ||||
| @ -92,9 +92,9 @@ func RefixMergeBase(x *xorm.Engine) error { | ||||
| 			// we should recalculate | ||||
| 			refs := append([]string{}, parents[1:]...) | ||||
| 			refs = append(refs, gitRefName) | ||||
| 			cmd := git.NewCommand(git.DefaultContext, "merge-base").AddDashesAndList(refs...) | ||||
| 			cmd := git.NewCommand("merge-base").AddDashesAndList(refs...) | ||||
| 
 | ||||
| 			pr.MergeBase, _, err = cmd.RunStdString(&git.RunOpts{Dir: repoPath}) | ||||
| 			pr.MergeBase, _, err = cmd.RunStdString(git.DefaultContext, &git.RunOpts{Dir: repoPath}) | ||||
| 			if err != nil { | ||||
| 				log.Error("Unable to get merge base for merged PR ID %d, Index %d in %s/%s. Error: %v", pr.ID, pr.Index, baseRepo.OwnerName, baseRepo.Name, err) | ||||
| 				continue | ||||
|  | ||||
							
								
								
									
										19
									
								
								models/migrations/v1_24/v314.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								models/migrations/v1_24/v314.go
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,19 @@ | ||||
| // Copyright 2025 The Gitea Authors. All rights reserved. | ||||
| // SPDX-License-Identifier: MIT | ||||
| 
 | ||||
| package v1_24 //nolint | ||||
| 
 | ||||
| import ( | ||||
| 	"xorm.io/xorm" | ||||
| ) | ||||
| 
 | ||||
| func UpdateOwnerIDOfRepoLevelActionsTables(x *xorm.Engine) error { | ||||
| 	if _, err := x.Exec("UPDATE `action_runner` SET `owner_id` = 0 WHERE `repo_id` > 0 AND `owner_id` > 0"); err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	if _, err := x.Exec("UPDATE `action_variable` SET `owner_id` = 0 WHERE `repo_id` > 0 AND `owner_id` > 0"); err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	_, err := x.Exec("UPDATE `secret` SET `owner_id` = 0 WHERE `repo_id` > 0 AND `owner_id` > 0") | ||||
| 	return err | ||||
| } | ||||
| @ -133,5 +133,8 @@ func GetTeamsByOrgIDs(ctx context.Context, orgIDs []int64) (TeamList, error) { | ||||
| 
 | ||||
| func GetTeamsByIDs(ctx context.Context, teamIDs []int64) (map[int64]*Team, error) { | ||||
| 	teams := make(map[int64]*Team, len(teamIDs)) | ||||
| 	if len(teamIDs) == 0 { | ||||
| 		return teams, nil | ||||
| 	} | ||||
| 	return teams, db.GetEngine(ctx).Where(builder.In("`id`", teamIDs)).Find(&teams) | ||||
| } | ||||
|  | ||||
| @ -110,9 +110,12 @@ func GetPackageDescriptor(ctx context.Context, pv *PackageVersion) (*PackageDesc | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 	repository, err := repo_model.GetRepositoryByID(ctx, p.RepoID) | ||||
| 	if err != nil && !repo_model.IsErrRepoNotExist(err) { | ||||
| 		return nil, err | ||||
| 	var repository *repo_model.Repository | ||||
| 	if p.RepoID > 0 { | ||||
| 		repository, err = repo_model.GetRepositoryByID(ctx, p.RepoID) | ||||
| 		if err != nil && !repo_model.IsErrRepoNotExist(err) { | ||||
| 			return nil, err | ||||
| 		} | ||||
| 	} | ||||
| 	creator, err := user_model.GetUserByID(ctx, pv.CreatorID) | ||||
| 	if err != nil { | ||||
|  | ||||
| @ -336,6 +336,9 @@ func UpdateColumnSorting(ctx context.Context, cl ColumnList) error { | ||||
| 
 | ||||
| func GetColumnsByIDs(ctx context.Context, projectID int64, columnsIDs []int64) (ColumnList, error) { | ||||
| 	columns := make([]*Column, 0, 5) | ||||
| 	if len(columnsIDs) == 0 { | ||||
| 		return columns, nil | ||||
| 	} | ||||
| 	if err := db.GetEngine(ctx). | ||||
| 		Where("project_id =?", projectID). | ||||
| 		In("id", columnsIDs). | ||||
|  | ||||
| @ -50,15 +50,15 @@ func (archiver *RepoArchiver) RelativePath() string { | ||||
| func repoArchiverForRelativePath(relativePath string) (*RepoArchiver, error) { | ||||
| 	parts := strings.SplitN(relativePath, "/", 3) | ||||
| 	if len(parts) != 3 { | ||||
| 		return nil, util.SilentWrap{Message: fmt.Sprintf("invalid storage path: %s", relativePath), Err: util.ErrInvalidArgument} | ||||
| 		return nil, util.NewInvalidArgumentErrorf("invalid storage path: must have 3 parts") | ||||
| 	} | ||||
| 	repoID, err := strconv.ParseInt(parts[0], 10, 64) | ||||
| 	if err != nil { | ||||
| 		return nil, util.SilentWrap{Message: fmt.Sprintf("invalid storage path: %s", relativePath), Err: util.ErrInvalidArgument} | ||||
| 		return nil, util.NewInvalidArgumentErrorf("invalid storage path: invalid repo id") | ||||
| 	} | ||||
| 	commitID, archiveType := git.SplitArchiveNameType(parts[2]) | ||||
| 	if archiveType == git.ArchiveUnknown { | ||||
| 		return nil, util.SilentWrap{Message: fmt.Sprintf("invalid storage path: %s", relativePath), Err: util.ErrInvalidArgument} | ||||
| 		return nil, util.NewInvalidArgumentErrorf("invalid storage path: invalid archive type") | ||||
| 	} | ||||
| 	return &RepoArchiver{RepoID: repoID, CommitID: commitID, Type: archiveType}, nil | ||||
| } | ||||
|  | ||||
| @ -646,13 +646,15 @@ func (repo *Repository) DescriptionHTML(ctx context.Context) template.HTML { | ||||
| type CloneLink struct { | ||||
| 	SSH   string | ||||
| 	HTTPS string | ||||
| 	Tea   string | ||||
| } | ||||
| 
 | ||||
| // ComposeHTTPSCloneURL returns HTTPS clone URL based on given owner and repository name. | ||||
| // ComposeHTTPSCloneURL returns HTTPS clone URL based on the given owner and repository name. | ||||
| func ComposeHTTPSCloneURL(ctx context.Context, owner, repo string) string { | ||||
| 	return fmt.Sprintf("%s%s/%s.git", httplib.GuessCurrentAppURL(ctx), url.PathEscape(owner), url.PathEscape(repo)) | ||||
| } | ||||
| 
 | ||||
| // ComposeSSHCloneURL returns SSH clone URL based on the given owner and repository name. | ||||
| func ComposeSSHCloneURL(doer *user_model.User, ownerName, repoName string) string { | ||||
| 	sshUser := setting.SSH.User | ||||
| 	sshDomain := setting.SSH.Domain | ||||
| @ -686,11 +688,17 @@ func ComposeSSHCloneURL(doer *user_model.User, ownerName, repoName string) strin | ||||
| 	return fmt.Sprintf("%s@%s:%s/%s.git", sshUser, sshHost, url.PathEscape(ownerName), url.PathEscape(repoName)) | ||||
| } | ||||
| 
 | ||||
| // ComposeTeaCloneCommand returns Tea CLI clone command based on the given owner and repository name. | ||||
| func ComposeTeaCloneCommand(ctx context.Context, owner, repo string) string { | ||||
| 	return fmt.Sprintf("tea clone %s/%s", url.PathEscape(owner), url.PathEscape(repo)) | ||||
| } | ||||
| 
 | ||||
| func (repo *Repository) cloneLink(ctx context.Context, doer *user_model.User, repoPathName string) *CloneLink { | ||||
| 	cl := new(CloneLink) | ||||
| 	cl.SSH = ComposeSSHCloneURL(doer, repo.OwnerName, repoPathName) | ||||
| 	cl.HTTPS = ComposeHTTPSCloneURL(ctx, repo.OwnerName, repoPathName) | ||||
| 	return cl | ||||
| 	return &CloneLink{ | ||||
| 		SSH:   ComposeSSHCloneURL(doer, repo.OwnerName, repoPathName), | ||||
| 		HTTPS: ComposeHTTPSCloneURL(ctx, repo.OwnerName, repoPathName), | ||||
| 		Tea:   ComposeTeaCloneCommand(ctx, repo.OwnerName, repoPathName), | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| // CloneLink returns clone URLs of repository. | ||||
| @ -831,6 +839,9 @@ func GetRepositoryByID(ctx context.Context, id int64) (*Repository, error) { | ||||
| // GetRepositoriesMapByIDs returns the repositories by given id slice. | ||||
| func GetRepositoriesMapByIDs(ctx context.Context, ids []int64) (map[int64]*Repository, error) { | ||||
| 	repos := make(map[int64]*Repository, len(ids)) | ||||
| 	if len(ids) == 0 { | ||||
| 		return repos, nil | ||||
| 	} | ||||
| 	return repos, db.GetEngine(ctx).In("id", ids).Find(&repos) | ||||
| } | ||||
| 
 | ||||
|  | ||||
| @ -21,11 +21,6 @@ import ( | ||||
| 	"xorm.io/builder" | ||||
| ) | ||||
| 
 | ||||
| // FindReposMapByIDs find repos as map | ||||
| func FindReposMapByIDs(ctx context.Context, repoIDs []int64, res map[int64]*Repository) error { | ||||
| 	return db.GetEngine(ctx).In("id", repoIDs).Find(&res) | ||||
| } | ||||
| 
 | ||||
| // RepositoryListDefaultPageSize is the default number of repositories | ||||
| // to load in memory when running administrative tasks on all (or almost | ||||
| // all) of them. | ||||
|  | ||||
| @ -165,3 +165,17 @@ func GetSecretsOfTask(ctx context.Context, task *actions_model.ActionTask) (map[ | ||||
| 
 | ||||
| 	return secrets, nil | ||||
| } | ||||
| 
 | ||||
| func CountWrongRepoLevelSecrets(ctx context.Context) (int64, error) { | ||||
| 	var result int64 | ||||
| 	_, err := db.GetEngine(ctx).SQL("SELECT count(`id`) FROM `secret` WHERE `repo_id` > 0 AND `owner_id` > 0").Get(&result) | ||||
| 	return result, err | ||||
| } | ||||
| 
 | ||||
| func UpdateWrongRepoLevelSecrets(ctx context.Context) (int64, error) { | ||||
| 	result, err := db.GetEngine(ctx).Exec("UPDATE `secret` SET `owner_id` = 0 WHERE `repo_id` > 0 AND `owner_id` > 0") | ||||
| 	if err != nil { | ||||
| 		return 0, err | ||||
| 	} | ||||
| 	return result.RowsAffected() | ||||
| } | ||||
|  | ||||
| @ -34,7 +34,7 @@ func SetMustChangePassword(ctx context.Context, all, mustChangePassword bool, in | ||||
| 	if !all { | ||||
| 		include = sliceTrimSpaceDropEmpty(include) | ||||
| 		if len(include) == 0 { | ||||
| 			return 0, util.NewSilentWrapErrorf(util.ErrInvalidArgument, "no users to include provided") | ||||
| 			return 0, util.ErrorWrap(util.ErrInvalidArgument, "no users to include provided") | ||||
| 		} | ||||
| 
 | ||||
| 		cond = cond.And(builder.In("lower_name", include)) | ||||
|  | ||||
| @ -11,6 +11,10 @@ import ( | ||||
| 
 | ||||
| func GetUsersMapByIDs(ctx context.Context, userIDs []int64) (map[int64]*User, error) { | ||||
| 	userMaps := make(map[int64]*User, len(userIDs)) | ||||
| 	if len(userIDs) == 0 { | ||||
| 		return userMaps, nil | ||||
| 	} | ||||
| 
 | ||||
| 	left := len(userIDs) | ||||
| 	for left > 0 { | ||||
| 		limit := db.DefaultMaxInSize | ||||
|  | ||||
| @ -29,8 +29,8 @@ type WriteCloserError interface { | ||||
| // This is needed otherwise the git cat-file will hang for invalid repositories. | ||||
| func ensureValidGitRepository(ctx context.Context, repoPath string) error { | ||||
| 	stderr := strings.Builder{} | ||||
| 	err := NewCommand(ctx, "rev-parse"). | ||||
| 		Run(&RunOpts{ | ||||
| 	err := NewCommand("rev-parse"). | ||||
| 		Run(ctx, &RunOpts{ | ||||
| 			Dir:    repoPath, | ||||
| 			Stderr: &stderr, | ||||
| 		}) | ||||
| @ -61,8 +61,8 @@ func catFileBatchCheck(ctx context.Context, repoPath string) (WriteCloserError, | ||||
| 
 | ||||
| 	go func() { | ||||
| 		stderr := strings.Builder{} | ||||
| 		err := NewCommand(ctx, "cat-file", "--batch-check"). | ||||
| 			Run(&RunOpts{ | ||||
| 		err := NewCommand("cat-file", "--batch-check"). | ||||
| 			Run(ctx, &RunOpts{ | ||||
| 				Dir:    repoPath, | ||||
| 				Stdin:  batchStdinReader, | ||||
| 				Stdout: batchStdoutWriter, | ||||
| @ -109,8 +109,8 @@ func catFileBatch(ctx context.Context, repoPath string) (WriteCloserError, *bufi | ||||
| 
 | ||||
| 	go func() { | ||||
| 		stderr := strings.Builder{} | ||||
| 		err := NewCommand(ctx, "cat-file", "--batch"). | ||||
| 			Run(&RunOpts{ | ||||
| 		err := NewCommand("cat-file", "--batch"). | ||||
| 			Run(ctx, &RunOpts{ | ||||
| 				Dir:    repoPath, | ||||
| 				Stdin:  batchStdinReader, | ||||
| 				Stdout: batchStdoutWriter, | ||||
|  | ||||
| @ -135,7 +135,7 @@ func CreateBlameReader(ctx context.Context, objectFormat ObjectFormat, repoPath | ||||
| 		ignoreRevsFile = tryCreateBlameIgnoreRevsFile(commit) | ||||
| 	} | ||||
| 
 | ||||
| 	cmd := NewCommandContextNoGlobals(ctx, "blame", "--porcelain") | ||||
| 	cmd := NewCommandNoGlobals("blame", "--porcelain") | ||||
| 	if ignoreRevsFile != nil { | ||||
| 		// Possible improvement: use --ignore-revs-file /dev/stdin on unix | ||||
| 		// There is no equivalent on Windows. May be implemented if Gitea uses an external git backend. | ||||
| @ -155,7 +155,7 @@ func CreateBlameReader(ctx context.Context, objectFormat ObjectFormat, repoPath | ||||
| 	go func() { | ||||
| 		stderr := bytes.Buffer{} | ||||
| 		// TODO: it doesn't work for directories (the directories shouldn't be "blamed"), and the "err" should be returned by "Read" but not by "Close" | ||||
| 		err := cmd.Run(&RunOpts{ | ||||
| 		err := cmd.Run(ctx, &RunOpts{ | ||||
| 			UseContextTimeout: true, | ||||
| 			Dir:               repoPath, | ||||
| 			Stdout:            stdout, | ||||
|  | ||||
| @ -44,7 +44,6 @@ const DefaultLocale = "C" | ||||
| type Command struct { | ||||
| 	prog             string | ||||
| 	args             []string | ||||
| 	parentContext    context.Context | ||||
| 	globalArgsLength int | ||||
| 	brokenArgs       []string | ||||
| } | ||||
| @ -82,7 +81,7 @@ func (c *Command) LogString() string { | ||||
| 
 | ||||
| // NewCommand creates and returns a new Git Command based on given command and arguments. | ||||
| // Each argument should be safe to be trusted. User-provided arguments should be passed to AddDynamicArguments instead. | ||||
| func NewCommand(ctx context.Context, args ...internal.CmdArg) *Command { | ||||
| func NewCommand(args ...internal.CmdArg) *Command { | ||||
| 	// Make an explicit copy of globalCommandArgs, otherwise append might overwrite it | ||||
| 	cargs := make([]string, 0, len(globalCommandArgs)+len(args)) | ||||
| 	for _, arg := range globalCommandArgs { | ||||
| @ -94,31 +93,23 @@ func NewCommand(ctx context.Context, args ...internal.CmdArg) *Command { | ||||
| 	return &Command{ | ||||
| 		prog:             GitExecutable, | ||||
| 		args:             cargs, | ||||
| 		parentContext:    ctx, | ||||
| 		globalArgsLength: len(globalCommandArgs), | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| // NewCommandContextNoGlobals creates and returns a new Git Command based on given command and arguments only with the specify args and don't care global command args | ||||
| // NewCommandNoGlobals creates and returns a new Git Command based on given command and arguments only with the specified args and don't use global command args | ||||
| // Each argument should be safe to be trusted. User-provided arguments should be passed to AddDynamicArguments instead. | ||||
| func NewCommandContextNoGlobals(ctx context.Context, args ...internal.CmdArg) *Command { | ||||
| func NewCommandNoGlobals(args ...internal.CmdArg) *Command { | ||||
| 	cargs := make([]string, 0, len(args)) | ||||
| 	for _, arg := range args { | ||||
| 		cargs = append(cargs, string(arg)) | ||||
| 	} | ||||
| 	return &Command{ | ||||
| 		prog:          GitExecutable, | ||||
| 		args:          cargs, | ||||
| 		parentContext: ctx, | ||||
| 		prog: GitExecutable, | ||||
| 		args: cargs, | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| // SetParentContext sets the parent context for this command | ||||
| func (c *Command) SetParentContext(ctx context.Context) *Command { | ||||
| 	c.parentContext = ctx | ||||
| 	return c | ||||
| } | ||||
| 
 | ||||
| // isSafeArgumentValue checks if the argument is safe to be used as a value (not an option) | ||||
| func isSafeArgumentValue(s string) bool { | ||||
| 	return s == "" || s[0] != '-' | ||||
| @ -277,11 +268,11 @@ func CommonCmdServEnvs() []string { | ||||
| var ErrBrokenCommand = errors.New("git command is broken") | ||||
| 
 | ||||
| // Run runs the command with the RunOpts | ||||
| func (c *Command) Run(opts *RunOpts) error { | ||||
| 	return c.run(1, opts) | ||||
| func (c *Command) Run(ctx context.Context, opts *RunOpts) error { | ||||
| 	return c.run(ctx, 1, opts) | ||||
| } | ||||
| 
 | ||||
| func (c *Command) run(skip int, opts *RunOpts) error { | ||||
| func (c *Command) run(ctx context.Context, skip int, opts *RunOpts) error { | ||||
| 	if len(c.brokenArgs) != 0 { | ||||
| 		log.Error("git command is broken: %s, broken args: %s", c.LogString(), strings.Join(c.brokenArgs, " ")) | ||||
| 		return ErrBrokenCommand | ||||
| @ -305,19 +296,18 @@ func (c *Command) run(skip int, opts *RunOpts) error { | ||||
| 	desc := fmt.Sprintf("git.Run(by:%s, repo:%s): %s", callerInfo, logArgSanitize(opts.Dir), cmdLogString) | ||||
| 	log.Debug("git.Command: %s", desc) | ||||
| 
 | ||||
| 	_, span := gtprof.GetTracer().Start(c.parentContext, gtprof.TraceSpanGitRun) | ||||
| 	_, span := gtprof.GetTracer().Start(ctx, gtprof.TraceSpanGitRun) | ||||
| 	defer span.End() | ||||
| 	span.SetAttributeString(gtprof.TraceAttrFuncCaller, callerInfo) | ||||
| 	span.SetAttributeString(gtprof.TraceAttrGitCommand, cmdLogString) | ||||
| 
 | ||||
| 	var ctx context.Context | ||||
| 	var cancel context.CancelFunc | ||||
| 	var finished context.CancelFunc | ||||
| 
 | ||||
| 	if opts.UseContextTimeout { | ||||
| 		ctx, cancel, finished = process.GetManager().AddContext(c.parentContext, desc) | ||||
| 		ctx, cancel, finished = process.GetManager().AddContext(ctx, desc) | ||||
| 	} else { | ||||
| 		ctx, cancel, finished = process.GetManager().AddContextTimeout(c.parentContext, timeout, desc) | ||||
| 		ctx, cancel, finished = process.GetManager().AddContextTimeout(ctx, timeout, desc) | ||||
| 	} | ||||
| 	defer finished() | ||||
| 
 | ||||
| @ -410,8 +400,8 @@ func IsErrorExitCode(err error, code int) bool { | ||||
| } | ||||
| 
 | ||||
| // RunStdString runs the command with options and returns stdout/stderr as string. and store stderr to returned error (err combined with stderr). | ||||
| func (c *Command) RunStdString(opts *RunOpts) (stdout, stderr string, runErr RunStdError) { | ||||
| 	stdoutBytes, stderrBytes, err := c.runStdBytes(opts) | ||||
| func (c *Command) RunStdString(ctx context.Context, opts *RunOpts) (stdout, stderr string, runErr RunStdError) { | ||||
| 	stdoutBytes, stderrBytes, err := c.runStdBytes(ctx, opts) | ||||
| 	stdout = util.UnsafeBytesToString(stdoutBytes) | ||||
| 	stderr = util.UnsafeBytesToString(stderrBytes) | ||||
| 	if err != nil { | ||||
| @ -422,11 +412,11 @@ func (c *Command) RunStdString(opts *RunOpts) (stdout, stderr string, runErr Run | ||||
| } | ||||
| 
 | ||||
| // RunStdBytes runs the command with options and returns stdout/stderr as bytes. and store stderr to returned error (err combined with stderr). | ||||
| func (c *Command) RunStdBytes(opts *RunOpts) (stdout, stderr []byte, runErr RunStdError) { | ||||
| 	return c.runStdBytes(opts) | ||||
| func (c *Command) RunStdBytes(ctx context.Context, opts *RunOpts) (stdout, stderr []byte, runErr RunStdError) { | ||||
| 	return c.runStdBytes(ctx, opts) | ||||
| } | ||||
| 
 | ||||
| func (c *Command) runStdBytes(opts *RunOpts) (stdout, stderr []byte, runErr RunStdError) { | ||||
| func (c *Command) runStdBytes(ctx context.Context, opts *RunOpts) (stdout, stderr []byte, runErr RunStdError) { | ||||
| 	if opts == nil { | ||||
| 		opts = &RunOpts{} | ||||
| 	} | ||||
| @ -449,7 +439,7 @@ func (c *Command) runStdBytes(opts *RunOpts) (stdout, stderr []byte, runErr RunS | ||||
| 		PipelineFunc:      opts.PipelineFunc, | ||||
| 	} | ||||
| 
 | ||||
| 	err := c.run(2, newOpts) | ||||
| 	err := c.run(ctx, 2, newOpts) | ||||
| 	stderr = stderrBuf.Bytes() | ||||
| 	if err != nil { | ||||
| 		return nil, stderr, &runStdError{err: err, stderr: util.UnsafeBytesToString(stderr)} | ||||
|  | ||||
| @ -15,9 +15,9 @@ func TestRunWithContextNoTimeout(t *testing.T) { | ||||
| 	maxLoops := 10 | ||||
| 
 | ||||
| 	// 'git --version' does not block so it must be finished before the timeout triggered. | ||||
| 	cmd := NewCommand(t.Context(), "--version") | ||||
| 	cmd := NewCommand("--version") | ||||
| 	for i := 0; i < maxLoops; i++ { | ||||
| 		if err := cmd.Run(&RunOpts{}); err != nil { | ||||
| 		if err := cmd.Run(t.Context(), &RunOpts{}); err != nil { | ||||
| 			t.Fatal(err) | ||||
| 		} | ||||
| 	} | ||||
| @ -27,9 +27,9 @@ func TestRunWithContextTimeout(t *testing.T) { | ||||
| 	maxLoops := 10 | ||||
| 
 | ||||
| 	// 'git hash-object --stdin' blocks on stdin so we can have the timeout triggered. | ||||
| 	cmd := NewCommand(t.Context(), "hash-object", "--stdin") | ||||
| 	cmd := NewCommand("hash-object", "--stdin") | ||||
| 	for i := 0; i < maxLoops; i++ { | ||||
| 		if err := cmd.Run(&RunOpts{Timeout: 1 * time.Millisecond}); err != nil { | ||||
| 		if err := cmd.Run(t.Context(), &RunOpts{Timeout: 1 * time.Millisecond}); err != nil { | ||||
| 			if err != context.DeadlineExceeded { | ||||
| 				t.Fatalf("Testing %d/%d: %v", i, maxLoops, err) | ||||
| 			} | ||||
|  | ||||
| @ -10,14 +10,14 @@ import ( | ||||
| ) | ||||
| 
 | ||||
| func TestRunWithContextStd(t *testing.T) { | ||||
| 	cmd := NewCommand(t.Context(), "--version") | ||||
| 	stdout, stderr, err := cmd.RunStdString(&RunOpts{}) | ||||
| 	cmd := NewCommand("--version") | ||||
| 	stdout, stderr, err := cmd.RunStdString(t.Context(), &RunOpts{}) | ||||
| 	assert.NoError(t, err) | ||||
| 	assert.Empty(t, stderr) | ||||
| 	assert.Contains(t, stdout, "git version") | ||||
| 
 | ||||
| 	cmd = NewCommand(t.Context(), "--no-such-arg") | ||||
| 	stdout, stderr, err = cmd.RunStdString(&RunOpts{}) | ||||
| 	cmd = NewCommand("--no-such-arg") | ||||
| 	stdout, stderr, err = cmd.RunStdString(t.Context(), &RunOpts{}) | ||||
| 	if assert.Error(t, err) { | ||||
| 		assert.Equal(t, stderr, err.Stderr()) | ||||
| 		assert.Contains(t, err.Stderr(), "unknown option:") | ||||
| @ -25,17 +25,17 @@ func TestRunWithContextStd(t *testing.T) { | ||||
| 		assert.Empty(t, stdout) | ||||
| 	} | ||||
| 
 | ||||
| 	cmd = NewCommand(t.Context()) | ||||
| 	cmd = NewCommand() | ||||
| 	cmd.AddDynamicArguments("-test") | ||||
| 	assert.ErrorIs(t, cmd.Run(&RunOpts{}), ErrBrokenCommand) | ||||
| 	assert.ErrorIs(t, cmd.Run(t.Context(), &RunOpts{}), ErrBrokenCommand) | ||||
| 
 | ||||
| 	cmd = NewCommand(t.Context()) | ||||
| 	cmd = NewCommand() | ||||
| 	cmd.AddDynamicArguments("--test") | ||||
| 	assert.ErrorIs(t, cmd.Run(&RunOpts{}), ErrBrokenCommand) | ||||
| 	assert.ErrorIs(t, cmd.Run(t.Context(), &RunOpts{}), ErrBrokenCommand) | ||||
| 
 | ||||
| 	subCmd := "version" | ||||
| 	cmd = NewCommand(t.Context()).AddDynamicArguments(subCmd) // for test purpose only, the sub-command should never be dynamic for production | ||||
| 	stdout, stderr, err = cmd.RunStdString(&RunOpts{}) | ||||
| 	cmd = NewCommand().AddDynamicArguments(subCmd) // for test purpose only, the sub-command should never be dynamic for production | ||||
| 	stdout, stderr, err = cmd.RunStdString(t.Context(), &RunOpts{}) | ||||
| 	assert.NoError(t, err) | ||||
| 	assert.Empty(t, stderr) | ||||
| 	assert.Contains(t, stdout, "git version") | ||||
| @ -53,9 +53,9 @@ func TestGitArgument(t *testing.T) { | ||||
| } | ||||
| 
 | ||||
| func TestCommandString(t *testing.T) { | ||||
| 	cmd := NewCommandContextNoGlobals(t.Context(), "a", "-m msg", "it's a test", `say "hello"`) | ||||
| 	cmd := NewCommandNoGlobals("a", "-m msg", "it's a test", `say "hello"`) | ||||
| 	assert.EqualValues(t, cmd.prog+` a "-m msg" "it's a test" "say \"hello\""`, cmd.LogString()) | ||||
| 
 | ||||
| 	cmd = NewCommandContextNoGlobals(t.Context(), "url: https://a:b@c/", "/root/dir-a/dir-b") | ||||
| 	cmd = NewCommandNoGlobals("url: https://a:b@c/", "/root/dir-a/dir-b") | ||||
| 	assert.EqualValues(t, cmd.prog+` "url: https://sanitized-credential@c/" .../dir-a/dir-b`, cmd.LogString()) | ||||
| } | ||||
|  | ||||
| @ -91,12 +91,12 @@ func AddChanges(repoPath string, all bool, files ...string) error { | ||||
| 
 | ||||
| // AddChangesWithArgs marks local changes to be ready for commit. | ||||
| func AddChangesWithArgs(repoPath string, globalArgs TrustedCmdArgs, all bool, files ...string) error { | ||||
| 	cmd := NewCommandContextNoGlobals(DefaultContext, globalArgs...).AddArguments("add") | ||||
| 	cmd := NewCommandNoGlobals(globalArgs...).AddArguments("add") | ||||
| 	if all { | ||||
| 		cmd.AddArguments("--all") | ||||
| 	} | ||||
| 	cmd.AddDashesAndList(files...) | ||||
| 	_, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	_, _, err := cmd.RunStdString(DefaultContext, &RunOpts{Dir: repoPath}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| @ -118,7 +118,7 @@ func CommitChanges(repoPath string, opts CommitChangesOptions) error { | ||||
| // CommitChangesWithArgs commits local changes with given committer, author and message. | ||||
| // If author is nil, it will be the same as committer. | ||||
| func CommitChangesWithArgs(repoPath string, args TrustedCmdArgs, opts CommitChangesOptions) error { | ||||
| 	cmd := NewCommandContextNoGlobals(DefaultContext, args...) | ||||
| 	cmd := NewCommandNoGlobals(args...) | ||||
| 	if opts.Committer != nil { | ||||
| 		cmd.AddOptionValues("-c", "user.name="+opts.Committer.Name) | ||||
| 		cmd.AddOptionValues("-c", "user.email="+opts.Committer.Email) | ||||
| @ -133,7 +133,7 @@ func CommitChangesWithArgs(repoPath string, args TrustedCmdArgs, opts CommitChan | ||||
| 	} | ||||
| 	cmd.AddOptionFormat("--message=%s", opts.Message) | ||||
| 
 | ||||
| 	_, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	_, _, err := cmd.RunStdString(DefaultContext, &RunOpts{Dir: repoPath}) | ||||
| 	// No stderr but exit status 1 means nothing to commit. | ||||
| 	if err != nil && err.Error() == "exit status 1" { | ||||
| 		return nil | ||||
| @ -143,7 +143,7 @@ func CommitChangesWithArgs(repoPath string, args TrustedCmdArgs, opts CommitChan | ||||
| 
 | ||||
| // AllCommitsCount returns count of all commits in repository | ||||
| func AllCommitsCount(ctx context.Context, repoPath string, hidePRRefs bool, files ...string) (int64, error) { | ||||
| 	cmd := NewCommand(ctx, "rev-list") | ||||
| 	cmd := NewCommand("rev-list") | ||||
| 	if hidePRRefs { | ||||
| 		cmd.AddArguments("--exclude=" + PullPrefix + "*") | ||||
| 	} | ||||
| @ -152,7 +152,7 @@ func AllCommitsCount(ctx context.Context, repoPath string, hidePRRefs bool, file | ||||
| 		cmd.AddDashesAndList(files...) | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	stdout, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		return 0, err | ||||
| 	} | ||||
| @ -170,7 +170,7 @@ type CommitsCountOptions struct { | ||||
| 
 | ||||
| // CommitsCount returns number of total commits of until given revision. | ||||
| func CommitsCount(ctx context.Context, opts CommitsCountOptions) (int64, error) { | ||||
| 	cmd := NewCommand(ctx, "rev-list", "--count") | ||||
| 	cmd := NewCommand("rev-list", "--count") | ||||
| 
 | ||||
| 	cmd.AddDynamicArguments(opts.Revision...) | ||||
| 
 | ||||
| @ -182,7 +182,7 @@ func CommitsCount(ctx context.Context, opts CommitsCountOptions) (int64, error) | ||||
| 		cmd.AddDashesAndList(opts.RelPath...) | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, err := cmd.RunStdString(&RunOpts{Dir: opts.RepoPath}) | ||||
| 	stdout, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: opts.RepoPath}) | ||||
| 	if err != nil { | ||||
| 		return 0, err | ||||
| 	} | ||||
| @ -217,7 +217,7 @@ func (c *Commit) HasPreviousCommit(objectID ObjectID) (bool, error) { | ||||
| 		return false, nil | ||||
| 	} | ||||
| 
 | ||||
| 	_, _, err := NewCommand(c.repo.Ctx, "merge-base", "--is-ancestor").AddDynamicArguments(that, this).RunStdString(&RunOpts{Dir: c.repo.Path}) | ||||
| 	_, _, err := NewCommand("merge-base", "--is-ancestor").AddDynamicArguments(that, this).RunStdString(c.repo.Ctx, &RunOpts{Dir: c.repo.Path}) | ||||
| 	if err == nil { | ||||
| 		return true, nil | ||||
| 	} | ||||
| @ -358,12 +358,12 @@ func (c *Commit) GetFileContent(filename string, limit int) (string, error) { | ||||
| 
 | ||||
| // GetBranchName gets the closest branch name (as returned by 'git name-rev --name-only') | ||||
| func (c *Commit) GetBranchName() (string, error) { | ||||
| 	cmd := NewCommand(c.repo.Ctx, "name-rev") | ||||
| 	cmd := NewCommand("name-rev") | ||||
| 	if DefaultFeatures().CheckVersionAtLeast("2.13.0") { | ||||
| 		cmd.AddArguments("--exclude", "refs/tags/*") | ||||
| 	} | ||||
| 	cmd.AddArguments("--name-only", "--no-undefined").AddDynamicArguments(c.ID.String()) | ||||
| 	data, _, err := cmd.RunStdString(&RunOpts{Dir: c.repo.Path}) | ||||
| 	data, _, err := cmd.RunStdString(c.repo.Ctx, &RunOpts{Dir: c.repo.Path}) | ||||
| 	if err != nil { | ||||
| 		// handle special case where git can not describe commit | ||||
| 		if strings.Contains(err.Error(), "cannot describe") { | ||||
| @ -441,7 +441,7 @@ func GetCommitFileStatus(ctx context.Context, repoPath, commitID string) (*Commi | ||||
| 	}() | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	err := NewCommand(ctx, "log", "--name-status", "-m", "--pretty=format:", "--first-parent", "--no-renames", "-z", "-1").AddDynamicArguments(commitID).Run(&RunOpts{ | ||||
| 	err := NewCommand("log", "--name-status", "-m", "--pretty=format:", "--first-parent", "--no-renames", "-z", "-1").AddDynamicArguments(commitID).Run(ctx, &RunOpts{ | ||||
| 		Dir:    repoPath, | ||||
| 		Stdout: w, | ||||
| 		Stderr: stderr, | ||||
| @ -457,7 +457,7 @@ func GetCommitFileStatus(ctx context.Context, repoPath, commitID string) (*Commi | ||||
| 
 | ||||
| // GetFullCommitID returns full length (40) of commit ID by given short SHA in a repository. | ||||
| func GetFullCommitID(ctx context.Context, repoPath, shortID string) (string, error) { | ||||
| 	commitID, _, err := NewCommand(ctx, "rev-parse").AddDynamicArguments(shortID).RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	commitID, _, err := NewCommand("rev-parse").AddDynamicArguments(shortID).RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		if strings.Contains(err.Error(), "exit status 128") { | ||||
| 			return "", ErrNotExist{shortID, ""} | ||||
|  | ||||
| @ -116,7 +116,7 @@ func syncGitConfig() (err error) { | ||||
| } | ||||
| 
 | ||||
| func configSet(key, value string) error { | ||||
| 	stdout, _, err := NewCommand(DefaultContext, "config", "--global", "--get").AddDynamicArguments(key).RunStdString(nil) | ||||
| 	stdout, _, err := NewCommand("config", "--global", "--get").AddDynamicArguments(key).RunStdString(DefaultContext, nil) | ||||
| 	if err != nil && !IsErrorExitCode(err, 1) { | ||||
| 		return fmt.Errorf("failed to get git config %s, err: %w", key, err) | ||||
| 	} | ||||
| @ -126,7 +126,7 @@ func configSet(key, value string) error { | ||||
| 		return nil | ||||
| 	} | ||||
| 
 | ||||
| 	_, _, err = NewCommand(DefaultContext, "config", "--global").AddDynamicArguments(key, value).RunStdString(nil) | ||||
| 	_, _, err = NewCommand("config", "--global").AddDynamicArguments(key, value).RunStdString(DefaultContext, nil) | ||||
| 	if err != nil { | ||||
| 		return fmt.Errorf("failed to set git global config %s, err: %w", key, err) | ||||
| 	} | ||||
| @ -135,14 +135,14 @@ func configSet(key, value string) error { | ||||
| } | ||||
| 
 | ||||
| func configSetNonExist(key, value string) error { | ||||
| 	_, _, err := NewCommand(DefaultContext, "config", "--global", "--get").AddDynamicArguments(key).RunStdString(nil) | ||||
| 	_, _, err := NewCommand("config", "--global", "--get").AddDynamicArguments(key).RunStdString(DefaultContext, nil) | ||||
| 	if err == nil { | ||||
| 		// already exist | ||||
| 		return nil | ||||
| 	} | ||||
| 	if IsErrorExitCode(err, 1) { | ||||
| 		// not exist, set new config | ||||
| 		_, _, err = NewCommand(DefaultContext, "config", "--global").AddDynamicArguments(key, value).RunStdString(nil) | ||||
| 		_, _, err = NewCommand("config", "--global").AddDynamicArguments(key, value).RunStdString(DefaultContext, nil) | ||||
| 		if err != nil { | ||||
| 			return fmt.Errorf("failed to set git global config %s, err: %w", key, err) | ||||
| 		} | ||||
| @ -153,14 +153,14 @@ func configSetNonExist(key, value string) error { | ||||
| } | ||||
| 
 | ||||
| func configAddNonExist(key, value string) error { | ||||
| 	_, _, err := NewCommand(DefaultContext, "config", "--global", "--get").AddDynamicArguments(key, regexp.QuoteMeta(value)).RunStdString(nil) | ||||
| 	_, _, err := NewCommand("config", "--global", "--get").AddDynamicArguments(key, regexp.QuoteMeta(value)).RunStdString(DefaultContext, nil) | ||||
| 	if err == nil { | ||||
| 		// already exist | ||||
| 		return nil | ||||
| 	} | ||||
| 	if IsErrorExitCode(err, 1) { | ||||
| 		// not exist, add new config | ||||
| 		_, _, err = NewCommand(DefaultContext, "config", "--global", "--add").AddDynamicArguments(key, value).RunStdString(nil) | ||||
| 		_, _, err = NewCommand("config", "--global", "--add").AddDynamicArguments(key, value).RunStdString(DefaultContext, nil) | ||||
| 		if err != nil { | ||||
| 			return fmt.Errorf("failed to add git global config %s, err: %w", key, err) | ||||
| 		} | ||||
| @ -170,10 +170,10 @@ func configAddNonExist(key, value string) error { | ||||
| } | ||||
| 
 | ||||
| func configUnsetAll(key, value string) error { | ||||
| 	_, _, err := NewCommand(DefaultContext, "config", "--global", "--get").AddDynamicArguments(key).RunStdString(nil) | ||||
| 	_, _, err := NewCommand("config", "--global", "--get").AddDynamicArguments(key).RunStdString(DefaultContext, nil) | ||||
| 	if err == nil { | ||||
| 		// exist, need to remove | ||||
| 		_, _, err = NewCommand(DefaultContext, "config", "--global", "--unset-all").AddDynamicArguments(key, regexp.QuoteMeta(value)).RunStdString(nil) | ||||
| 		_, _, err = NewCommand("config", "--global", "--unset-all").AddDynamicArguments(key, regexp.QuoteMeta(value)).RunStdString(DefaultContext, nil) | ||||
| 		if err != nil { | ||||
| 			return fmt.Errorf("failed to unset git global config %s, err: %w", key, err) | ||||
| 		} | ||||
|  | ||||
| @ -34,8 +34,8 @@ func GetRawDiff(repo *Repository, commitID string, diffType RawDiffType, writer | ||||
| // GetReverseRawDiff dumps the reverse diff results of repository in given commit ID to io.Writer. | ||||
| func GetReverseRawDiff(ctx context.Context, repoPath, commitID string, writer io.Writer) error { | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	cmd := NewCommand(ctx, "show", "--pretty=format:revert %H%n", "-R").AddDynamicArguments(commitID) | ||||
| 	if err := cmd.Run(&RunOpts{ | ||||
| 	cmd := NewCommand("show", "--pretty=format:revert %H%n", "-R").AddDynamicArguments(commitID) | ||||
| 	if err := cmd.Run(ctx, &RunOpts{ | ||||
| 		Dir:    repoPath, | ||||
| 		Stdout: writer, | ||||
| 		Stderr: stderr, | ||||
| @ -56,7 +56,7 @@ func GetRepoRawDiffForFile(repo *Repository, startCommit, endCommit string, diff | ||||
| 		files = append(files, file) | ||||
| 	} | ||||
| 
 | ||||
| 	cmd := NewCommand(repo.Ctx) | ||||
| 	cmd := NewCommand() | ||||
| 	switch diffType { | ||||
| 	case RawDiffNormal: | ||||
| 		if len(startCommit) != 0 { | ||||
| @ -89,7 +89,7 @@ func GetRepoRawDiffForFile(repo *Repository, startCommit, endCommit string, diff | ||||
| 	} | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	if err = cmd.Run(&RunOpts{ | ||||
| 	if err = cmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdout: writer, | ||||
| 		Stderr: stderr, | ||||
| @ -301,8 +301,8 @@ func GetAffectedFiles(repo *Repository, branchName, oldCommitID, newCommitID str | ||||
| 	affectedFiles := make([]string, 0, 32) | ||||
| 
 | ||||
| 	// Run `git diff --name-only` to get the names of the changed files | ||||
| 	err = NewCommand(repo.Ctx, "diff", "--name-only").AddDynamicArguments(oldCommitID, newCommitID). | ||||
| 		Run(&RunOpts{ | ||||
| 	err = NewCommand("diff", "--name-only").AddDynamicArguments(oldCommitID, newCommitID). | ||||
| 		Run(repo.Ctx, &RunOpts{ | ||||
| 			Env:    env, | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: stdoutWriter, | ||||
|  | ||||
| @ -10,5 +10,5 @@ import ( | ||||
| 
 | ||||
| // Fsck verifies the connectivity and validity of the objects in the database | ||||
| func Fsck(ctx context.Context, repoPath string, timeout time.Duration, args TrustedCmdArgs) error { | ||||
| 	return NewCommand(ctx, "fsck").AddArguments(args...).Run(&RunOpts{Timeout: timeout, Dir: repoPath}) | ||||
| 	return NewCommand("fsck").AddArguments(args...).Run(ctx, &RunOpts{Timeout: timeout, Dir: repoPath}) | ||||
| } | ||||
|  | ||||
| @ -60,7 +60,7 @@ func DefaultFeatures() *Features { | ||||
| } | ||||
| 
 | ||||
| func loadGitVersionFeatures() (*Features, error) { | ||||
| 	stdout, _, runErr := NewCommand(DefaultContext, "version").RunStdString(nil) | ||||
| 	stdout, _, runErr := NewCommand("version").RunStdString(DefaultContext, nil) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
|  | ||||
| @ -52,7 +52,7 @@ func GrepSearch(ctx context.Context, repo *Repository, search string, opts GrepO | ||||
| 	 2^@repo: go-gitea/gitea | ||||
| 	*/ | ||||
| 	var results []*GrepResult | ||||
| 	cmd := NewCommand(ctx, "grep", "--null", "--break", "--heading", "--fixed-strings", "--line-number", "--ignore-case", "--full-name") | ||||
| 	cmd := NewCommand("grep", "--null", "--break", "--heading", "--fixed-strings", "--line-number", "--ignore-case", "--full-name") | ||||
| 	cmd.AddOptionValues("--context", fmt.Sprint(opts.ContextLineNumber)) | ||||
| 	if opts.IsFuzzy { | ||||
| 		words := strings.Fields(search) | ||||
| @ -66,7 +66,7 @@ func GrepSearch(ctx context.Context, repo *Repository, search string, opts GrepO | ||||
| 	cmd.AddDashesAndList(opts.PathspecList...) | ||||
| 	opts.MaxResultLimit = util.IfZero(opts.MaxResultLimit, 50) | ||||
| 	stderr := bytes.Buffer{} | ||||
| 	err = cmd.Run(&RunOpts{ | ||||
| 	err = cmd.Run(ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdout: stdoutWriter, | ||||
| 		Stderr: &stderr, | ||||
|  | ||||
| @ -34,7 +34,7 @@ func LogNameStatusRepo(ctx context.Context, repository, head, treepath string, p | ||||
| 		_ = stdoutWriter.Close() | ||||
| 	} | ||||
| 
 | ||||
| 	cmd := NewCommand(ctx) | ||||
| 	cmd := NewCommand() | ||||
| 	cmd.AddArguments("log", "--name-status", "-c", "--format=commit%x00%H %P%x00", "--parents", "--no-renames", "-t", "-z").AddDynamicArguments(head) | ||||
| 
 | ||||
| 	var files []string | ||||
| @ -64,7 +64,7 @@ func LogNameStatusRepo(ctx context.Context, repository, head, treepath string, p | ||||
| 
 | ||||
| 	go func() { | ||||
| 		stderr := strings.Builder{} | ||||
| 		err := cmd.Run(&RunOpts{ | ||||
| 		err := cmd.Run(ctx, &RunOpts{ | ||||
| 			Dir:    repository, | ||||
| 			Stdout: stdoutWriter, | ||||
| 			Stderr: &stderr, | ||||
|  | ||||
| @ -25,8 +25,8 @@ func CatFileBatchCheck(ctx context.Context, shasToCheckReader *io.PipeReader, ca | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	var errbuf strings.Builder | ||||
| 	cmd := git.NewCommand(ctx, "cat-file", "--batch-check") | ||||
| 	if err := cmd.Run(&git.RunOpts{ | ||||
| 	cmd := git.NewCommand("cat-file", "--batch-check") | ||||
| 	if err := cmd.Run(ctx, &git.RunOpts{ | ||||
| 		Dir:    tmpBasePath, | ||||
| 		Stdin:  shasToCheckReader, | ||||
| 		Stdout: catFileCheckWriter, | ||||
| @ -43,8 +43,8 @@ func CatFileBatchCheckAllObjects(ctx context.Context, catFileCheckWriter *io.Pip | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	var errbuf strings.Builder | ||||
| 	cmd := git.NewCommand(ctx, "cat-file", "--batch-check", "--batch-all-objects") | ||||
| 	if err := cmd.Run(&git.RunOpts{ | ||||
| 	cmd := git.NewCommand("cat-file", "--batch-check", "--batch-all-objects") | ||||
| 	if err := cmd.Run(ctx, &git.RunOpts{ | ||||
| 		Dir:    tmpBasePath, | ||||
| 		Stdout: catFileCheckWriter, | ||||
| 		Stderr: stderr, | ||||
| @ -64,7 +64,7 @@ func CatFileBatch(ctx context.Context, shasToBatchReader *io.PipeReader, catFile | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	var errbuf strings.Builder | ||||
| 	if err := git.NewCommand(ctx, "cat-file", "--batch").Run(&git.RunOpts{ | ||||
| 	if err := git.NewCommand("cat-file", "--batch").Run(ctx, &git.RunOpts{ | ||||
| 		Dir:    tmpBasePath, | ||||
| 		Stdout: catFileBatchWriter, | ||||
| 		Stdin:  shasToBatchReader, | ||||
|  | ||||
| @ -32,7 +32,7 @@ func FindLFSFile(repo *git.Repository, objectID git.ObjectID) ([]*LFSResult, err | ||||
| 
 | ||||
| 	go func() { | ||||
| 		stderr := strings.Builder{} | ||||
| 		err := git.NewCommand(repo.Ctx, "rev-list", "--all").Run(&git.RunOpts{ | ||||
| 		err := git.NewCommand("rev-list", "--all").Run(repo.Ctx, &git.RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: revListWriter, | ||||
| 			Stderr: &stderr, | ||||
|  | ||||
| @ -22,7 +22,7 @@ func NameRevStdin(ctx context.Context, shasToNameReader *io.PipeReader, nameRevS | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	var errbuf strings.Builder | ||||
| 	if err := git.NewCommand(ctx, "name-rev", "--stdin", "--name-only", "--always").Run(&git.RunOpts{ | ||||
| 	if err := git.NewCommand("name-rev", "--stdin", "--name-only", "--always").Run(ctx, &git.RunOpts{ | ||||
| 		Dir:    tmpBasePath, | ||||
| 		Stdout: nameRevStdinWriter, | ||||
| 		Stdin:  shasToNameReader, | ||||
|  | ||||
| @ -23,8 +23,8 @@ func RevListAllObjects(ctx context.Context, revListWriter *io.PipeWriter, wg *sy | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	var errbuf strings.Builder | ||||
| 	cmd := git.NewCommand(ctx, "rev-list", "--objects", "--all") | ||||
| 	if err := cmd.Run(&git.RunOpts{ | ||||
| 	cmd := git.NewCommand("rev-list", "--objects", "--all") | ||||
| 	if err := cmd.Run(ctx, &git.RunOpts{ | ||||
| 		Dir:    basePath, | ||||
| 		Stdout: revListWriter, | ||||
| 		Stderr: stderr, | ||||
| @ -42,11 +42,11 @@ func RevListObjects(ctx context.Context, revListWriter *io.PipeWriter, wg *sync. | ||||
| 	defer revListWriter.Close() | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	var errbuf strings.Builder | ||||
| 	cmd := git.NewCommand(ctx, "rev-list", "--objects").AddDynamicArguments(headSHA) | ||||
| 	cmd := git.NewCommand("rev-list", "--objects").AddDynamicArguments(headSHA) | ||||
| 	if baseSHA != "" { | ||||
| 		cmd = cmd.AddArguments("--not").AddDynamicArguments(baseSHA) | ||||
| 	} | ||||
| 	if err := cmd.Run(&git.RunOpts{ | ||||
| 	if err := cmd.Run(ctx, &git.RunOpts{ | ||||
| 		Dir:    tmpBasePath, | ||||
| 		Stdout: revListWriter, | ||||
| 		Stderr: stderr, | ||||
|  | ||||
| @ -17,12 +17,12 @@ import ( | ||||
| func GetRemoteAddress(ctx context.Context, repoPath, remoteName string) (string, error) { | ||||
| 	var cmd *Command | ||||
| 	if DefaultFeatures().CheckVersionAtLeast("2.7") { | ||||
| 		cmd = NewCommand(ctx, "remote", "get-url").AddDynamicArguments(remoteName) | ||||
| 		cmd = NewCommand("remote", "get-url").AddDynamicArguments(remoteName) | ||||
| 	} else { | ||||
| 		cmd = NewCommand(ctx, "config", "--get").AddDynamicArguments("remote." + remoteName + ".url") | ||||
| 		cmd = NewCommand("config", "--get").AddDynamicArguments("remote." + remoteName + ".url") | ||||
| 	} | ||||
| 
 | ||||
| 	result, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	result, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		return "", err | ||||
| 	} | ||||
|  | ||||
| @ -57,7 +57,7 @@ func (repo *Repository) parsePrettyFormatLogToList(logs []byte) ([]*Commit, erro | ||||
| 
 | ||||
| // IsRepoURLAccessible checks if given repository URL is accessible. | ||||
| func IsRepoURLAccessible(ctx context.Context, url string) bool { | ||||
| 	_, _, err := NewCommand(ctx, "ls-remote", "-q", "-h").AddDynamicArguments(url, "HEAD").RunStdString(nil) | ||||
| 	_, _, err := NewCommand("ls-remote", "-q", "-h").AddDynamicArguments(url, "HEAD").RunStdString(ctx, nil) | ||||
| 	return err == nil | ||||
| } | ||||
| 
 | ||||
| @ -68,7 +68,7 @@ func InitRepository(ctx context.Context, repoPath string, bare bool, objectForma | ||||
| 		return err | ||||
| 	} | ||||
| 
 | ||||
| 	cmd := NewCommand(ctx, "init") | ||||
| 	cmd := NewCommand("init") | ||||
| 
 | ||||
| 	if !IsValidObjectFormat(objectFormatName) { | ||||
| 		return fmt.Errorf("invalid object format: %s", objectFormatName) | ||||
| @ -80,15 +80,15 @@ func InitRepository(ctx context.Context, repoPath string, bare bool, objectForma | ||||
| 	if bare { | ||||
| 		cmd.AddArguments("--bare") | ||||
| 	} | ||||
| 	_, _, err = cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	_, _, err = cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // IsEmpty Check if repository is empty. | ||||
| func (repo *Repository) IsEmpty() (bool, error) { | ||||
| 	var errbuf, output strings.Builder | ||||
| 	if err := NewCommand(repo.Ctx).AddOptionFormat("--git-dir=%s", repo.Path).AddArguments("rev-list", "-n", "1", "--all"). | ||||
| 		Run(&RunOpts{ | ||||
| 	if err := NewCommand().AddOptionFormat("--git-dir=%s", repo.Path).AddArguments("rev-list", "-n", "1", "--all"). | ||||
| 		Run(repo.Ctx, &RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: &output, | ||||
| 			Stderr: &errbuf, | ||||
| @ -129,7 +129,7 @@ func CloneWithArgs(ctx context.Context, args TrustedCmdArgs, from, to string, op | ||||
| 		return err | ||||
| 	} | ||||
| 
 | ||||
| 	cmd := NewCommandContextNoGlobals(ctx, args...).AddArguments("clone") | ||||
| 	cmd := NewCommandNoGlobals(args...).AddArguments("clone") | ||||
| 	if opts.SkipTLSVerify { | ||||
| 		cmd.AddArguments("-c", "http.sslVerify=false") | ||||
| 	} | ||||
| @ -170,7 +170,7 @@ func CloneWithArgs(ctx context.Context, args TrustedCmdArgs, from, to string, op | ||||
| 	} | ||||
| 
 | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	if err = cmd.Run(&RunOpts{ | ||||
| 	if err = cmd.Run(ctx, &RunOpts{ | ||||
| 		Timeout: opts.Timeout, | ||||
| 		Env:     envs, | ||||
| 		Stdout:  io.Discard, | ||||
| @ -193,7 +193,7 @@ type PushOptions struct { | ||||
| 
 | ||||
| // Push pushs local commits to given remote branch. | ||||
| func Push(ctx context.Context, repoPath string, opts PushOptions) error { | ||||
| 	cmd := NewCommand(ctx, "push") | ||||
| 	cmd := NewCommand("push") | ||||
| 	if opts.Force { | ||||
| 		cmd.AddArguments("-f") | ||||
| 	} | ||||
| @ -206,7 +206,7 @@ func Push(ctx context.Context, repoPath string, opts PushOptions) error { | ||||
| 	} | ||||
| 	cmd.AddDashesAndList(remoteBranchArgs...) | ||||
| 
 | ||||
| 	stdout, stderr, err := cmd.RunStdString(&RunOpts{Env: opts.Env, Timeout: opts.Timeout, Dir: repoPath}) | ||||
| 	stdout, stderr, err := cmd.RunStdString(ctx, &RunOpts{Env: opts.Env, Timeout: opts.Timeout, Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		if strings.Contains(stderr, "non-fast-forward") { | ||||
| 			return &ErrPushOutOfDate{StdOut: stdout, StdErr: stderr, Err: err} | ||||
| @ -225,8 +225,8 @@ func Push(ctx context.Context, repoPath string, opts PushOptions) error { | ||||
| 
 | ||||
| // GetLatestCommitTime returns time for latest commit in repository (across all branches) | ||||
| func GetLatestCommitTime(ctx context.Context, repoPath string) (time.Time, error) { | ||||
| 	cmd := NewCommand(ctx, "for-each-ref", "--sort=-committerdate", BranchPrefix, "--count", "1", "--format=%(committerdate)") | ||||
| 	stdout, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	cmd := NewCommand("for-each-ref", "--sort=-committerdate", BranchPrefix, "--count", "1", "--format=%(committerdate)") | ||||
| 	stdout, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		return time.Time{}, err | ||||
| 	} | ||||
| @ -242,9 +242,9 @@ type DivergeObject struct { | ||||
| 
 | ||||
| // GetDivergingCommits returns the number of commits a targetBranch is ahead or behind a baseBranch | ||||
| func GetDivergingCommits(ctx context.Context, repoPath, baseBranch, targetBranch string) (do DivergeObject, err error) { | ||||
| 	cmd := NewCommand(ctx, "rev-list", "--count", "--left-right"). | ||||
| 	cmd := NewCommand("rev-list", "--count", "--left-right"). | ||||
| 		AddDynamicArguments(baseBranch + "..." + targetBranch).AddArguments("--") | ||||
| 	stdout, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	stdout, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		return do, err | ||||
| 	} | ||||
| @ -273,23 +273,23 @@ func (repo *Repository) CreateBundle(ctx context.Context, commit string, out io. | ||||
| 	defer os.RemoveAll(tmp) | ||||
| 
 | ||||
| 	env := append(os.Environ(), "GIT_OBJECT_DIRECTORY="+filepath.Join(repo.Path, "objects")) | ||||
| 	_, _, err = NewCommand(ctx, "init", "--bare").RunStdString(&RunOpts{Dir: tmp, Env: env}) | ||||
| 	_, _, err = NewCommand("init", "--bare").RunStdString(ctx, &RunOpts{Dir: tmp, Env: env}) | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 
 | ||||
| 	_, _, err = NewCommand(ctx, "reset", "--soft").AddDynamicArguments(commit).RunStdString(&RunOpts{Dir: tmp, Env: env}) | ||||
| 	_, _, err = NewCommand("reset", "--soft").AddDynamicArguments(commit).RunStdString(ctx, &RunOpts{Dir: tmp, Env: env}) | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 
 | ||||
| 	_, _, err = NewCommand(ctx, "branch", "-m", "bundle").RunStdString(&RunOpts{Dir: tmp, Env: env}) | ||||
| 	_, _, err = NewCommand("branch", "-m", "bundle").RunStdString(ctx, &RunOpts{Dir: tmp, Env: env}) | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 
 | ||||
| 	tmpFile := filepath.Join(tmp, "bundle") | ||||
| 	_, _, err = NewCommand(ctx, "bundle", "create").AddDynamicArguments(tmpFile, "bundle", "HEAD").RunStdString(&RunOpts{Dir: tmp, Env: env}) | ||||
| 	_, _, err = NewCommand("bundle", "create").AddDynamicArguments(tmpFile, "bundle", "HEAD").RunStdString(ctx, &RunOpts{Dir: tmp, Env: env}) | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
|  | ||||
| @ -53,7 +53,7 @@ func (repo *Repository) CreateArchive(ctx context.Context, format ArchiveType, t | ||||
| 		return fmt.Errorf("unknown format: %v", format) | ||||
| 	} | ||||
| 
 | ||||
| 	cmd := NewCommand(ctx, "archive") | ||||
| 	cmd := NewCommand("archive") | ||||
| 	if usePrefix { | ||||
| 		cmd.AddOptionFormat("--prefix=%s", filepath.Base(strings.TrimSuffix(repo.Path, ".git"))+"/") | ||||
| 	} | ||||
| @ -61,7 +61,7 @@ func (repo *Repository) CreateArchive(ctx context.Context, format ArchiveType, t | ||||
| 	cmd.AddDynamicArguments(commitID) | ||||
| 
 | ||||
| 	var stderr strings.Builder | ||||
| 	err := cmd.Run(&RunOpts{ | ||||
| 	err := cmd.Run(ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdout: target, | ||||
| 		Stderr: &stderr, | ||||
|  | ||||
| @ -41,7 +41,7 @@ func (repo *Repository) CheckAttribute(opts CheckAttributeOpts) (map[string]map[ | ||||
| 	stdOut := new(bytes.Buffer) | ||||
| 	stdErr := new(bytes.Buffer) | ||||
| 
 | ||||
| 	cmd := NewCommand(repo.Ctx, "check-attr", "-z") | ||||
| 	cmd := NewCommand("check-attr", "-z") | ||||
| 
 | ||||
| 	if opts.AllAttributes { | ||||
| 		cmd.AddArguments("-a") | ||||
| @ -59,7 +59,7 @@ func (repo *Repository) CheckAttribute(opts CheckAttributeOpts) (map[string]map[ | ||||
| 
 | ||||
| 	cmd.AddDashesAndList(opts.Filenames...) | ||||
| 
 | ||||
| 	if err := cmd.Run(&RunOpts{ | ||||
| 	if err := cmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Env:    env, | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdout: stdOut, | ||||
| @ -122,7 +122,7 @@ func (c *CheckAttributeReader) Init(ctx context.Context) error { | ||||
| 	} | ||||
| 
 | ||||
| 	c.ctx, c.cancel = context.WithCancel(ctx) | ||||
| 	c.cmd = NewCommand(c.ctx, "check-attr", "--stdin", "-z") | ||||
| 	c.cmd = NewCommand("check-attr", "--stdin", "-z") | ||||
| 
 | ||||
| 	if len(c.IndexFile) > 0 { | ||||
| 		c.cmd.AddArguments("--cached") | ||||
| @ -159,7 +159,7 @@ func (c *CheckAttributeReader) Run() error { | ||||
| 		_ = c.stdOut.Close() | ||||
| 	}() | ||||
| 	stdErr := new(bytes.Buffer) | ||||
| 	err := c.cmd.Run(&RunOpts{ | ||||
| 	err := c.cmd.Run(c.ctx, &RunOpts{ | ||||
| 		Env:    c.env, | ||||
| 		Dir:    c.Repo.Path, | ||||
| 		Stdin:  c.stdinReader, | ||||
|  | ||||
| @ -9,10 +9,10 @@ import ( | ||||
| 
 | ||||
| // LineBlame returns the latest commit at the given line | ||||
| func (repo *Repository) LineBlame(revision, path, file string, line uint) (*Commit, error) { | ||||
| 	res, _, err := NewCommand(repo.Ctx, "blame"). | ||||
| 	res, _, err := NewCommand("blame"). | ||||
| 		AddOptionFormat("-L %d,%d", line, line). | ||||
| 		AddOptionValues("-p", revision). | ||||
| 		AddDashesAndList(file).RunStdString(&RunOpts{Dir: path}) | ||||
| 		AddDashesAndList(file).RunStdString(repo.Ctx, &RunOpts{Dir: path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
|  | ||||
| @ -16,7 +16,7 @@ const BranchPrefix = "refs/heads/" | ||||
| 
 | ||||
| // IsReferenceExist returns true if given reference exists in the repository. | ||||
| func IsReferenceExist(ctx context.Context, repoPath, name string) bool { | ||||
| 	_, _, err := NewCommand(ctx, "show-ref", "--verify").AddDashesAndList(name).RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	_, _, err := NewCommand("show-ref", "--verify").AddDashesAndList(name).RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	return err == nil | ||||
| } | ||||
| 
 | ||||
| @ -38,7 +38,7 @@ func (repo *Repository) GetHEADBranch() (*Branch, error) { | ||||
| 	if repo == nil { | ||||
| 		return nil, fmt.Errorf("nil repo") | ||||
| 	} | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "symbolic-ref", "HEAD").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("symbolic-ref", "HEAD").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| @ -56,7 +56,7 @@ func (repo *Repository) GetHEADBranch() (*Branch, error) { | ||||
| } | ||||
| 
 | ||||
| func GetDefaultBranch(ctx context.Context, repoPath string) (string, error) { | ||||
| 	stdout, _, err := NewCommand(ctx, "symbolic-ref", "HEAD").RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	stdout, _, err := NewCommand("symbolic-ref", "HEAD").RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		return "", err | ||||
| 	} | ||||
| @ -105,7 +105,7 @@ type DeleteBranchOptions struct { | ||||
| 
 | ||||
| // DeleteBranch delete a branch by name on repository. | ||||
| func (repo *Repository) DeleteBranch(name string, opts DeleteBranchOptions) error { | ||||
| 	cmd := NewCommand(repo.Ctx, "branch") | ||||
| 	cmd := NewCommand("branch") | ||||
| 
 | ||||
| 	if opts.Force { | ||||
| 		cmd.AddArguments("-D") | ||||
| @ -114,36 +114,36 @@ func (repo *Repository) DeleteBranch(name string, opts DeleteBranchOptions) erro | ||||
| 	} | ||||
| 
 | ||||
| 	cmd.AddDashesAndList(name) | ||||
| 	_, _, err := cmd.RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := cmd.RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 
 | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // CreateBranch create a new branch | ||||
| func (repo *Repository) CreateBranch(branch, oldbranchOrCommit string) error { | ||||
| 	cmd := NewCommand(repo.Ctx, "branch") | ||||
| 	cmd := NewCommand("branch") | ||||
| 	cmd.AddDashesAndList(branch, oldbranchOrCommit) | ||||
| 
 | ||||
| 	_, _, err := cmd.RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := cmd.RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 
 | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // AddRemote adds a new remote to repository. | ||||
| func (repo *Repository) AddRemote(name, url string, fetch bool) error { | ||||
| 	cmd := NewCommand(repo.Ctx, "remote", "add") | ||||
| 	cmd := NewCommand("remote", "add") | ||||
| 	if fetch { | ||||
| 		cmd.AddArguments("-f") | ||||
| 	} | ||||
| 	cmd.AddDynamicArguments(name, url) | ||||
| 
 | ||||
| 	_, _, err := cmd.RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := cmd.RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // RemoveRemote removes a remote from repository. | ||||
| func (repo *Repository) RemoveRemote(name string) error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "remote", "rm").AddDynamicArguments(name).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("remote", "rm").AddDynamicArguments(name).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| @ -154,6 +154,6 @@ func (branch *Branch) GetCommit() (*Commit, error) { | ||||
| 
 | ||||
| // RenameBranch rename a branch | ||||
| func (repo *Repository) RenameBranch(from, to string) error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "branch", "-m").AddDynamicArguments(from, to).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("branch", "-m").AddDynamicArguments(from, to).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
|  | ||||
| @ -109,7 +109,7 @@ func WalkShowRef(ctx context.Context, repoPath string, extraArgs TrustedCmdArgs, | ||||
| 		stderrBuilder := &strings.Builder{} | ||||
| 		args := TrustedCmdArgs{"for-each-ref", "--format=%(objectname) %(refname)"} | ||||
| 		args = append(args, extraArgs...) | ||||
| 		err := NewCommand(ctx, args...).Run(&RunOpts{ | ||||
| 		err := NewCommand(args...).Run(ctx, &RunOpts{ | ||||
| 			Dir:    repoPath, | ||||
| 			Stdout: stdoutWriter, | ||||
| 			Stderr: stderrBuilder, | ||||
|  | ||||
| @ -59,7 +59,7 @@ func (repo *Repository) getCommitByPathWithID(id ObjectID, relpath string) (*Com | ||||
| 		relpath = `\` + relpath | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, runErr := NewCommand(repo.Ctx, "log", "-1", prettyLogFormat).AddDynamicArguments(id.String()).AddDashesAndList(relpath).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, runErr := NewCommand("log", "-1", prettyLogFormat).AddDynamicArguments(id.String()).AddDashesAndList(relpath).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
| @ -74,7 +74,7 @@ func (repo *Repository) getCommitByPathWithID(id ObjectID, relpath string) (*Com | ||||
| 
 | ||||
| // GetCommitByPath returns the last commit of relative path. | ||||
| func (repo *Repository) GetCommitByPath(relpath string) (*Commit, error) { | ||||
| 	stdout, _, runErr := NewCommand(repo.Ctx, "log", "-1", prettyLogFormat).AddDashesAndList(relpath).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, runErr := NewCommand("log", "-1", prettyLogFormat).AddDashesAndList(relpath).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
| @ -90,7 +90,7 @@ func (repo *Repository) GetCommitByPath(relpath string) (*Commit, error) { | ||||
| } | ||||
| 
 | ||||
| func (repo *Repository) commitsByRange(id ObjectID, page, pageSize int, not string) ([]*Commit, error) { | ||||
| 	cmd := NewCommand(repo.Ctx, "log"). | ||||
| 	cmd := NewCommand("log"). | ||||
| 		AddOptionFormat("--skip=%d", (page-1)*pageSize). | ||||
| 		AddOptionFormat("--max-count=%d", pageSize). | ||||
| 		AddArguments(prettyLogFormat). | ||||
| @ -100,7 +100,7 @@ func (repo *Repository) commitsByRange(id ObjectID, page, pageSize int, not stri | ||||
| 		cmd.AddOptionValues("--not", not) | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, err := cmd.RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := cmd.RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| @ -134,7 +134,7 @@ func (repo *Repository) searchCommits(id ObjectID, opts SearchCommitsOptions) ([ | ||||
| 	} | ||||
| 
 | ||||
| 	// create new git log command with limit of 100 commits | ||||
| 	cmd := NewCommand(repo.Ctx, "log", "-100", prettyLogFormat).AddDynamicArguments(id.String()) | ||||
| 	cmd := NewCommand("log", "-100", prettyLogFormat).AddDynamicArguments(id.String()) | ||||
| 
 | ||||
| 	// pretend that all refs along with HEAD were listed on command line as <commis> | ||||
| 	// https://git-scm.com/docs/git-log#Documentation/git-log.txt---all | ||||
| @ -154,7 +154,7 @@ func (repo *Repository) searchCommits(id ObjectID, opts SearchCommitsOptions) ([ | ||||
| 
 | ||||
| 	// search for commits matching given constraints and keywords in commit msg | ||||
| 	addCommonSearchArgs(cmd) | ||||
| 	stdout, _, err := cmd.RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := cmd.RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| @ -168,14 +168,14 @@ func (repo *Repository) searchCommits(id ObjectID, opts SearchCommitsOptions) ([ | ||||
| 		// ignore anything not matching a valid sha pattern | ||||
| 		if id.Type().IsValid(v) { | ||||
| 			// create new git log command with 1 commit limit | ||||
| 			hashCmd := NewCommand(repo.Ctx, "log", "-1", prettyLogFormat) | ||||
| 			hashCmd := NewCommand("log", "-1", prettyLogFormat) | ||||
| 			// add previous arguments except for --grep and --all | ||||
| 			addCommonSearchArgs(hashCmd) | ||||
| 			// add keyword as <commit> | ||||
| 			hashCmd.AddDynamicArguments(v) | ||||
| 
 | ||||
| 			// search with given constraints for commit matching sha hash of v | ||||
| 			hashMatching, _, err := hashCmd.RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 			hashMatching, _, err := hashCmd.RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 			if err != nil || bytes.Contains(stdout, hashMatching) { | ||||
| 				continue | ||||
| 			} | ||||
| @ -190,7 +190,7 @@ func (repo *Repository) searchCommits(id ObjectID, opts SearchCommitsOptions) ([ | ||||
| // FileChangedBetweenCommits Returns true if the file changed between commit IDs id1 and id2 | ||||
| // You must ensure that id1 and id2 are valid commit ids. | ||||
| func (repo *Repository) FileChangedBetweenCommits(filename, id1, id2 string) (bool, error) { | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "diff", "--name-only", "-z").AddDynamicArguments(id1, id2).AddDashesAndList(filename).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("diff", "--name-only", "-z").AddDynamicArguments(id1, id2).AddDashesAndList(filename).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return false, err | ||||
| 	} | ||||
| @ -223,7 +223,7 @@ func (repo *Repository) CommitsByFileAndRange(opts CommitsByFileAndRangeOptions) | ||||
| 	}() | ||||
| 	go func() { | ||||
| 		stderr := strings.Builder{} | ||||
| 		gitCmd := NewCommand(repo.Ctx, "rev-list"). | ||||
| 		gitCmd := NewCommand("rev-list"). | ||||
| 			AddOptionFormat("--max-count=%d", setting.Git.CommitsRangeSize). | ||||
| 			AddOptionFormat("--skip=%d", (opts.Page-1)*setting.Git.CommitsRangeSize) | ||||
| 		gitCmd.AddDynamicArguments(opts.Revision) | ||||
| @ -233,7 +233,7 @@ func (repo *Repository) CommitsByFileAndRange(opts CommitsByFileAndRangeOptions) | ||||
| 		} | ||||
| 
 | ||||
| 		gitCmd.AddDashesAndList(opts.File) | ||||
| 		err := gitCmd.Run(&RunOpts{ | ||||
| 		err := gitCmd.Run(repo.Ctx, &RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: stdoutWriter, | ||||
| 			Stderr: &stderr, | ||||
| @ -275,11 +275,11 @@ func (repo *Repository) CommitsByFileAndRange(opts CommitsByFileAndRangeOptions) | ||||
| 
 | ||||
| // FilesCountBetween return the number of files changed between two commits | ||||
| func (repo *Repository) FilesCountBetween(startCommitID, endCommitID string) (int, error) { | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "diff", "--name-only").AddDynamicArguments(startCommitID + "..." + endCommitID).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("diff", "--name-only").AddDynamicArguments(startCommitID+"..."+endCommitID).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil && strings.Contains(err.Error(), "no merge base") { | ||||
| 		// git >= 2.28 now returns an error if startCommitID and endCommitID have become unrelated. | ||||
| 		// previously it would return the results of git diff --name-only startCommitID endCommitID so let's try that... | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "diff", "--name-only").AddDynamicArguments(startCommitID, endCommitID).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 		stdout, _, err = NewCommand("diff", "--name-only").AddDynamicArguments(startCommitID, endCommitID).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	} | ||||
| 	if err != nil { | ||||
| 		return 0, err | ||||
| @ -293,13 +293,13 @@ func (repo *Repository) CommitsBetween(last, before *Commit) ([]*Commit, error) | ||||
| 	var stdout []byte | ||||
| 	var err error | ||||
| 	if before == nil { | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "rev-list").AddDynamicArguments(last.ID.String()).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 		stdout, _, err = NewCommand("rev-list").AddDynamicArguments(last.ID.String()).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	} else { | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "rev-list").AddDynamicArguments(before.ID.String() + ".." + last.ID.String()).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 		stdout, _, err = NewCommand("rev-list").AddDynamicArguments(before.ID.String()+".."+last.ID.String()).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		if err != nil && strings.Contains(err.Error(), "no merge base") { | ||||
| 			// future versions of git >= 2.28 are likely to return an error if before and last have become unrelated. | ||||
| 			// previously it would return the results of git rev-list before last so let's try that... | ||||
| 			stdout, _, err = NewCommand(repo.Ctx, "rev-list").AddDynamicArguments(before.ID.String(), last.ID.String()).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 			stdout, _, err = NewCommand("rev-list").AddDynamicArguments(before.ID.String(), last.ID.String()).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		} | ||||
| 	} | ||||
| 	if err != nil { | ||||
| @ -313,22 +313,22 @@ func (repo *Repository) CommitsBetweenLimit(last, before *Commit, limit, skip in | ||||
| 	var stdout []byte | ||||
| 	var err error | ||||
| 	if before == nil { | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "rev-list"). | ||||
| 		stdout, _, err = NewCommand("rev-list"). | ||||
| 			AddOptionValues("--max-count", strconv.Itoa(limit)). | ||||
| 			AddOptionValues("--skip", strconv.Itoa(skip)). | ||||
| 			AddDynamicArguments(last.ID.String()).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 			AddDynamicArguments(last.ID.String()).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	} else { | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "rev-list"). | ||||
| 		stdout, _, err = NewCommand("rev-list"). | ||||
| 			AddOptionValues("--max-count", strconv.Itoa(limit)). | ||||
| 			AddOptionValues("--skip", strconv.Itoa(skip)). | ||||
| 			AddDynamicArguments(before.ID.String() + ".." + last.ID.String()).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 			AddDynamicArguments(before.ID.String()+".."+last.ID.String()).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		if err != nil && strings.Contains(err.Error(), "no merge base") { | ||||
| 			// future versions of git >= 2.28 are likely to return an error if before and last have become unrelated. | ||||
| 			// previously it would return the results of git rev-list --max-count n before last so let's try that... | ||||
| 			stdout, _, err = NewCommand(repo.Ctx, "rev-list"). | ||||
| 			stdout, _, err = NewCommand("rev-list"). | ||||
| 				AddOptionValues("--max-count", strconv.Itoa(limit)). | ||||
| 				AddOptionValues("--skip", strconv.Itoa(skip)). | ||||
| 				AddDynamicArguments(before.ID.String(), last.ID.String()).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 				AddDynamicArguments(before.ID.String(), last.ID.String()).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		} | ||||
| 	} | ||||
| 	if err != nil { | ||||
| @ -343,13 +343,13 @@ func (repo *Repository) CommitsBetweenNotBase(last, before *Commit, baseBranch s | ||||
| 	var stdout []byte | ||||
| 	var err error | ||||
| 	if before == nil { | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "rev-list").AddDynamicArguments(last.ID.String()).AddOptionValues("--not", baseBranch).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 		stdout, _, err = NewCommand("rev-list").AddDynamicArguments(last.ID.String()).AddOptionValues("--not", baseBranch).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	} else { | ||||
| 		stdout, _, err = NewCommand(repo.Ctx, "rev-list").AddDynamicArguments(before.ID.String()+".."+last.ID.String()).AddOptionValues("--not", baseBranch).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 		stdout, _, err = NewCommand("rev-list").AddDynamicArguments(before.ID.String()+".."+last.ID.String()).AddOptionValues("--not", baseBranch).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		if err != nil && strings.Contains(err.Error(), "no merge base") { | ||||
| 			// future versions of git >= 2.28 are likely to return an error if before and last have become unrelated. | ||||
| 			// previously it would return the results of git rev-list before last so let's try that... | ||||
| 			stdout, _, err = NewCommand(repo.Ctx, "rev-list").AddDynamicArguments(before.ID.String(), last.ID.String()).AddOptionValues("--not", baseBranch).RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 			stdout, _, err = NewCommand("rev-list").AddDynamicArguments(before.ID.String(), last.ID.String()).AddOptionValues("--not", baseBranch).RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		} | ||||
| 	} | ||||
| 	if err != nil { | ||||
| @ -395,13 +395,13 @@ func (repo *Repository) CommitsCountBetween(start, end string) (int64, error) { | ||||
| 
 | ||||
| // commitsBefore the limit is depth, not total number of returned commits. | ||||
| func (repo *Repository) commitsBefore(id ObjectID, limit int) ([]*Commit, error) { | ||||
| 	cmd := NewCommand(repo.Ctx, "log", prettyLogFormat) | ||||
| 	cmd := NewCommand("log", prettyLogFormat) | ||||
| 	if limit > 0 { | ||||
| 		cmd.AddOptionFormat("-%d", limit) | ||||
| 	} | ||||
| 	cmd.AddDynamicArguments(id.String()) | ||||
| 
 | ||||
| 	stdout, _, runErr := cmd.RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, runErr := cmd.RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
| @ -438,10 +438,10 @@ func (repo *Repository) getCommitsBeforeLimit(id ObjectID, num int) ([]*Commit, | ||||
| 
 | ||||
| func (repo *Repository) getBranches(env []string, commitID string, limit int) ([]string, error) { | ||||
| 	if DefaultFeatures().CheckVersionAtLeast("2.7.0") { | ||||
| 		stdout, _, err := NewCommand(repo.Ctx, "for-each-ref", "--format=%(refname:strip=2)"). | ||||
| 		stdout, _, err := NewCommand("for-each-ref", "--format=%(refname:strip=2)"). | ||||
| 			AddOptionFormat("--count=%d", limit). | ||||
| 			AddOptionValues("--contains", commitID, BranchPrefix). | ||||
| 			RunStdString(&RunOpts{ | ||||
| 			RunStdString(repo.Ctx, &RunOpts{ | ||||
| 				Dir: repo.Path, | ||||
| 				Env: env, | ||||
| 			}) | ||||
| @ -453,7 +453,7 @@ func (repo *Repository) getBranches(env []string, commitID string, limit int) ([ | ||||
| 		return branches, nil | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "branch").AddOptionValues("--contains", commitID).RunStdString(&RunOpts{ | ||||
| 	stdout, _, err := NewCommand("branch").AddOptionValues("--contains", commitID).RunStdString(repo.Ctx, &RunOpts{ | ||||
| 		Dir: repo.Path, | ||||
| 		Env: env, | ||||
| 	}) | ||||
| @ -495,7 +495,7 @@ func (repo *Repository) GetCommitsFromIDs(commitIDs []string) []*Commit { | ||||
| 
 | ||||
| // IsCommitInBranch check if the commit is on the branch | ||||
| func (repo *Repository) IsCommitInBranch(commitID, branch string) (r bool, err error) { | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "branch", "--contains").AddDynamicArguments(commitID, branch).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("branch", "--contains").AddDynamicArguments(commitID, branch).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return false, err | ||||
| 	} | ||||
| @ -521,10 +521,10 @@ func (repo *Repository) AddLastCommitCache(cacheKey, fullName, sha string) error | ||||
| 
 | ||||
| // GetCommitBranchStart returns the commit where the branch diverged | ||||
| func (repo *Repository) GetCommitBranchStart(env []string, branch, endCommitID string) (string, error) { | ||||
| 	cmd := NewCommand(repo.Ctx, "log", prettyLogFormat) | ||||
| 	cmd := NewCommand("log", prettyLogFormat) | ||||
| 	cmd.AddDynamicArguments(endCommitID) | ||||
| 
 | ||||
| 	stdout, _, runErr := cmd.RunStdBytes(&RunOpts{ | ||||
| 	stdout, _, runErr := cmd.RunStdBytes(repo.Ctx, &RunOpts{ | ||||
| 		Dir: repo.Path, | ||||
| 		Env: env, | ||||
| 	}) | ||||
|  | ||||
| @ -59,7 +59,7 @@ func (repo *Repository) ConvertToGitID(commitID string) (ObjectID, error) { | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	actualCommitID, _, err := NewCommand(repo.Ctx, "rev-parse", "--verify").AddDynamicArguments(commitID).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	actualCommitID, _, err := NewCommand("rev-parse", "--verify").AddDynamicArguments(commitID).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	actualCommitID = strings.TrimSpace(actualCommitID) | ||||
| 	if err != nil { | ||||
| 		if strings.Contains(err.Error(), "unknown revision or path") || | ||||
|  | ||||
| @ -16,7 +16,7 @@ import ( | ||||
| 
 | ||||
| // ResolveReference resolves a name to a reference | ||||
| func (repo *Repository) ResolveReference(name string) (string, error) { | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "show-ref", "--hash").AddDynamicArguments(name).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("show-ref", "--hash").AddDynamicArguments(name).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		if strings.Contains(err.Error(), "not a valid ref") { | ||||
| 			return "", ErrNotExist{name, ""} | ||||
| @ -52,13 +52,13 @@ func (repo *Repository) GetRefCommitID(name string) (string, error) { | ||||
| 
 | ||||
| // SetReference sets the commit ID string of given reference (e.g. branch or tag). | ||||
| func (repo *Repository) SetReference(name, commitID string) error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "update-ref").AddDynamicArguments(name, commitID).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("update-ref").AddDynamicArguments(name, commitID).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // RemoveReference removes the given reference (e.g. branch or tag). | ||||
| func (repo *Repository) RemoveReference(name string) error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "update-ref", "--no-deref", "-d").AddDynamicArguments(name).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("update-ref", "--no-deref", "-d").AddDynamicArguments(name).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| @ -68,7 +68,7 @@ func (repo *Repository) IsCommitExist(name string) bool { | ||||
| 		log.Error("IsCommitExist: %v", err) | ||||
| 		return false | ||||
| 	} | ||||
| 	_, _, err := NewCommand(repo.Ctx, "cat-file", "-e").AddDynamicArguments(name).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("cat-file", "-e").AddDynamicArguments(name).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err == nil | ||||
| } | ||||
| 
 | ||||
|  | ||||
| @ -12,7 +12,7 @@ import ( | ||||
| // this requires git v2.18 to be installed | ||||
| func WriteCommitGraph(ctx context.Context, repoPath string) error { | ||||
| 	if DefaultFeatures().CheckVersionAtLeast("2.18") { | ||||
| 		if _, _, err := NewCommand(ctx, "commit-graph", "write").RunStdString(&RunOpts{Dir: repoPath}); err != nil { | ||||
| 		if _, _, err := NewCommand("commit-graph", "write").RunStdString(ctx, &RunOpts{Dir: repoPath}); err != nil { | ||||
| 			return fmt.Errorf("unable to write commit-graph for '%s' : %w", repoPath, err) | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| @ -39,13 +39,13 @@ func (repo *Repository) GetMergeBase(tmpRemote, base, head string) (string, stri | ||||
| 	if tmpRemote != "origin" { | ||||
| 		tmpBaseName := RemotePrefix + tmpRemote + "/tmp_" + base | ||||
| 		// Fetch commit into a temporary branch in order to be able to handle commits and tags | ||||
| 		_, _, err := NewCommand(repo.Ctx, "fetch", "--no-tags").AddDynamicArguments(tmpRemote).AddDashesAndList(base + ":" + tmpBaseName).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 		_, _, err := NewCommand("fetch", "--no-tags").AddDynamicArguments(tmpRemote).AddDashesAndList(base+":"+tmpBaseName).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		if err == nil { | ||||
| 			base = tmpBaseName | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "merge-base").AddDashesAndList(base, head).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("merge-base").AddDashesAndList(base, head).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return strings.TrimSpace(stdout), base, err | ||||
| } | ||||
| 
 | ||||
| @ -94,9 +94,9 @@ func (repo *Repository) GetCompareInfo(basePath, baseBranch, headBranch string, | ||||
| 		if !fileOnly { | ||||
| 			// avoid: ambiguous argument 'refs/a...refs/b': unknown revision or path not in the working tree. Use '--': 'git <command> [<revision>...] -- [<file>...]' | ||||
| 			var logs []byte | ||||
| 			logs, _, err = NewCommand(repo.Ctx, "log").AddArguments(prettyLogFormat). | ||||
| 				AddDynamicArguments(baseCommitID + separator + headBranch).AddArguments("--"). | ||||
| 				RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 			logs, _, err = NewCommand("log").AddArguments(prettyLogFormat). | ||||
| 				AddDynamicArguments(baseCommitID+separator+headBranch).AddArguments("--"). | ||||
| 				RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 			if err != nil { | ||||
| 				return nil, err | ||||
| 			} | ||||
| @ -150,8 +150,8 @@ func (repo *Repository) GetDiffNumChangedFiles(base, head string, directComparis | ||||
| 	} | ||||
| 
 | ||||
| 	// avoid: ambiguous argument 'refs/a...refs/b': unknown revision or path not in the working tree. Use '--': 'git <command> [<revision>...] -- [<file>...]' | ||||
| 	if err := NewCommand(repo.Ctx, "diff", "-z", "--name-only").AddDynamicArguments(base + separator + head).AddArguments("--"). | ||||
| 		Run(&RunOpts{ | ||||
| 	if err := NewCommand("diff", "-z", "--name-only").AddDynamicArguments(base+separator+head).AddArguments("--"). | ||||
| 		Run(repo.Ctx, &RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: w, | ||||
| 			Stderr: stderr, | ||||
| @ -161,7 +161,7 @@ func (repo *Repository) GetDiffNumChangedFiles(base, head string, directComparis | ||||
| 			// previously it would return the results of git diff -z --name-only base head so let's try that... | ||||
| 			w = &lineCountWriter{} | ||||
| 			stderr.Reset() | ||||
| 			if err = NewCommand(repo.Ctx, "diff", "-z", "--name-only").AddDynamicArguments(base, head).AddArguments("--").Run(&RunOpts{ | ||||
| 			if err = NewCommand("diff", "-z", "--name-only").AddDynamicArguments(base, head).AddArguments("--").Run(repo.Ctx, &RunOpts{ | ||||
| 				Dir:    repo.Path, | ||||
| 				Stdout: w, | ||||
| 				Stderr: stderr, | ||||
| @ -189,8 +189,8 @@ func GetDiffShortStat(ctx context.Context, repoPath string, trustedArgs TrustedC | ||||
| 	// $ git diff --shortstat 1ebb35b98889ff77299f24d82da426b434b0cca0...788b8b1440462d477f45b0088875 | ||||
| 	// we get: | ||||
| 	// " 9902 files changed, 2034198 insertions(+), 298800 deletions(-)\n" | ||||
| 	cmd := NewCommand(ctx, "diff", "--shortstat").AddArguments(trustedArgs...).AddDynamicArguments(dynamicArgs...) | ||||
| 	stdout, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}) | ||||
| 	cmd := NewCommand("diff", "--shortstat").AddArguments(trustedArgs...).AddDynamicArguments(dynamicArgs...) | ||||
| 	stdout, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}) | ||||
| 	if err != nil { | ||||
| 		return 0, 0, 0, err | ||||
| 	} | ||||
| @ -236,8 +236,8 @@ func parseDiffStat(stdout string) (numFiles, totalAdditions, totalDeletions int, | ||||
| // GetDiff generates and returns patch data between given revisions, optimized for human readability | ||||
| func (repo *Repository) GetDiff(compareArg string, w io.Writer) error { | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	return NewCommand(repo.Ctx, "diff", "-p").AddDynamicArguments(compareArg). | ||||
| 		Run(&RunOpts{ | ||||
| 	return NewCommand("diff", "-p").AddDynamicArguments(compareArg). | ||||
| 		Run(repo.Ctx, &RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: w, | ||||
| 			Stderr: stderr, | ||||
| @ -246,7 +246,7 @@ func (repo *Repository) GetDiff(compareArg string, w io.Writer) error { | ||||
| 
 | ||||
| // GetDiffBinary generates and returns patch data between given revisions, including binary diffs. | ||||
| func (repo *Repository) GetDiffBinary(compareArg string, w io.Writer) error { | ||||
| 	return NewCommand(repo.Ctx, "diff", "-p", "--binary", "--histogram").AddDynamicArguments(compareArg).Run(&RunOpts{ | ||||
| 	return NewCommand("diff", "-p", "--binary", "--histogram").AddDynamicArguments(compareArg).Run(repo.Ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdout: w, | ||||
| 	}) | ||||
| @ -255,8 +255,8 @@ func (repo *Repository) GetDiffBinary(compareArg string, w io.Writer) error { | ||||
| // GetPatch generates and returns format-patch data between given revisions, able to be used with `git apply` | ||||
| func (repo *Repository) GetPatch(compareArg string, w io.Writer) error { | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	return NewCommand(repo.Ctx, "format-patch", "--binary", "--stdout").AddDynamicArguments(compareArg). | ||||
| 		Run(&RunOpts{ | ||||
| 	return NewCommand("format-patch", "--binary", "--stdout").AddDynamicArguments(compareArg). | ||||
| 		Run(repo.Ctx, &RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: w, | ||||
| 			Stderr: stderr, | ||||
| @ -271,13 +271,13 @@ func (repo *Repository) GetFilesChangedBetween(base, head string) ([]string, err | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| 	cmd := NewCommand(repo.Ctx, "diff-tree", "--name-only", "--root", "--no-commit-id", "-r", "-z") | ||||
| 	cmd := NewCommand("diff-tree", "--name-only", "--root", "--no-commit-id", "-r", "-z") | ||||
| 	if base == objectFormat.EmptyObjectID().String() { | ||||
| 		cmd.AddDynamicArguments(head) | ||||
| 	} else { | ||||
| 		cmd.AddDynamicArguments(base, head) | ||||
| 	} | ||||
| 	stdout, _, err := cmd.RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := cmd.RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
|  | ||||
| @ -33,7 +33,7 @@ func (repo *Repository) GetDefaultPublicGPGKey(forceUpdate bool) (*GPGSettings, | ||||
| 		Sign: true, | ||||
| 	} | ||||
| 
 | ||||
| 	value, _, _ := NewCommand(repo.Ctx, "config", "--get", "commit.gpgsign").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	value, _, _ := NewCommand("config", "--get", "commit.gpgsign").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	sign, valid := ParseBool(strings.TrimSpace(value)) | ||||
| 	if !sign || !valid { | ||||
| 		gpgSettings.Sign = false | ||||
| @ -41,13 +41,13 @@ func (repo *Repository) GetDefaultPublicGPGKey(forceUpdate bool) (*GPGSettings, | ||||
| 		return gpgSettings, nil | ||||
| 	} | ||||
| 
 | ||||
| 	signingKey, _, _ := NewCommand(repo.Ctx, "config", "--get", "user.signingkey").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	signingKey, _, _ := NewCommand("config", "--get", "user.signingkey").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	gpgSettings.KeyID = strings.TrimSpace(signingKey) | ||||
| 
 | ||||
| 	defaultEmail, _, _ := NewCommand(repo.Ctx, "config", "--get", "user.email").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	defaultEmail, _, _ := NewCommand("config", "--get", "user.email").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	gpgSettings.Email = strings.TrimSpace(defaultEmail) | ||||
| 
 | ||||
| 	defaultName, _, _ := NewCommand(repo.Ctx, "config", "--get", "user.name").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	defaultName, _, _ := NewCommand("config", "--get", "user.name").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	gpgSettings.Name = strings.TrimSpace(defaultName) | ||||
| 
 | ||||
| 	if err := gpgSettings.LoadPublicKeyContent(); err != nil { | ||||
|  | ||||
| @ -22,7 +22,7 @@ func (repo *Repository) ReadTreeToIndex(treeish string, indexFilename ...string) | ||||
| 	} | ||||
| 
 | ||||
| 	if len(treeish) != objectFormat.FullLength() { | ||||
| 		res, _, err := NewCommand(repo.Ctx, "rev-parse", "--verify").AddDynamicArguments(treeish).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 		res, _, err := NewCommand("rev-parse", "--verify").AddDynamicArguments(treeish).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		if err != nil { | ||||
| 			return err | ||||
| 		} | ||||
| @ -42,7 +42,7 @@ func (repo *Repository) readTreeToIndex(id ObjectID, indexFilename ...string) er | ||||
| 	if len(indexFilename) > 0 { | ||||
| 		env = append(os.Environ(), "GIT_INDEX_FILE="+indexFilename[0]) | ||||
| 	} | ||||
| 	_, _, err := NewCommand(repo.Ctx, "read-tree").AddDynamicArguments(id.String()).RunStdString(&RunOpts{Dir: repo.Path, Env: env}) | ||||
| 	_, _, err := NewCommand("read-tree").AddDynamicArguments(id.String()).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path, Env: env}) | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| @ -83,14 +83,14 @@ func (repo *Repository) ReadTreeToTemporaryIndex(treeish string) (tmpIndexFilena | ||||
| 
 | ||||
| // EmptyIndex empties the index | ||||
| func (repo *Repository) EmptyIndex() error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "read-tree", "--empty").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("read-tree", "--empty").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // LsFiles checks if the given filenames are in the index | ||||
| func (repo *Repository) LsFiles(filenames ...string) ([]string, error) { | ||||
| 	cmd := NewCommand(repo.Ctx, "ls-files", "-z").AddDashesAndList(filenames...) | ||||
| 	res, _, err := cmd.RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	cmd := NewCommand("ls-files", "-z").AddDashesAndList(filenames...) | ||||
| 	res, _, err := cmd.RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| @ -108,7 +108,7 @@ func (repo *Repository) RemoveFilesFromIndex(filenames ...string) error { | ||||
| 	if err != nil { | ||||
| 		return err | ||||
| 	} | ||||
| 	cmd := NewCommand(repo.Ctx, "update-index", "--remove", "-z", "--index-info") | ||||
| 	cmd := NewCommand("update-index", "--remove", "-z", "--index-info") | ||||
| 	stdout := new(bytes.Buffer) | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	buffer := new(bytes.Buffer) | ||||
| @ -118,7 +118,7 @@ func (repo *Repository) RemoveFilesFromIndex(filenames ...string) error { | ||||
| 			buffer.WriteString("0 blob " + objectFormat.EmptyObjectID().String() + "\t" + file + "\000") | ||||
| 		} | ||||
| 	} | ||||
| 	return cmd.Run(&RunOpts{ | ||||
| 	return cmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdin:  bytes.NewReader(buffer.Bytes()), | ||||
| 		Stdout: stdout, | ||||
| @ -134,7 +134,7 @@ type IndexObjectInfo struct { | ||||
| 
 | ||||
| // AddObjectsToIndex adds the provided object hashes to the index at the provided filenames | ||||
| func (repo *Repository) AddObjectsToIndex(objects ...IndexObjectInfo) error { | ||||
| 	cmd := NewCommand(repo.Ctx, "update-index", "--add", "--replace", "-z", "--index-info") | ||||
| 	cmd := NewCommand("update-index", "--add", "--replace", "-z", "--index-info") | ||||
| 	stdout := new(bytes.Buffer) | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	buffer := new(bytes.Buffer) | ||||
| @ -142,7 +142,7 @@ func (repo *Repository) AddObjectsToIndex(objects ...IndexObjectInfo) error { | ||||
| 		// using format: mode SP type SP sha1 TAB path | ||||
| 		buffer.WriteString(object.Mode + " blob " + object.Object.String() + "\t" + object.Filename + "\000") | ||||
| 	} | ||||
| 	return cmd.Run(&RunOpts{ | ||||
| 	return cmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdin:  bytes.NewReader(buffer.Bytes()), | ||||
| 		Stdout: stdout, | ||||
| @ -157,7 +157,7 @@ func (repo *Repository) AddObjectToIndex(mode string, object ObjectID, filename | ||||
| 
 | ||||
| // WriteTree writes the current index as a tree to the object db and returns its hash | ||||
| func (repo *Repository) WriteTree() (*Tree, error) { | ||||
| 	stdout, _, runErr := NewCommand(repo.Ctx, "write-tree").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, runErr := NewCommand("write-tree").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
|  | ||||
| @ -68,13 +68,13 @@ func (repo *Repository) HashObject(reader io.Reader) (ObjectID, error) { | ||||
| func (repo *Repository) hashObject(reader io.Reader, save bool) (string, error) { | ||||
| 	var cmd *Command | ||||
| 	if save { | ||||
| 		cmd = NewCommand(repo.Ctx, "hash-object", "-w", "--stdin") | ||||
| 		cmd = NewCommand("hash-object", "-w", "--stdin") | ||||
| 	} else { | ||||
| 		cmd = NewCommand(repo.Ctx, "hash-object", "--stdin") | ||||
| 		cmd = NewCommand("hash-object", "--stdin") | ||||
| 	} | ||||
| 	stdout := new(bytes.Buffer) | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	err := cmd.Run(&RunOpts{ | ||||
| 	err := cmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdin:  reader, | ||||
| 		Stdout: stdout, | ||||
|  | ||||
| @ -18,7 +18,7 @@ func (repo *Repository) GetRefs() ([]*Reference, error) { | ||||
| // ListOccurrences lists all refs of the given refType the given commit appears in sorted by creation date DESC | ||||
| // refType should only be a literal "branch" or "tag" and nothing else | ||||
| func (repo *Repository) ListOccurrences(ctx context.Context, refType, commitSHA string) ([]string, error) { | ||||
| 	cmd := NewCommand(ctx) | ||||
| 	cmd := NewCommand() | ||||
| 	if refType == "branch" { | ||||
| 		cmd.AddArguments("branch") | ||||
| 	} else if refType == "tag" { | ||||
| @ -26,7 +26,7 @@ func (repo *Repository) ListOccurrences(ctx context.Context, refType, commitSHA | ||||
| 	} else { | ||||
| 		return nil, util.NewInvalidArgumentErrorf(`can only use "branch" or "tag" for refType, but got %q`, refType) | ||||
| 	} | ||||
| 	stdout, _, err := cmd.AddArguments("--no-color", "--sort=-creatordate", "--contains").AddDynamicArguments(commitSHA).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := cmd.AddArguments("--no-color", "--sort=-creatordate", "--contains").AddDynamicArguments(commitSHA).RunStdString(ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
|  | ||||
| @ -21,7 +21,7 @@ func (repo *Repository) GetRefsFiltered(pattern string) ([]*Reference, error) { | ||||
| 
 | ||||
| 	go func() { | ||||
| 		stderrBuilder := &strings.Builder{} | ||||
| 		err := NewCommand(repo.Ctx, "for-each-ref").Run(&RunOpts{ | ||||
| 		err := NewCommand("for-each-ref").Run(repo.Ctx, &RunOpts{ | ||||
| 			Dir:    repo.Path, | ||||
| 			Stdout: stdoutWriter, | ||||
| 			Stderr: stderrBuilder, | ||||
|  | ||||
| @ -40,7 +40,7 @@ func (repo *Repository) GetCodeActivityStats(fromTime time.Time, branch string) | ||||
| 
 | ||||
| 	since := fromTime.Format(time.RFC3339) | ||||
| 
 | ||||
| 	stdout, _, runErr := NewCommand(repo.Ctx, "rev-list", "--count", "--no-merges", "--branches=*", "--date=iso").AddOptionFormat("--since='%s'", since).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, runErr := NewCommand("rev-list", "--count", "--no-merges", "--branches=*", "--date=iso").AddOptionFormat("--since='%s'", since).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
| @ -60,7 +60,7 @@ func (repo *Repository) GetCodeActivityStats(fromTime time.Time, branch string) | ||||
| 		_ = stdoutWriter.Close() | ||||
| 	}() | ||||
| 
 | ||||
| 	gitCmd := NewCommand(repo.Ctx, "log", "--numstat", "--no-merges", "--pretty=format:---%n%h%n%aN%n%aE%n", "--date=iso").AddOptionFormat("--since='%s'", since) | ||||
| 	gitCmd := NewCommand("log", "--numstat", "--no-merges", "--pretty=format:---%n%h%n%aN%n%aE%n", "--date=iso").AddOptionFormat("--since='%s'", since) | ||||
| 	if len(branch) == 0 { | ||||
| 		gitCmd.AddArguments("--branches=*") | ||||
| 	} else { | ||||
| @ -68,7 +68,7 @@ func (repo *Repository) GetCodeActivityStats(fromTime time.Time, branch string) | ||||
| 	} | ||||
| 
 | ||||
| 	stderr := new(strings.Builder) | ||||
| 	err = gitCmd.Run(&RunOpts{ | ||||
| 	err = gitCmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Env:    []string{}, | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdout: stdoutWriter, | ||||
|  | ||||
| @ -24,13 +24,13 @@ func IsTagExist(ctx context.Context, repoPath, name string) bool { | ||||
| 
 | ||||
| // CreateTag create one tag in the repository | ||||
| func (repo *Repository) CreateTag(name, revision string) error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "tag").AddDashesAndList(name, revision).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("tag").AddDashesAndList(name, revision).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| // CreateAnnotatedTag create one annotated tag in the repository | ||||
| func (repo *Repository) CreateAnnotatedTag(name, message, revision string) error { | ||||
| 	_, _, err := NewCommand(repo.Ctx, "tag", "-a", "-m").AddDynamicArguments(message).AddDashesAndList(name, revision).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	_, _, err := NewCommand("tag", "-a", "-m").AddDynamicArguments(message).AddDashesAndList(name, revision).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
| @ -40,7 +40,7 @@ func (repo *Repository) GetTagNameBySHA(sha string) (string, error) { | ||||
| 		return "", fmt.Errorf("SHA is too short: %s", sha) | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "show-ref", "--tags", "-d").RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("show-ref", "--tags", "-d").RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return "", err | ||||
| 	} | ||||
| @ -63,7 +63,7 @@ func (repo *Repository) GetTagNameBySHA(sha string) (string, error) { | ||||
| 
 | ||||
| // GetTagID returns the object ID for a tag (annotated tags have both an object SHA AND a commit SHA) | ||||
| func (repo *Repository) GetTagID(name string) (string, error) { | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "show-ref", "--tags").AddDashesAndList(name).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 	stdout, _, err := NewCommand("show-ref", "--tags").AddDashesAndList(name).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return "", err | ||||
| 	} | ||||
| @ -123,9 +123,9 @@ func (repo *Repository) GetTagInfos(page, pageSize int) ([]*Tag, int, error) { | ||||
| 	rc := &RunOpts{Dir: repo.Path, Stdout: stdoutWriter, Stderr: &stderr} | ||||
| 
 | ||||
| 	go func() { | ||||
| 		err := NewCommand(repo.Ctx, "for-each-ref"). | ||||
| 		err := NewCommand("for-each-ref"). | ||||
| 			AddOptionFormat("--format=%s", forEachRefFmt.Flag()). | ||||
| 			AddArguments("--sort", "-*creatordate", "refs/tags").Run(rc) | ||||
| 			AddArguments("--sort", "-*creatordate", "refs/tags").Run(repo.Ctx, rc) | ||||
| 		if err != nil { | ||||
| 			_ = stdoutWriter.CloseWithError(ConcatenateError(err, stderr.String())) | ||||
| 		} else { | ||||
|  | ||||
| @ -33,7 +33,7 @@ func (repo *Repository) CommitTree(author, committer *Signature, tree *Tree, opt | ||||
| 		"GIT_COMMITTER_EMAIL="+committer.Email, | ||||
| 		"GIT_COMMITTER_DATE="+commitTimeStr, | ||||
| 	) | ||||
| 	cmd := NewCommand(repo.Ctx, "commit-tree").AddDynamicArguments(tree.ID.String()) | ||||
| 	cmd := NewCommand("commit-tree").AddDynamicArguments(tree.ID.String()) | ||||
| 
 | ||||
| 	for _, parent := range opts.Parents { | ||||
| 		cmd.AddArguments("-p").AddDynamicArguments(parent) | ||||
| @ -53,7 +53,7 @@ func (repo *Repository) CommitTree(author, committer *Signature, tree *Tree, opt | ||||
| 
 | ||||
| 	stdout := new(bytes.Buffer) | ||||
| 	stderr := new(bytes.Buffer) | ||||
| 	err := cmd.Run(&RunOpts{ | ||||
| 	err := cmd.Run(repo.Ctx, &RunOpts{ | ||||
| 		Env:    env, | ||||
| 		Dir:    repo.Path, | ||||
| 		Stdin:  messageBytes, | ||||
|  | ||||
| @ -36,7 +36,7 @@ func (repo *Repository) GetTree(idStr string) (*Tree, error) { | ||||
| 	} | ||||
| 
 | ||||
| 	if len(idStr) != objectFormat.FullLength() { | ||||
| 		res, _, err := NewCommand(repo.Ctx, "rev-parse", "--verify").AddDynamicArguments(idStr).RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 		res, _, err := NewCommand("rev-parse", "--verify").AddDynamicArguments(idStr).RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 		if err != nil { | ||||
| 			return nil, err | ||||
| 		} | ||||
|  | ||||
| @ -45,7 +45,7 @@ func GetTemplateSubmoduleCommits(ctx context.Context, repoPath string) (submodul | ||||
| 			return scanner.Err() | ||||
| 		}, | ||||
| 	} | ||||
| 	err = NewCommand(ctx, "ls-tree", "-r", "--", "HEAD").Run(opts) | ||||
| 	err = NewCommand("ls-tree", "-r", "--", "HEAD").Run(ctx, opts) | ||||
| 	if err != nil { | ||||
| 		return nil, fmt.Errorf("GetTemplateSubmoduleCommits: error running git ls-tree: %v", err) | ||||
| 	} | ||||
| @ -56,8 +56,8 @@ func GetTemplateSubmoduleCommits(ctx context.Context, repoPath string) (submodul | ||||
| // It is only for generating new repos based on existing template, requires the .gitmodules file to be already present in the work dir. | ||||
| func AddTemplateSubmoduleIndexes(ctx context.Context, repoPath string, submodules []TemplateSubmoduleCommit) error { | ||||
| 	for _, submodule := range submodules { | ||||
| 		cmd := NewCommand(ctx, "update-index", "--add", "--cacheinfo", "160000").AddDynamicArguments(submodule.Commit, submodule.Path) | ||||
| 		if stdout, _, err := cmd.RunStdString(&RunOpts{Dir: repoPath}); err != nil { | ||||
| 		cmd := NewCommand("update-index", "--add", "--cacheinfo", "160000").AddDynamicArguments(submodule.Commit, submodule.Path) | ||||
| 		if stdout, _, err := cmd.RunStdString(ctx, &RunOpts{Dir: repoPath}); err != nil { | ||||
| 			log.Error("Unable to add %s as submodule to repo %s: stdout %s\nError: %v", submodule.Path, repoPath, stdout, err) | ||||
| 			return err | ||||
| 		} | ||||
|  | ||||
| @ -30,14 +30,14 @@ func TestAddTemplateSubmoduleIndexes(t *testing.T) { | ||||
| 	ctx := t.Context() | ||||
| 	tmpDir := t.TempDir() | ||||
| 	var err error | ||||
| 	_, _, err = NewCommand(ctx, "init").RunStdString(&RunOpts{Dir: tmpDir}) | ||||
| 	_, _, err = NewCommand("init").RunStdString(ctx, &RunOpts{Dir: tmpDir}) | ||||
| 	require.NoError(t, err) | ||||
| 	_ = os.Mkdir(filepath.Join(tmpDir, "new-dir"), 0o755) | ||||
| 	err = AddTemplateSubmoduleIndexes(ctx, tmpDir, []TemplateSubmoduleCommit{{Path: "new-dir", Commit: "1234567890123456789012345678901234567890"}}) | ||||
| 	require.NoError(t, err) | ||||
| 	_, _, err = NewCommand(ctx, "add", "--all").RunStdString(&RunOpts{Dir: tmpDir}) | ||||
| 	_, _, err = NewCommand("add", "--all").RunStdString(ctx, &RunOpts{Dir: tmpDir}) | ||||
| 	require.NoError(t, err) | ||||
| 	_, _, err = NewCommand(ctx, "-c", "user.name=a", "-c", "user.email=b", "commit", "-m=test").RunStdString(&RunOpts{Dir: tmpDir}) | ||||
| 	_, _, err = NewCommand("-c", "user.name=a", "-c", "user.email=b", "commit", "-m=test").RunStdString(ctx, &RunOpts{Dir: tmpDir}) | ||||
| 	require.NoError(t, err) | ||||
| 	submodules, err := GetTemplateSubmoduleCommits(DefaultContext, tmpDir) | ||||
| 	require.NoError(t, err) | ||||
|  | ||||
| @ -48,10 +48,10 @@ func (t *Tree) SubTree(rpath string) (*Tree, error) { | ||||
| 
 | ||||
| // LsTree checks if the given filenames are in the tree | ||||
| func (repo *Repository) LsTree(ref string, filenames ...string) ([]string, error) { | ||||
| 	cmd := NewCommand(repo.Ctx, "ls-tree", "-z", "--name-only"). | ||||
| 	cmd := NewCommand("ls-tree", "-z", "--name-only"). | ||||
| 		AddDashesAndList(append([]string{ref}, filenames...)...) | ||||
| 
 | ||||
| 	res, _, err := cmd.RunStdBytes(&RunOpts{Dir: repo.Path}) | ||||
| 	res, _, err := cmd.RunStdBytes(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
| @ -65,9 +65,9 @@ func (repo *Repository) LsTree(ref string, filenames ...string) ([]string, error | ||||
| 
 | ||||
| // GetTreePathLatestCommit returns the latest commit of a tree path | ||||
| func (repo *Repository) GetTreePathLatestCommit(refName, treePath string) (*Commit, error) { | ||||
| 	stdout, _, err := NewCommand(repo.Ctx, "rev-list", "-1"). | ||||
| 	stdout, _, err := NewCommand("rev-list", "-1"). | ||||
| 		AddDynamicArguments(refName).AddDashesAndList(treePath). | ||||
| 		RunStdString(&RunOpts{Dir: repo.Path}) | ||||
| 		RunStdString(repo.Ctx, &RunOpts{Dir: repo.Path}) | ||||
| 	if err != nil { | ||||
| 		return nil, err | ||||
| 	} | ||||
|  | ||||
| @ -70,7 +70,7 @@ func (t *Tree) ListEntries() (Entries, error) { | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, runErr := NewCommand(t.repo.Ctx, "ls-tree", "-l").AddDynamicArguments(t.ID.String()).RunStdBytes(&RunOpts{Dir: t.repo.Path}) | ||||
| 	stdout, _, runErr := NewCommand("ls-tree", "-l").AddDynamicArguments(t.ID.String()).RunStdBytes(t.repo.Ctx, &RunOpts{Dir: t.repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		if strings.Contains(runErr.Error(), "fatal: Not a valid object name") || strings.Contains(runErr.Error(), "fatal: not a tree object") { | ||||
| 			return nil, ErrNotExist{ | ||||
| @ -96,10 +96,10 @@ func (t *Tree) listEntriesRecursive(extraArgs TrustedCmdArgs) (Entries, error) { | ||||
| 		return t.entriesRecursive, nil | ||||
| 	} | ||||
| 
 | ||||
| 	stdout, _, runErr := NewCommand(t.repo.Ctx, "ls-tree", "-t", "-r"). | ||||
| 	stdout, _, runErr := NewCommand("ls-tree", "-t", "-r"). | ||||
| 		AddArguments(extraArgs...). | ||||
| 		AddDynamicArguments(t.ID.String()). | ||||
| 		RunStdBytes(&RunOpts{Dir: t.repo.Path}) | ||||
| 		RunStdBytes(t.repo.Ctx, &RunOpts{Dir: t.repo.Path}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
|  | ||||
| @ -33,9 +33,9 @@ func GetBranchCommitID(ctx context.Context, repo Repository, branch string) (str | ||||
| 
 | ||||
| // SetDefaultBranch sets default branch of repository. | ||||
| func SetDefaultBranch(ctx context.Context, repo Repository, name string) error { | ||||
| 	_, _, err := git.NewCommand(ctx, "symbolic-ref", "HEAD"). | ||||
| 		AddDynamicArguments(git.BranchPrefix + name). | ||||
| 		RunStdString(&git.RunOpts{Dir: repoPath(repo)}) | ||||
| 	_, _, err := git.NewCommand("symbolic-ref", "HEAD"). | ||||
| 		AddDynamicArguments(git.BranchPrefix+name). | ||||
| 		RunStdString(ctx, &git.RunOpts{Dir: repoPath(repo)}) | ||||
| 	return err | ||||
| } | ||||
| 
 | ||||
|  | ||||
| @ -158,7 +158,7 @@ func (b *Indexer) addUpdate(ctx context.Context, batchWriter git.WriteCloserErro | ||||
| 	var err error | ||||
| 	if !update.Sized { | ||||
| 		var stdout string | ||||
| 		stdout, _, err = git.NewCommand(ctx, "cat-file", "-s").AddDynamicArguments(update.BlobSha).RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		stdout, _, err = git.NewCommand("cat-file", "-s").AddDynamicArguments(update.BlobSha).RunStdString(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		if err != nil { | ||||
| 			return err | ||||
| 		} | ||||
|  | ||||
| @ -143,7 +143,7 @@ func (b *Indexer) addUpdate(ctx context.Context, batchWriter git.WriteCloserErro | ||||
| 	var err error | ||||
| 	if !update.Sized { | ||||
| 		var stdout string | ||||
| 		stdout, _, err = git.NewCommand(ctx, "cat-file", "-s").AddDynamicArguments(update.BlobSha).RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		stdout, _, err = git.NewCommand("cat-file", "-s").AddDynamicArguments(update.BlobSha).RunStdString(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		if err != nil { | ||||
| 			return nil, err | ||||
| 		} | ||||
|  | ||||
| @ -16,7 +16,7 @@ import ( | ||||
| ) | ||||
| 
 | ||||
| func getDefaultBranchSha(ctx context.Context, repo *repo_model.Repository) (string, error) { | ||||
| 	stdout, _, err := git.NewCommand(ctx, "show-ref", "-s").AddDynamicArguments(git.BranchPrefix + repo.DefaultBranch).RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 	stdout, _, err := git.NewCommand("show-ref", "-s").AddDynamicArguments(git.BranchPrefix+repo.DefaultBranch).RunStdString(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 	if err != nil { | ||||
| 		return "", err | ||||
| 	} | ||||
| @ -32,8 +32,8 @@ func getRepoChanges(ctx context.Context, repo *repo_model.Repository, revision s | ||||
| 
 | ||||
| 	needGenesis := len(status.CommitSha) == 0 | ||||
| 	if !needGenesis { | ||||
| 		hasAncestorCmd := git.NewCommand(ctx, "merge-base").AddDynamicArguments(status.CommitSha, revision) | ||||
| 		stdout, _, _ := hasAncestorCmd.RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		hasAncestorCmd := git.NewCommand("merge-base").AddDynamicArguments(status.CommitSha, revision) | ||||
| 		stdout, _, _ := hasAncestorCmd.RunStdString(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		needGenesis = len(stdout) == 0 | ||||
| 	} | ||||
| 
 | ||||
| @ -86,7 +86,7 @@ func parseGitLsTreeOutput(stdout []byte) ([]internal.FileUpdate, error) { | ||||
| // genesisChanges get changes to add repo to the indexer for the first time | ||||
| func genesisChanges(ctx context.Context, repo *repo_model.Repository, revision string) (*internal.RepoChanges, error) { | ||||
| 	var changes internal.RepoChanges | ||||
| 	stdout, _, runErr := git.NewCommand(ctx, "ls-tree", "--full-tree", "-l", "-r").AddDynamicArguments(revision).RunStdBytes(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 	stdout, _, runErr := git.NewCommand("ls-tree", "--full-tree", "-l", "-r").AddDynamicArguments(revision).RunStdBytes(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 	if runErr != nil { | ||||
| 		return nil, runErr | ||||
| 	} | ||||
| @ -98,8 +98,8 @@ func genesisChanges(ctx context.Context, repo *repo_model.Repository, revision s | ||||
| 
 | ||||
| // nonGenesisChanges get changes since the previous indexer update | ||||
| func nonGenesisChanges(ctx context.Context, repo *repo_model.Repository, revision string) (*internal.RepoChanges, error) { | ||||
| 	diffCmd := git.NewCommand(ctx, "diff", "--name-status").AddDynamicArguments(repo.CodeIndexerStatus.CommitSha, revision) | ||||
| 	stdout, _, runErr := diffCmd.RunStdString(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 	diffCmd := git.NewCommand("diff", "--name-status").AddDynamicArguments(repo.CodeIndexerStatus.CommitSha, revision) | ||||
| 	stdout, _, runErr := diffCmd.RunStdString(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 	if runErr != nil { | ||||
| 		// previous commit sha may have been removed by a force push, so | ||||
| 		// try rebuilding from scratch | ||||
| @ -115,9 +115,9 @@ func nonGenesisChanges(ctx context.Context, repo *repo_model.Repository, revisio | ||||
| 	updatedFilenames := make([]string, 0, 10) | ||||
| 
 | ||||
| 	updateChanges := func() error { | ||||
| 		cmd := git.NewCommand(ctx, "ls-tree", "--full-tree", "-l").AddDynamicArguments(revision). | ||||
| 		cmd := git.NewCommand("ls-tree", "--full-tree", "-l").AddDynamicArguments(revision). | ||||
| 			AddDashesAndList(updatedFilenames...) | ||||
| 		lsTreeStdout, _, err := cmd.RunStdBytes(&git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		lsTreeStdout, _, err := cmd.RunStdBytes(ctx, &git.RunOpts{Dir: repo.RepoPath()}) | ||||
| 		if err != nil { | ||||
| 			return err | ||||
| 		} | ||||
|  | ||||
| @ -62,6 +62,10 @@ func TestSanitizer(t *testing.T) { | ||||
| 		`<a href="javascript:alert('xss')">bad</a>`, `bad`, | ||||
| 		`<a href="vbscript:no">bad</a>`, `bad`, | ||||
| 		`<a href="data:1234">bad</a>`, `bad`, | ||||
| 
 | ||||
| 		// Some classes and attributes are used by the frontend framework and will execute JS code, so make sure they are removed | ||||
| 		`<div class="link-action" data-attr-class="foo" data-url="xxx">txt</div>`, `<div data-attr-class="foo">txt</div>`, | ||||
| 		`<div class="form-fetch-action" data-markdown-generated-content="bar" data-global-init="a" data-global-click="b">txt</div>`, `<div data-markdown-generated-content="bar">txt</div>`, | ||||
| 	} | ||||
| 
 | ||||
| 	for i := 0; i < len(testCases); i += 2 { | ||||
|  | ||||
| @ -17,9 +17,9 @@ import ( | ||||
| ) | ||||
| 
 | ||||
| var ( | ||||
| 	ErrInvalidStructure = util.SilentWrap{Message: "package structure is invalid", Err: util.ErrInvalidArgument} | ||||
| 	ErrInvalidName      = util.SilentWrap{Message: "package name is invalid", Err: util.ErrInvalidArgument} | ||||
| 	ErrInvalidVersion   = util.SilentWrap{Message: "package version is invalid", Err: util.ErrInvalidArgument} | ||||
| 	ErrInvalidStructure = util.NewInvalidArgumentErrorf("package structure is invalid") | ||||
| 	ErrInvalidName      = util.NewInvalidArgumentErrorf("package name is invalid") | ||||
| 	ErrInvalidVersion   = util.NewInvalidArgumentErrorf("package version is invalid") | ||||
| ) | ||||
| 
 | ||||
| const ( | ||||
|  | ||||
| @ -1,13 +0,0 @@ | ||||
| // Copyright 2022 The Gitea Authors. All rights reserved. | ||||
| // SPDX-License-Identifier: MIT | ||||
| 
 | ||||
| package i18n | ||||
| 
 | ||||
| import ( | ||||
| 	"code.gitea.io/gitea/modules/util" | ||||
| ) | ||||
| 
 | ||||
| var ( | ||||
| 	ErrLocaleAlreadyExist = util.SilentWrap{Message: "lang already exists", Err: util.ErrAlreadyExist} | ||||
| 	ErrUncertainArguments = util.SilentWrap{Message: "arguments to i18n should not contain uncertain slices", Err: util.ErrInvalidArgument} | ||||
| ) | ||||
| @ -4,6 +4,7 @@ | ||||
| package i18n | ||||
| 
 | ||||
| import ( | ||||
| 	"errors" | ||||
| 	"fmt" | ||||
| 	"reflect" | ||||
| ) | ||||
| @ -30,7 +31,7 @@ func Format(format string, args ...any) (msg string, err error) { | ||||
| 					fmtArgs = append(fmtArgs, val.Index(i).Interface()) | ||||
| 				} | ||||
| 			} else { | ||||
| 				err = ErrUncertainArguments | ||||
| 				err = errors.New("arguments to i18n should not contain uncertain slices") | ||||
| 				break | ||||
| 			} | ||||
| 		} else { | ||||
|  | ||||
| @ -4,6 +4,7 @@ | ||||
| package i18n | ||||
| 
 | ||||
| import ( | ||||
| 	"errors" | ||||
| 	"fmt" | ||||
| 	"html/template" | ||||
| 	"slices" | ||||
| @ -41,7 +42,7 @@ func NewLocaleStore() LocaleStore { | ||||
| // AddLocaleByIni adds locale by ini into the store | ||||
| func (store *localeStore) AddLocaleByIni(langName, langDesc string, source, moreSource []byte) error { | ||||
| 	if _, ok := store.localeMap[langName]; ok { | ||||
| 		return ErrLocaleAlreadyExist | ||||
| 		return errors.New("lang has already been added") | ||||
| 	} | ||||
| 
 | ||||
| 	store.langNames = append(store.langNames, langName) | ||||
|  | ||||
| @ -22,74 +22,74 @@ var ( | ||||
| 	ErrUnprocessableContent = errors.New("unprocessable content") | ||||
| ) | ||||
| 
 | ||||
| // SilentWrap provides a simple wrapper for a wrapped error where the wrapped error message plays no part in the error message | ||||
| // errorWrapper provides a simple wrapper for a wrapped error where the wrapped error message plays no part in the error message | ||||
| // Especially useful for "untyped" errors created with "errors.New(…)" that can be classified as 'invalid argument', 'permission denied', 'exists already', or 'does not exist' | ||||
| type SilentWrap struct { | ||||
| type errorWrapper struct { | ||||
| 	Message string | ||||
| 	Err     error | ||||
| } | ||||
| 
 | ||||
| // Error returns the message | ||||
| func (w SilentWrap) Error() string { | ||||
| func (w errorWrapper) Error() string { | ||||
| 	return w.Message | ||||
| } | ||||
| 
 | ||||
| // Unwrap returns the underlying error | ||||
| func (w SilentWrap) Unwrap() error { | ||||
| func (w errorWrapper) Unwrap() error { | ||||
| 	return w.Err | ||||
| } | ||||
| 
 | ||||
| type LocaleWrap struct { | ||||
| type LocaleWrapper struct { | ||||
| 	err    error | ||||
| 	TrKey  string | ||||
| 	TrArgs []any | ||||
| } | ||||
| 
 | ||||
| // Error returns the message | ||||
| func (w LocaleWrap) Error() string { | ||||
| func (w LocaleWrapper) Error() string { | ||||
| 	return w.err.Error() | ||||
| } | ||||
| 
 | ||||
| // Unwrap returns the underlying error | ||||
| func (w LocaleWrap) Unwrap() error { | ||||
| func (w LocaleWrapper) Unwrap() error { | ||||
| 	return w.err | ||||
| } | ||||
| 
 | ||||
| // NewSilentWrapErrorf returns an error that formats as the given text but unwraps as the provided error | ||||
| func NewSilentWrapErrorf(unwrap error, message string, args ...any) error { | ||||
| // ErrorWrap returns an error that formats as the given text but unwraps as the provided error | ||||
| func ErrorWrap(unwrap error, message string, args ...any) error { | ||||
| 	if len(args) == 0 { | ||||
| 		return SilentWrap{Message: message, Err: unwrap} | ||||
| 		return errorWrapper{Message: message, Err: unwrap} | ||||
| 	} | ||||
| 	return SilentWrap{Message: fmt.Sprintf(message, args...), Err: unwrap} | ||||
| 	return errorWrapper{Message: fmt.Sprintf(message, args...), Err: unwrap} | ||||
| } | ||||
| 
 | ||||
| // NewInvalidArgumentErrorf returns an error that formats as the given text but unwraps as an ErrInvalidArgument | ||||
| func NewInvalidArgumentErrorf(message string, args ...any) error { | ||||
| 	return NewSilentWrapErrorf(ErrInvalidArgument, message, args...) | ||||
| 	return ErrorWrap(ErrInvalidArgument, message, args...) | ||||
| } | ||||
| 
 | ||||
| // NewPermissionDeniedErrorf returns an error that formats as the given text but unwraps as an ErrPermissionDenied | ||||
| func NewPermissionDeniedErrorf(message string, args ...any) error { | ||||
| 	return NewSilentWrapErrorf(ErrPermissionDenied, message, args...) | ||||
| 	return ErrorWrap(ErrPermissionDenied, message, args...) | ||||
| } | ||||
| 
 | ||||
| // NewAlreadyExistErrorf returns an error that formats as the given text but unwraps as an ErrAlreadyExist | ||||
| func NewAlreadyExistErrorf(message string, args ...any) error { | ||||
| 	return NewSilentWrapErrorf(ErrAlreadyExist, message, args...) | ||||
| 	return ErrorWrap(ErrAlreadyExist, message, args...) | ||||
| } | ||||
| 
 | ||||
| // NewNotExistErrorf returns an error that formats as the given text but unwraps as an ErrNotExist | ||||
| func NewNotExistErrorf(message string, args ...any) error { | ||||
| 	return NewSilentWrapErrorf(ErrNotExist, message, args...) | ||||
| 	return ErrorWrap(ErrNotExist, message, args...) | ||||
| } | ||||
| 
 | ||||
| // ErrWrapLocale wraps an err with a translation key and arguments | ||||
| func ErrWrapLocale(err error, trKey string, trArgs ...any) error { | ||||
| 	return LocaleWrap{err: err, TrKey: trKey, TrArgs: trArgs} | ||||
| // ErrorWrapLocale wraps an err with a translation key and arguments | ||||
| func ErrorWrapLocale(err error, trKey string, trArgs ...any) error { | ||||
| 	return LocaleWrapper{err: err, TrKey: trKey, TrArgs: trArgs} | ||||
| } | ||||
| 
 | ||||
| func ErrAsLocale(err error) *LocaleWrap { | ||||
| 	var e LocaleWrap | ||||
| func ErrorAsLocale(err error) *LocaleWrapper { | ||||
| 	var e LocaleWrapper | ||||
| 	if errors.As(err, &e) { | ||||
| 		return &e | ||||
| 	} | ||||
|  | ||||
| @ -911,7 +911,6 @@ delete_token_success=Token byl odstraněn. Aplikace, které jej používají ji | ||||
| repo_and_org_access=Repozitář a přístup organizace | ||||
| permissions_public_only=Pouze veřejnost | ||||
| permissions_access_all=Vše (veřejné, soukromé a omezené) | ||||
| select_permissions=Vyberte oprávnění | ||||
| permission_not_set=Není nastaveno | ||||
| permission_no_access=Bez přístupu | ||||
| permission_read=Přečtené | ||||
| @ -2580,7 +2579,6 @@ diff.commit=revize | ||||
| diff.git-notes=Poznámky | ||||
| diff.data_not_available=Rozdílový obsah není dostupný | ||||
| diff.options_button=Možnosti rozdílového porovnání | ||||
| diff.show_diff_stats=Zobrazit statistiky | ||||
| diff.download_patch=Stáhněte soubor záplaty | ||||
| diff.download_diff=Stáhněte rozdílový soubor | ||||
| diff.show_split_view=Rozdělené zobrazení | ||||
|  | ||||
| @ -910,7 +910,6 @@ delete_token_success=Der Zugriffstoken wurde gelöscht. Anwendungen die diesen T | ||||
| repo_and_org_access=Repository- und Organisationszugriff | ||||
| permissions_public_only=Nur öffentlich | ||||
| permissions_access_all=Alle (öffentlich, privat und begrenzt) | ||||
| select_permissions=Berechtigungen auswählen | ||||
| permission_not_set=Nicht festgelegt | ||||
| permission_no_access=Kein Zugriff | ||||
| permission_read=Lesen | ||||
| @ -2569,7 +2568,6 @@ diff.commit=Commit | ||||
| diff.git-notes=Hinweise | ||||
| diff.data_not_available=Keine Diff-Daten verfügbar | ||||
| diff.options_button=Diff-Optionen | ||||
| diff.show_diff_stats=Statistiken anzeigen | ||||
| diff.download_patch=Patch-Datei herunterladen | ||||
| diff.download_diff=Vergleichs-Datei herunterladen | ||||
| diff.show_split_view=Geteilte Ansicht | ||||
|  | ||||
| @ -810,7 +810,6 @@ delete_token_success=Το διακριτικό έχει διαγραφεί. Οι | ||||
| repo_and_org_access=Πρόσβαση στο Αποθετήριο και Οργανισμό | ||||
| permissions_public_only=Δημόσια μόνο | ||||
| permissions_access_all=Όλα (δημόσια, ιδιωτικά, και περιορισμένα) | ||||
| select_permissions=Επιλέξτε δικαιώματα | ||||
| permission_no_access=Καμία Πρόσβαση | ||||
| permission_read=Αναγνωσμένες | ||||
| permission_write=Ανάγνωση και Εγγραφή | ||||
| @ -2317,7 +2316,6 @@ diff.commit=υποβολή | ||||
| diff.git-notes=Σημειώσεις | ||||
| diff.data_not_available=Δεν Υπάρχει Διαθέσιμο Περιεχόμενο Diff | ||||
| diff.options_button=Επιλογές Diff | ||||
| diff.show_diff_stats=Εμφάνιση Στατιστικών | ||||
| diff.download_patch=Λήψη Αρχείου Patch | ||||
| diff.download_diff=Λήψη Αρχείου Diff | ||||
| diff.show_split_view=Διαιρεμένη Προβολή | ||||
|  | ||||
| @ -917,7 +917,6 @@ delete_token_success = The token has been deleted. Applications using it no long | ||||
| repo_and_org_access = Repository and Organization Access | ||||
| permissions_public_only = Public only | ||||
| permissions_access_all = All (public, private, and limited) | ||||
| select_permissions = Select permissions | ||||
| permission_not_set = Not set | ||||
| permission_no_access = No Access | ||||
| permission_read = Read | ||||
| @ -1939,7 +1938,7 @@ pulls.outdated_with_base_branch = This branch is out-of-date with the base branc | ||||
| pulls.close = Close Pull Request | ||||
| pulls.closed_at = `closed this pull request <a id="%[1]s" href="#%[1]s">%[2]s</a>` | ||||
| pulls.reopened_at = `reopened this pull request <a id="%[1]s" href="#%[1]s">%[2]s</a>` | ||||
| pulls.cmd_instruction_hint = `View <a class="show-instruction">command line instructions</a>.` | ||||
| pulls.cmd_instruction_hint = View command line instructions | ||||
| pulls.cmd_instruction_checkout_title = Checkout | ||||
| pulls.cmd_instruction_checkout_desc = From your project repository, check out a new branch and test the changes. | ||||
| pulls.cmd_instruction_merge_title = Merge | ||||
| @ -2597,7 +2596,6 @@ diff.commit = commit | ||||
| diff.git-notes = Notes | ||||
| diff.data_not_available = Diff Content Not Available | ||||
| diff.options_button = Diff Options | ||||
| diff.show_diff_stats = Show Stats | ||||
| diff.download_patch = Download Patch File | ||||
| diff.download_diff = Download Diff File | ||||
| diff.show_split_view = Split View | ||||
|  | ||||
| @ -806,7 +806,6 @@ delete_token_success=El token ha sido eliminado. Las aplicaciones que lo usen ya | ||||
| repo_and_org_access=Acceso al Repositorio y a la Organización | ||||
| permissions_public_only=Sólo público | ||||
| permissions_access_all=Todo (público, privado y limitado) | ||||
| select_permissions=Seleccionar permisos | ||||
| permission_no_access=Sin acceso | ||||
| permission_read=Leídas | ||||
| permission_write=Lectura y Escritura | ||||
| @ -2298,7 +2297,6 @@ diff.commit=commit | ||||
| diff.git-notes=Notas | ||||
| diff.data_not_available=El contenido del Diff no está disponible | ||||
| diff.options_button=Opciones de diferencias | ||||
| diff.show_diff_stats=Mostrar estadísticas | ||||
| diff.download_patch=Descargar archivo de parche | ||||
| diff.download_diff=Descargar archivo de diferencias | ||||
| diff.show_split_view=Dividir vista | ||||
|  | ||||
| @ -1777,7 +1777,6 @@ diff.commit=کامیت | ||||
| diff.git-notes=یادداشتها | ||||
| diff.data_not_available=محتوای تفاوت ها در دسترس نیست | ||||
| diff.options_button=تنظیمات (diff) تغییرات | ||||
| diff.show_diff_stats=نمایش وضعیت | ||||
| diff.download_patch=دانلود پرونده وصله | ||||
| diff.download_diff=دانلود فایل تغییرات diff | ||||
| diff.show_split_view=مشاهده تقسیم شده | ||||
|  | ||||
| @ -917,7 +917,6 @@ delete_token_success=Ce jeton a été supprimé. Les applications l'utilisant n' | ||||
| repo_and_org_access=Accès aux Organisations et Dépôts | ||||
| permissions_public_only=Publique uniquement | ||||
| permissions_access_all=Tout (public, privé et limité) | ||||
| select_permissions=Sélectionner les autorisations | ||||
| permission_not_set=Non défini | ||||
| permission_no_access=Aucun accès | ||||
| permission_read=Lecture | ||||
| @ -1701,7 +1700,9 @@ issues.time_estimate_invalid=Le format du temps estimé est invalide | ||||
| issues.start_tracking_history=`a commencé son travail %s.` | ||||
| issues.tracker_auto_close=Le minuteur sera automatiquement arrêté quand le ticket sera fermé. | ||||
| issues.tracking_already_started=`Vous avez déjà un minuteur en cours sur <a href="%s">un autre ticket</a> !` | ||||
| issues.stop_tracking=Arrêter le minuteur | ||||
| issues.stop_tracking_history=a travaillé sur <b>%[1]s</b> %[2]s | ||||
| issues.cancel_tracking=Abandonner | ||||
| issues.cancel_tracking_history=`a abandonné son minuteur %s.` | ||||
| issues.del_time=Supprimer ce minuteur du journal | ||||
| issues.add_time_history=a pointé du temps de travail sur <b>%[1]s</b>, %[2]s | ||||
| @ -2590,7 +2591,6 @@ diff.commit=révision | ||||
| diff.git-notes=Notes | ||||
| diff.data_not_available=Contenu de la comparaison indisponible | ||||
| diff.options_button=Option de Diff | ||||
| diff.show_diff_stats=Voir les Statistiques | ||||
| diff.download_patch=Télécharger le Fichier Patch | ||||
| diff.download_diff=Télécharger le Fichier des Différences | ||||
| diff.show_split_view=Vue séparée | ||||
|  | ||||
| @ -917,7 +917,6 @@ delete_token_success=Tá an comhartha scriosta. Níl rochtain ag iarratais a ús | ||||
| repo_and_org_access=Rochtain Stórála agus Eagraíochta | ||||
| permissions_public_only=Poiblí amháin | ||||
| permissions_access_all=Gach (poiblí, príobháideach agus teoranta) | ||||
| select_permissions=Roghnaigh ceadanna | ||||
| permission_not_set=Níl leagtha | ||||
| permission_no_access=Gan rochtain | ||||
| permission_read=Léigh | ||||
| @ -1464,6 +1463,8 @@ issues.filter_milestones=Cloch Mhíle Scagaire | ||||
| issues.filter_projects=Tionscadal Scagaire | ||||
| issues.filter_labels=Lipéad Scagaire | ||||
| issues.filter_reviewers=Athbhreithneoir Scagaire | ||||
| issues.filter_no_results=Gan torthaí | ||||
| issues.filter_no_results_placeholder=Bain triail as do scagairí cuardaigh a choigeartú. | ||||
| issues.new=Eagrán Nua | ||||
| issues.new.title_empty=Ní féidir leis an teideal a bheith folamh | ||||
| issues.new.labels=Lipéid | ||||
| @ -1701,7 +1702,9 @@ issues.time_estimate_invalid=Tá formáid meastachán ama neamhbhailí | ||||
| issues.start_tracking_history=thosaigh ag obair %s | ||||
| issues.tracker_auto_close=Stopfar ama go huathoibríoch nuair a dhúnfar an tsaincheist seo | ||||
| issues.tracking_already_started=`Tá tús curtha agat cheana féin ag rianú ama ar <a href="%s">eagrán eile</a>!` | ||||
| issues.stop_tracking=Stad uaineadóir | ||||
| issues.stop_tracking_history=d'oibrigh do <b>%[1]s</b> %[2]s | ||||
| issues.cancel_tracking=Caith amach | ||||
| issues.cancel_tracking_history=`rianú ama curtha ar ceal %s` | ||||
| issues.del_time=Scrios an log ama seo | ||||
| issues.add_time_history=cuireadh am caite <b>%[1]s</b> %[2]s leis | ||||
| @ -2590,7 +2593,6 @@ diff.commit=tiomantas | ||||
| diff.git-notes=Nótaí | ||||
| diff.data_not_available=Níl Ábhar Difríochtaí Ar Fáil | ||||
| diff.options_button=Roghanna Diff | ||||
| diff.show_diff_stats=Taispeáin Staitisticí | ||||
| diff.download_patch=Íoslódáil an comhad paiste | ||||
| diff.download_diff=Íoslódáil Comhad Diff | ||||
| diff.show_split_view=Amharc Scoilt | ||||
|  | ||||
| @ -1098,7 +1098,6 @@ diff.parent=szülő | ||||
| diff.commit=commit | ||||
| diff.git-notes=Megjegyzések | ||||
| diff.data_not_available=A különbségek nem megjeleníthetőek | ||||
| diff.show_diff_stats=Statisztikák mutatása | ||||
| diff.show_split_view=Osztott nézet | ||||
| diff.show_unified_view=Egyesített nézet | ||||
| diff.stats_desc=<strong>%d fájl</strong> változott, egészen pontosan <strong>%d új sor hozzáadva</strong> és <strong>%d régi sor törölve</strong> | ||||
|  | ||||
| @ -1929,7 +1929,6 @@ diff.commit=commit | ||||
| diff.git-notes=Note | ||||
| diff.data_not_available=Dati Diff non disponibili | ||||
| diff.options_button=Opzioni Diff | ||||
| diff.show_diff_stats=Mostra statistiche | ||||
| diff.download_patch=Scarica il file Patch | ||||
| diff.download_diff=Scarica il file Diff | ||||
| diff.show_split_view=Visualizzazione separata | ||||
|  | ||||
| @ -917,7 +917,6 @@ delete_token_success=トークンを削除しました。 削除したトーク | ||||
| repo_and_org_access=リポジトリと組織へのアクセス | ||||
| permissions_public_only=公開のみ | ||||
| permissions_access_all=すべて (公開、プライベート、限定) | ||||
| select_permissions=許可の選択 | ||||
| permission_not_set=設定なし | ||||
| permission_no_access=アクセス不可 | ||||
| permission_read=読み取り | ||||
| @ -2592,7 +2591,6 @@ diff.commit=コミット | ||||
| diff.git-notes=Notes | ||||
| diff.data_not_available=差分はありません | ||||
| diff.options_button=差分オプション | ||||
| diff.show_diff_stats=統計情報を表示 | ||||
| diff.download_patch=Patchファイルをダウンロード | ||||
| diff.download_diff=Diffファイルをダウンロード | ||||
| diff.show_split_view=分割表示 | ||||
|  | ||||
| @ -814,7 +814,6 @@ delete_token_success=Pilnvara tika izdzēsta. Lietojumprogrammām, kas izmantoja | ||||
| repo_and_org_access=Repozitorija un organizācijas piekļuve | ||||
| permissions_public_only=Tikai publiskie | ||||
| permissions_access_all=Visi (publiskie, privātie un ierobežotie) | ||||
| select_permissions=Norādiet tiesības | ||||
| permission_no_access=Nav piekļuves | ||||
| permission_read=Skatīšanās | ||||
| permission_write=Skatīšanās un raksīšanas | ||||
| @ -2317,7 +2316,6 @@ diff.commit=revīzija | ||||
| diff.git-notes=Piezīmes | ||||
| diff.data_not_available=Satura salīdzināšana nav pieejama | ||||
| diff.options_button=Salīdzināšanas iespējas | ||||
| diff.show_diff_stats=Rādīt statistiku | ||||
| diff.download_patch=Lejupielādēt ielāpa failu | ||||
| diff.download_diff=Lejupielādēt izmaiņu failu | ||||
| diff.show_split_view=Dalītais skats | ||||
|  | ||||
| @ -1864,7 +1864,6 @@ diff.commit=commit | ||||
| diff.git-notes=Notities | ||||
| diff.data_not_available=Diff gegevens niet beschikbaar | ||||
| diff.options_button=Diff opties | ||||
| diff.show_diff_stats=Statistieken weergeven | ||||
| diff.download_patch=Download Patch-bestand | ||||
| diff.download_diff=Download Diff-bestand | ||||
| diff.show_split_view=Zij-aan-zij weergave | ||||
|  | ||||
| @ -1728,7 +1728,6 @@ diff.commit=commit | ||||
| diff.git-notes=Notatki | ||||
| diff.data_not_available=Informacje nt. zmian nie są dostępne | ||||
| diff.options_button=Opcje porównania | ||||
| diff.show_diff_stats=Pokaż statystyki | ||||
| diff.download_patch=Ściągnij plik aktualizacji | ||||
| diff.download_diff=Ściągnij plik porównania | ||||
| diff.show_split_view=Widok podzielony | ||||
|  | ||||
Some files were not shown because too many files have changed in this diff Show More
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user