Skip to content

Commit 7f8174b

Browse files
committed
Fix other uses of io.Pipe and create a new Pipe similar to io.Pipe but
backed by *os.File Signed-off-by: Andrew Thornton <[email protected]>
1 parent 7983720 commit 7f8174b

25 files changed

+434
-196
lines changed

go.mod

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,6 @@ require (
1818
github.com/caddyserver/certmagic v0.15.4
1919
github.com/chi-middleware/proxy v1.1.1
2020
github.com/denisenkom/go-mssqldb v0.12.0
21-
github.com/djherbis/buffer v1.2.0
22-
github.com/djherbis/nio/v3 v3.0.1
2321
github.com/duo-labs/webauthn v0.0.0-20220223184316-4d1cf2d34051
2422
github.com/dustin/go-humanize v1.0.0
2523
github.com/editorconfig/editorconfig-core-go/v2 v2.4.3

go.sum

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -369,11 +369,6 @@ github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f h1:lO4WD4F/r
369369
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f/go.mod h1:cuUVRXasLTGF7a8hSLbxyZXjz+1KgoB3wDUb6vlszIc=
370370
github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no=
371371
github.com/dimchansky/utfbom v1.1.0/go.mod h1:rO41eb7gLfo8SF1jd9F8HplJm1Fewwi4mQvIirEdv+8=
372-
github.com/djherbis/buffer v1.1.0/go.mod h1:VwN8VdFkMY0DCALdY8o00d3IZ6Amz/UNVMWcSaJT44o=
373-
github.com/djherbis/buffer v1.2.0 h1:PH5Dd2ss0C7CRRhQCZ2u7MssF+No9ide8Ye71nPHcrQ=
374-
github.com/djherbis/buffer v1.2.0/go.mod h1:fjnebbZjCUpPinBRD+TDwXSOeNQ7fPQWLfGQqiAiUyE=
375-
github.com/djherbis/nio/v3 v3.0.1 h1:6wxhnuppteMa6RHA4L81Dq7ThkZH8SwnDzXDYy95vB4=
376-
github.com/djherbis/nio/v3 v3.0.1/go.mod h1:Ng4h80pbZFMla1yKzm61cF0tqqilXZYrogmWgZxOcmg=
377372
github.com/dlclark/regexp2 v1.4.0 h1:F1rxgk7p4uKjwIQxBs9oAXe5CqrXlCduYEJvrF4u93E=
378373
github.com/dlclark/regexp2 v1.4.0/go.mod h1:2pZnwuY/m+8K6iRw6wQdMtk+rH5tNGR1i55kozfMjCc=
379374
github.com/dnaeon/go-vcr v1.2.0/go.mod h1:R4UdLID7HZT3taECzJs4YgbbH6PIGXB6W/sc5OLb6RQ=

modules/git/batch_reader.go

Lines changed: 18 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@ import (
1010
"context"
1111
"fmt"
1212
"math"
13-
"os"
1413
"runtime"
1514
"strconv"
1615
"strings"
@@ -36,24 +35,21 @@ func EnsureValidGitRepository(ctx context.Context, repoPath string) error {
3635
}
3736

3837
func returnClosedReaderWriters(err error) (WriteCloserError, *bufio.Reader, func()) {
39-
wr := &writeCloserError{}
40-
rd := &readCloserError{}
41-
42-
_ = wr.CloseWithError(err)
43-
_ = rd.CloseWithError(err)
44-
45-
return wr, bufio.NewReader(rd), func() {}
38+
wr := &ClosedReadWriteCloserError{err}
39+
return wr, bufio.NewReader(wr), func() {}
4640
}
4741

4842
// CatFileBatchCheck opens git cat-file --batch-check in the provided repo and returns a stdin pipe, a stdout reader and cancel function
4943
func CatFileBatchCheck(ctx context.Context, repoPath string) (WriteCloserError, *bufio.Reader, func()) {
50-
batchStdinReader, batchStdinWriter, err := os.Pipe()
44+
batchStdinReader, batchStdinWriter, err := Pipe()
5145
if err != nil {
5246
log.Critical("Unable to open pipe to write to: %v", err)
5347
return returnClosedReaderWriters(err)
5448
}
55-
batchStdoutReader, batchStdoutWriter, err := os.Pipe()
49+
batchStdoutReader, batchStdoutWriter, err := Pipe()
5650
if err != nil {
51+
_ = batchStdinReader.Close()
52+
_ = batchStdinWriter.Close()
5753
log.Critical("Unable to open pipe to write to: %v", err)
5854
return returnClosedReaderWriters(err)
5955
}
@@ -69,9 +65,6 @@ func CatFileBatchCheck(ctx context.Context, repoPath string) (WriteCloserError,
6965
_, filename, line, _ := runtime.Caller(2)
7066
filename = strings.TrimPrefix(filename, callerPrefix)
7167

72-
wr := newWriteCloserError(batchStdinWriter)
73-
rd := newReadCloserError(batchStdoutReader)
74-
7568
go func() {
7669
stderr := strings.Builder{}
7770
err := NewCommand(ctx, "cat-file", "--batch-check").
@@ -84,10 +77,8 @@ func CatFileBatchCheck(ctx context.Context, repoPath string) (WriteCloserError,
8477
})
8578
if err != nil {
8679
err := ConcatenateError(err, (&stderr).String())
87-
_ = wr.CloseWithError(err)
88-
_ = rd.CloseWithError(err)
89-
_ = batchStdoutWriter.Close()
90-
_ = batchStdinReader.Close()
80+
_ = batchStdinReader.CloseWithError(err)
81+
_ = batchStdoutWriter.CloseWithError(err)
9182
} else {
9283
_ = batchStdoutWriter.Close()
9384
_ = batchStdinReader.Close()
@@ -96,29 +87,27 @@ func CatFileBatchCheck(ctx context.Context, repoPath string) (WriteCloserError,
9687
}()
9788

9889
// For simplicities sake we'll use a buffered reader to read from the cat-file --batch-check
99-
batchReader := bufio.NewReader(rd)
100-
101-
return wr, batchReader, cancel
90+
batchReader := bufio.NewReader(batchStdoutReader)
91+
return batchStdinWriter, batchReader, cancel
10292
}
10393

10494
// CatFileBatch opens git cat-file --batch in the provided repo and returns a stdin pipe, a stdout reader and cancel function
10595
func CatFileBatch(ctx context.Context, repoPath string) (WriteCloserError, *bufio.Reader, func()) {
10696
// We often want to feed the commits in order into cat-file --batch, followed by their trees and sub trees as necessary.
10797
// so let's create a batch stdin and stdout
108-
batchStdinReader, batchStdinWriter, err := os.Pipe()
98+
batchStdinReader, batchStdinWriter, err := Pipe()
10999
if err != nil {
110100
log.Critical("Unable to open pipe to write to: %v", err)
111101
return returnClosedReaderWriters(err)
112102
}
113-
batchStdoutReader, batchStdoutWriter, err := os.Pipe()
103+
batchStdoutReader, batchStdoutWriter, err := Pipe()
114104
if err != nil {
105+
_ = batchStdinReader.Close()
106+
_ = batchStdinWriter.Close()
115107
log.Critical("Unable to open pipe to write to: %v", err)
116108
return returnClosedReaderWriters(err)
117109
}
118110

119-
wr := newWriteCloserError(batchStdinWriter)
120-
rd := newReadCloserError(batchStdoutReader)
121-
122111
ctx, ctxCancel := context.WithCancel(ctx)
123112
closed := make(chan struct{})
124113
cancel := func() {
@@ -143,10 +132,8 @@ func CatFileBatch(ctx context.Context, repoPath string) (WriteCloserError, *bufi
143132
})
144133
if err != nil {
145134
err := ConcatenateError(err, (&stderr).String())
146-
_ = wr.CloseWithError(err)
147-
_ = rd.CloseWithError(err)
148-
_ = batchStdoutWriter.Close()
149-
_ = batchStdinReader.Close()
135+
_ = batchStdinReader.CloseWithError(err)
136+
_ = batchStdoutWriter.CloseWithError(err)
150137
} else {
151138
_ = batchStdoutWriter.Close()
152139
_ = batchStdinReader.Close()
@@ -155,9 +142,9 @@ func CatFileBatch(ctx context.Context, repoPath string) (WriteCloserError, *bufi
155142
}()
156143

157144
// For simplicities sake we'll us a buffered reader to read from the cat-file --batch
158-
batchReader := bufio.NewReaderSize(rd, 32*1024)
145+
batchReader := bufio.NewReaderSize(batchStdoutReader, 32*1024)
159146

160-
return wr, batchReader, cancel
147+
return batchStdinWriter, batchReader, cancel
161148
}
162149

163150
// ReadBatchLine reads the header line from cat-file --batch

modules/git/blob.go

Lines changed: 7 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import (
99
"bytes"
1010
"encoding/base64"
1111
"io"
12+
"strings"
1213

1314
"code.gitea.io/gitea/modules/typesniffer"
1415
"code.gitea.io/gitea/modules/util"
@@ -69,25 +70,18 @@ func (b *Blob) GetBlobContentBase64() (string, error) {
6970
}
7071
defer dataRc.Close()
7172

72-
pr, pw := io.Pipe()
73-
encoder := base64.NewEncoder(base64.StdEncoding, pw)
73+
sb := &strings.Builder{}
7474

75-
go func() {
76-
_, err := io.Copy(encoder, dataRc)
77-
_ = encoder.Close()
75+
encoder := base64.NewEncoder(base64.StdEncoding, sb)
7876

79-
if err != nil {
80-
_ = pw.CloseWithError(err)
81-
} else {
82-
_ = pw.Close()
83-
}
84-
}()
77+
_, err = io.Copy(encoder, dataRc)
78+
_ = encoder.Close()
8579

86-
out, err := io.ReadAll(pr)
8780
if err != nil {
8881
return "", err
8982
}
90-
return string(out), nil
83+
84+
return sb.String(), nil
9185
}
9286

9387
// GuessContentType guesses the content type of the blob.

modules/git/command.go

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -158,9 +158,21 @@ func (c *Command) Run(opts *RunOpts) error {
158158
)
159159

160160
cmd.Dir = opts.Dir
161-
cmd.Stdout = opts.Stdout
162-
cmd.Stderr = opts.Stderr
163-
cmd.Stdin = opts.Stdin
161+
if pipeWriter, ok := opts.Stdout.(*PipeWriter); ok {
162+
cmd.Stdout = pipeWriter.File()
163+
} else {
164+
cmd.Stdout = opts.Stdout
165+
}
166+
if pipeWriter, ok := opts.Stderr.(*PipeWriter); ok {
167+
cmd.Stderr = pipeWriter.File()
168+
} else {
169+
cmd.Stderr = opts.Stderr
170+
}
171+
if pipeReader, ok := opts.Stdin.(*PipeReader); ok {
172+
cmd.Stdin = pipeReader.File()
173+
} else {
174+
cmd.Stdin = opts.Stdin
175+
}
164176
if err := cmd.Start(); err != nil {
165177
return err
166178
}

modules/git/commit.go

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import (
1212
"errors"
1313
"fmt"
1414
"io"
15+
"os"
1516
"os/exec"
1617
"strconv"
1718
"strings"
@@ -475,7 +476,10 @@ func parseCommitFileStatus(fileStatus *CommitFileStatus, stdout io.Reader) {
475476

476477
// GetCommitFileStatus returns file status of commit in given repository.
477478
func GetCommitFileStatus(ctx context.Context, repoPath, commitID string) (*CommitFileStatus, error) {
478-
stdout, w := io.Pipe()
479+
stdout, w, err := os.Pipe()
480+
if err != nil {
481+
return nil, err
482+
}
479483
done := make(chan struct{})
480484
fileStatus := NewCommitFileStatus()
481485
go func() {
@@ -486,7 +490,7 @@ func GetCommitFileStatus(ctx context.Context, repoPath, commitID string) (*Commi
486490
stderr := new(bytes.Buffer)
487491
args := []string{"log", "--name-status", "-c", "--pretty=format:", "--parents", "--no-renames", "-z", "-1", commitID}
488492

489-
err := NewCommand(ctx, args...).Run(&RunOpts{
493+
err = NewCommand(ctx, args...).Run(&RunOpts{
490494
Dir: repoPath,
491495
Stdout: w,
492496
Stderr: stderr,

modules/git/log_name_status.go

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,15 +13,19 @@ import (
1313
"sort"
1414
"strings"
1515

16-
"github.com/djherbis/buffer"
17-
"github.com/djherbis/nio/v3"
16+
"code.gitea.io/gitea/modules/log"
1817
)
1918

2019
// LogNameStatusRepo opens git log --raw in the provided repo and returns a stdin pipe, a stdout reader and cancel function
2120
func LogNameStatusRepo(ctx context.Context, repository, head, treepath string, paths ...string) (*bufio.Reader, func()) {
2221
// We often want to feed the commits in order into cat-file --batch, followed by their trees and sub trees as necessary.
2322
// so let's create a batch stdin and stdout
24-
stdoutReader, stdoutWriter := nio.Pipe(buffer.New(32 * 1024))
23+
stdoutReader, stdoutWriter, err := Pipe()
24+
if err != nil {
25+
log.Critical("Unable to open pipe to write to: %v", err)
26+
rd := &ClosedReadWriteCloserError{err}
27+
return bufio.NewReader(rd), func() {}
28+
}
2529

2630
// Lets also create a context so that we can absolutely ensure that the command should die when we're done
2731
ctx, ctxCancel := context.WithCancel(ctx)

modules/git/pipeline/catfile.go

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ import (
99
"bytes"
1010
"context"
1111
"fmt"
12-
"io"
1312
"strconv"
1413
"strings"
1514
"sync"
@@ -19,7 +18,7 @@ import (
1918
)
2019

2120
// CatFileBatchCheck runs cat-file with --batch-check
22-
func CatFileBatchCheck(ctx context.Context, shasToCheckReader *io.PipeReader, catFileCheckWriter *io.PipeWriter, wg *sync.WaitGroup, tmpBasePath string) {
21+
func CatFileBatchCheck(ctx context.Context, shasToCheckReader git.ReadCloserError, catFileCheckWriter git.WriteCloserError, wg *sync.WaitGroup, tmpBasePath string) {
2322
defer wg.Done()
2423
defer shasToCheckReader.Close()
2524
defer catFileCheckWriter.Close()
@@ -38,7 +37,7 @@ func CatFileBatchCheck(ctx context.Context, shasToCheckReader *io.PipeReader, ca
3837
}
3938

4039
// CatFileBatchCheckAllObjects runs cat-file with --batch-check --batch-all
41-
func CatFileBatchCheckAllObjects(ctx context.Context, catFileCheckWriter *io.PipeWriter, wg *sync.WaitGroup, tmpBasePath string, errChan chan<- error) {
40+
func CatFileBatchCheckAllObjects(ctx context.Context, catFileCheckWriter git.WriteCloserError, wg *sync.WaitGroup, tmpBasePath string, errChan chan<- error) {
4241
defer wg.Done()
4342
defer catFileCheckWriter.Close()
4443

@@ -58,7 +57,7 @@ func CatFileBatchCheckAllObjects(ctx context.Context, catFileCheckWriter *io.Pip
5857
}
5958

6059
// CatFileBatch runs cat-file --batch
61-
func CatFileBatch(ctx context.Context, shasToBatchReader *io.PipeReader, catFileBatchWriter *io.PipeWriter, wg *sync.WaitGroup, tmpBasePath string) {
60+
func CatFileBatch(ctx context.Context, shasToBatchReader git.ReadCloserError, catFileBatchWriter git.WriteCloserError, wg *sync.WaitGroup, tmpBasePath string) {
6261
defer wg.Done()
6362
defer shasToBatchReader.Close()
6463
defer catFileBatchWriter.Close()
@@ -76,7 +75,7 @@ func CatFileBatch(ctx context.Context, shasToBatchReader *io.PipeReader, catFile
7675
}
7776

7877
// BlobsLessThan1024FromCatFileBatchCheck reads a pipeline from cat-file --batch-check and returns the blobs <1024 in size
79-
func BlobsLessThan1024FromCatFileBatchCheck(catFileCheckReader *io.PipeReader, shasToBatchWriter *io.PipeWriter, wg *sync.WaitGroup) {
78+
func BlobsLessThan1024FromCatFileBatchCheck(catFileCheckReader git.ReadCloserError, shasToBatchWriter git.WriteCloserError, wg *sync.WaitGroup) {
8079
defer wg.Done()
8180
defer catFileCheckReader.Close()
8281
scanner := bufio.NewScanner(catFileCheckReader)

modules/git/pipeline/lfs.go

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -99,8 +99,17 @@ func FindLFSFile(repo *git.Repository, hash git.SHA1) ([]*LFSResult, error) {
9999
sort.Sort(lfsResultSlice(results))
100100

101101
// Should really use a go-git function here but name-rev is not completed and recapitulating it is not simple
102-
shasToNameReader, shasToNameWriter := io.Pipe()
103-
nameRevStdinReader, nameRevStdinWriter := io.Pipe()
102+
shasToNameReader, shasToNameWriter, err := git.Pipe()
103+
if err != nil {
104+
return nil, err
105+
}
106+
nameRevStdinReader, nameRevStdinWriter, err := git.Pipe()
107+
if err != nil {
108+
_ = shasToNameReader.Close()
109+
_ = shasToNameWriter.Close()
110+
return nil, err
111+
}
112+
104113
errChan := make(chan error, 1)
105114
wg := sync.WaitGroup{}
106115
wg.Add(3)

modules/git/pipeline/lfs_nogogit.go

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,10 @@ func FindLFSFile(repo *git.Repository, hash git.SHA1) ([]*LFSResult, error) {
4545
basePath := repo.Path
4646

4747
// Use rev-list to provide us with all commits in order
48-
revListReader, revListWriter := io.Pipe()
48+
revListReader, revListWriter, err := git.Pipe()
49+
if err != nil {
50+
return nil, err
51+
}
4952
defer func() {
5053
_ = revListWriter.Close()
5154
_ = revListReader.Close()
@@ -195,8 +198,17 @@ func FindLFSFile(repo *git.Repository, hash git.SHA1) ([]*LFSResult, error) {
195198
sort.Sort(lfsResultSlice(results))
196199

197200
// Should really use a go-git function here but name-rev is not completed and recapitulating it is not simple
198-
shasToNameReader, shasToNameWriter := io.Pipe()
199-
nameRevStdinReader, nameRevStdinWriter := io.Pipe()
201+
shasToNameReader, shasToNameWriter, err := git.Pipe()
202+
if err != nil {
203+
return nil, err
204+
}
205+
nameRevStdinReader, nameRevStdinWriter, err := git.Pipe()
206+
if err != nil {
207+
_ = shasToNameReader.Close()
208+
_ = shasToNameWriter.Close()
209+
return nil, err
210+
}
211+
200212
errChan := make(chan error, 1)
201213
wg := sync.WaitGroup{}
202214
wg.Add(3)

0 commit comments

Comments
 (0)