Skip to content

Commit

Permalink
Properly enforce gitea environment for pushes (#9501)
Browse files Browse the repository at this point in the history
#8982 attempted to enforce the gitea environment for pushes - unfortunately it tested the settings before they were actually read in - and therefore does not do that!
  • Loading branch information
zeripath authored Dec 27, 2019
1 parent f2d03cd commit 4acca9d
Show file tree
Hide file tree
Showing 6 changed files with 36 additions and 8 deletions.
16 changes: 12 additions & 4 deletions cmd/hook.go
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,12 @@ var (
)

func runHookPreReceive(c *cli.Context) error {
if os.Getenv(models.EnvIsInternal) == "true" {
return nil
}

setup("hooks/pre-receive.log", false)

if len(os.Getenv("SSH_ORIGINAL_COMMAND")) == 0 {
if setting.OnlyAllowPushIfGiteaEnvironmentSet {
fail(`Rejecting changes as Gitea environment not set.
Expand All @@ -69,8 +75,6 @@ Gitea or set your environment appropriately.`, "")
}
}

setup("hooks/pre-receive.log", false)

// the environment setted on serv command
isWiki := (os.Getenv(models.EnvRepoIsWiki) == "true")
username := os.Getenv(models.EnvRepoUsername)
Expand Down Expand Up @@ -186,6 +190,12 @@ func runHookUpdate(c *cli.Context) error {
}

func runHookPostReceive(c *cli.Context) error {
if os.Getenv(models.EnvIsInternal) == "true" {
return nil
}

setup("hooks/post-receive.log", false)

if len(os.Getenv("SSH_ORIGINAL_COMMAND")) == 0 {
if setting.OnlyAllowPushIfGiteaEnvironmentSet {
fail(`Rejecting changes as Gitea environment not set.
Expand All @@ -196,8 +206,6 @@ Gitea or set your environment appropriately.`, "")
}
}

setup("hooks/post-receive.log", false)

// the environment setted on serv command
repoUser := os.Getenv(models.EnvRepoUsername)
isWiki := (os.Getenv(models.EnvRepoIsWiki) == "true")
Expand Down
10 changes: 10 additions & 0 deletions models/helper_environment.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,16 @@ import (
"strings"
)

// InternalPushingEnvironment returns an os environment to switch off hooks on push
// It is recommended to avoid using this unless you are pushing within a transaction
// or if you absolutely are sure that post-receive and pre-receive will do nothing
// We provide the full pushing-environment for other hook providers
func InternalPushingEnvironment(doer *User, repo *Repository) []string {
return append(PushingEnvironment(doer, repo),
EnvIsInternal+"=true",
)
}

// PushingEnvironment returns an os environment to allow hooks to work on push
func PushingEnvironment(doer *User, repo *Repository) []string {
return FullPushingEnvironment(doer, doer, repo, repo.Name, 0)
Expand Down
6 changes: 3 additions & 3 deletions models/repo.go
Original file line number Diff line number Diff line change
Expand Up @@ -1012,7 +1012,7 @@ func createDelegateHooks(repoPath string) (err error) {
}

// initRepoCommit temporarily changes with work directory.
func initRepoCommit(tmpPath string, u *User) (err error) {
func initRepoCommit(tmpPath string, repo *Repository, u *User) (err error) {
commitTimeStr := time.Now().Format(time.RFC3339)

sig := u.NewGitSig()
Expand Down Expand Up @@ -1061,7 +1061,7 @@ func initRepoCommit(tmpPath string, u *User) (err error) {

if stdout, err := git.NewCommand("push", "origin", "master").
SetDescription(fmt.Sprintf("initRepoCommit (git push): %s", tmpPath)).
RunInDir(tmpPath); err != nil {
RunInDirWithEnv(tmpPath, InternalPushingEnvironment(u, repo)); err != nil {
log.Error("Failed to push back to master: Stdout: %s\nError: %v", stdout, err)
return fmt.Errorf("git push: %v", err)
}
Expand Down Expand Up @@ -1219,7 +1219,7 @@ func initRepository(e Engine, repoPath string, u *User, repo *Repository, opts C
}

// Apply changes and commit.
if err = initRepoCommit(tmpDir, u); err != nil {
if err = initRepoCommit(tmpDir, repo, u); err != nil {
return fmt.Errorf("initRepoCommit: %v", err)
}
}
Expand Down
2 changes: 1 addition & 1 deletion models/repo_generate.go
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ func generateRepoCommit(e Engine, repo, templateRepo, generateRepo *Repository,
return fmt.Errorf("git remote add: %v", err)
}

return initRepoCommit(tmpDir, repo.Owner)
return initRepoCommit(tmpDir, repo, repo.Owner)
}

// generateRepository initializes repository from template
Expand Down
1 change: 1 addition & 0 deletions models/update.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ const (
EnvPusherID = "GITEA_PUSHER_ID"
EnvKeyID = "GITEA_KEY_ID"
EnvIsDeployKey = "GITEA_IS_DEPLOY_KEY"
EnvIsInternal = "GITEA_INTERNAL_PUSH"
)

// CommitToPushCommit transforms a git.Commit to PushCommit type.
Expand Down
9 changes: 9 additions & 0 deletions services/pull/pull.go
Original file line number Diff line number Diff line change
Expand Up @@ -242,10 +242,19 @@ func PushToBaseRepo(pr *models.PullRequest) (err error) {

_ = os.Remove(file)

if err = pr.LoadIssue(); err != nil {
return fmt.Errorf("unable to load issue %d for pr %d: %v", pr.IssueID, pr.ID, err)
}
if err = pr.Issue.LoadPoster(); err != nil {
return fmt.Errorf("unable to load poster %d for pr %d: %v", pr.Issue.PosterID, pr.ID, err)
}

if err = git.Push(headRepoPath, git.PushOptions{
Remote: tmpRemoteName,
Branch: fmt.Sprintf("%s:%s", pr.HeadBranch, headFile),
Force: true,
// Use InternalPushingEnvironment here because we know that pre-receive and post-receive do not run on a refs/pulls/...
Env: models.InternalPushingEnvironment(pr.Issue.Poster, pr.BaseRepo),
}); err != nil {
return fmt.Errorf("Push: %v", err)
}
Expand Down

0 comments on commit 4acca9d

Please sign in to comment.