aboutsummaryrefslogtreecommitdiffstats
path: root/cmd
diff options
context:
space:
mode:
Diffstat (limited to 'cmd')
-rw-r--r--cmd/hook.go148
1 files changed, 122 insertions, 26 deletions
diff --git a/cmd/hook.go b/cmd/hook.go
index aabd9637c2..331f6a2d2d 100644
--- a/cmd/hook.go
+++ b/cmd/hook.go
@@ -8,10 +8,12 @@ import (
"bufio"
"bytes"
"fmt"
+ "io"
"net/http"
"os"
"strconv"
"strings"
+ "time"
"code.gitea.io/gitea/models"
"code.gitea.io/gitea/modules/git"
@@ -58,6 +60,85 @@ var (
}
)
+type delayWriter struct {
+ internal io.Writer
+ buf *bytes.Buffer
+ timer *time.Timer
+}
+
+func newDelayWriter(internal io.Writer, delay time.Duration) *delayWriter {
+ timer := time.NewTimer(delay)
+ return &delayWriter{
+ internal: internal,
+ buf: &bytes.Buffer{},
+ timer: timer,
+ }
+}
+
+func (d *delayWriter) Write(p []byte) (n int, err error) {
+ if d.buf != nil {
+ select {
+ case <-d.timer.C:
+ _, err := d.internal.Write(d.buf.Bytes())
+ if err != nil {
+ return 0, err
+ }
+ d.buf = nil
+ return d.internal.Write(p)
+ default:
+ return d.buf.Write(p)
+ }
+ }
+ return d.internal.Write(p)
+}
+
+func (d *delayWriter) WriteString(s string) (n int, err error) {
+ if d.buf != nil {
+ select {
+ case <-d.timer.C:
+ _, err := d.internal.Write(d.buf.Bytes())
+ if err != nil {
+ return 0, err
+ }
+ d.buf = nil
+ return d.internal.Write([]byte(s))
+ default:
+ return d.buf.WriteString(s)
+ }
+ }
+ return d.internal.Write([]byte(s))
+}
+
+func (d *delayWriter) Close() error {
+ if d == nil {
+ return nil
+ }
+ stopped := d.timer.Stop()
+ if stopped {
+ return nil
+ }
+ select {
+ case <-d.timer.C:
+ default:
+ }
+ if d.buf == nil {
+ return nil
+ }
+ _, err := d.internal.Write(d.buf.Bytes())
+ d.buf = nil
+ return err
+}
+
+type nilWriter struct{}
+
+func (n *nilWriter) Write(p []byte) (int, error) {
+ return len(p), nil
+}
+
+func (n *nilWriter) WriteString(s string) (int, error) {
+ return len(s), nil
+}
+
func runHookPreReceive(c *cli.Context) error {
if os.Getenv(models.EnvIsInternal) == "true" {
return nil
@@ -101,6 +182,18 @@ Gitea or set your environment appropriately.`, "")
total := 0
lastline := 0
+ var out io.Writer
+ out = &nilWriter{}
+ if setting.Git.VerbosePush {
+ if setting.Git.VerbosePushDelay > 0 {
+ dWriter := newDelayWriter(os.Stdout, setting.Git.VerbosePushDelay)
+ defer dWriter.Close()
+ out = dWriter
+ } else {
+ out = os.Stdout
+ }
+ }
+
for scanner.Scan() {
// TODO: support news feeds for wiki
if isWiki {
@@ -124,12 +217,10 @@ Gitea or set your environment appropriately.`, "")
newCommitIDs[count] = newCommitID
refFullNames[count] = refFullName
count++
- fmt.Fprintf(os.Stdout, "*")
- os.Stdout.Sync()
+ fmt.Fprintf(out, "*")
if count >= hookBatchSize {
- fmt.Fprintf(os.Stdout, " Checking %d branches\n", count)
- os.Stdout.Sync()
+ fmt.Fprintf(out, " Checking %d branches\n", count)
hookOptions.OldCommitIDs = oldCommitIDs
hookOptions.NewCommitIDs = newCommitIDs
@@ -147,12 +238,10 @@ Gitea or set your environment appropriately.`, "")
lastline = 0
}
} else {
- fmt.Fprintf(os.Stdout, ".")
- os.Stdout.Sync()
+ fmt.Fprintf(out, ".")
}
if lastline >= hookBatchSize {
- fmt.Fprintf(os.Stdout, "\n")
- os.Stdout.Sync()
+ fmt.Fprintf(out, "\n")
lastline = 0
}
}
@@ -162,8 +251,7 @@ Gitea or set your environment appropriately.`, "")
hookOptions.NewCommitIDs = newCommitIDs[:count]
hookOptions.RefFullNames = refFullNames[:count]
- fmt.Fprintf(os.Stdout, " Checking %d branches\n", count)
- os.Stdout.Sync()
+ fmt.Fprintf(out, " Checking %d branches\n", count)
statusCode, msg := private.HookPreReceive(username, reponame, hookOptions)
switch statusCode {
@@ -173,14 +261,11 @@ Gitea or set your environment appropriately.`, "")
fail(msg, "")
}
} else if lastline > 0 {
- fmt.Fprintf(os.Stdout, "\n")
- os.Stdout.Sync()
+ fmt.Fprintf(out, "\n")
lastline = 0
}
- fmt.Fprintf(os.Stdout, "Checked %d references in total\n", total)
- os.Stdout.Sync()
-
+ fmt.Fprintf(out, "Checked %d references in total\n", total)
return nil
}
@@ -206,6 +291,19 @@ Gitea or set your environment appropriately.`, "")
}
}
+ var out io.Writer
+ var dWriter *delayWriter
+ out = &nilWriter{}
+ if setting.Git.VerbosePush {
+ if setting.Git.VerbosePushDelay > 0 {
+ dWriter = newDelayWriter(os.Stdout, setting.Git.VerbosePushDelay)
+ defer dWriter.Close()
+ out = dWriter
+ } else {
+ out = os.Stdout
+ }
+ }
+
// the environment setted on serv command
repoUser := os.Getenv(models.EnvRepoUsername)
isWiki := (os.Getenv(models.EnvRepoIsWiki) == "true")
@@ -241,7 +339,7 @@ Gitea or set your environment appropriately.`, "")
continue
}
- fmt.Fprintf(os.Stdout, ".")
+ fmt.Fprintf(out, ".")
oldCommitIDs[count] = string(fields[0])
newCommitIDs[count] = string(fields[1])
refFullNames[count] = string(fields[2])
@@ -250,16 +348,15 @@ Gitea or set your environment appropriately.`, "")
}
count++
total++
- os.Stdout.Sync()
if count >= hookBatchSize {
- fmt.Fprintf(os.Stdout, " Processing %d references\n", count)
- os.Stdout.Sync()
+ fmt.Fprintf(out, " Processing %d references\n", count)
hookOptions.OldCommitIDs = oldCommitIDs
hookOptions.NewCommitIDs = newCommitIDs
hookOptions.RefFullNames = refFullNames
resp, err := private.HookPostReceive(repoUser, repoName, hookOptions)
if resp == nil {
+ _ = dWriter.Close()
hookPrintResults(results)
fail("Internal Server Error", err)
}
@@ -277,9 +374,9 @@ Gitea or set your environment appropriately.`, "")
fail("Internal Server Error", "SetDefaultBranch failed with Error: %v", err)
}
}
- fmt.Fprintf(os.Stdout, "Processed %d references in total\n", total)
- os.Stdout.Sync()
+ fmt.Fprintf(out, "Processed %d references in total\n", total)
+ _ = dWriter.Close()
hookPrintResults(results)
return nil
}
@@ -288,19 +385,18 @@ Gitea or set your environment appropriately.`, "")
hookOptions.NewCommitIDs = newCommitIDs[:count]
hookOptions.RefFullNames = refFullNames[:count]
- fmt.Fprintf(os.Stdout, " Processing %d references\n", count)
- os.Stdout.Sync()
+ fmt.Fprintf(out, " Processing %d references\n", count)
resp, err := private.HookPostReceive(repoUser, repoName, hookOptions)
if resp == nil {
+ _ = dWriter.Close()
hookPrintResults(results)
fail("Internal Server Error", err)
}
wasEmpty = wasEmpty || resp.RepoWasEmpty
results = append(results, resp.Results...)
- fmt.Fprintf(os.Stdout, "Processed %d references in total\n", total)
- os.Stdout.Sync()
+ fmt.Fprintf(out, "Processed %d references in total\n", total)
if wasEmpty && masterPushed {
// We need to tell the repo to reset the default branch to master
@@ -309,7 +405,7 @@ Gitea or set your environment appropriately.`, "")
fail("Internal Server Error", "SetDefaultBranch failed with Error: %v", err)
}
}
-
+ _ = dWriter.Close()
hookPrintResults(results)
return nil