Merge pull request #25781 from kolyshkin/rm-goimports
Use golangci-lint fmt for pkg/bindings
This commit is contained in:
		
						commit
						0a0d05b3e3
					
				|  | @ -7,7 +7,7 @@ formatters: | ||||||
|     - gofmt |     - gofmt | ||||||
|     - goimports |     - goimports | ||||||
|   exclusions: |   exclusions: | ||||||
|     generated: strict |     generated: disable | ||||||
| 
 | 
 | ||||||
| linters: | linters: | ||||||
|   enable: |   enable: | ||||||
|  |  | ||||||
							
								
								
									
										6
									
								
								Makefile
								
								
								
								
							
							
						
						
									
										6
									
								
								Makefile
								
								
								
								
							|  | @ -478,7 +478,7 @@ podman-testing: bin/podman-testing | ||||||
| ###
 | ###
 | ||||||
| 
 | 
 | ||||||
| .PHONY: generate-bindings | .PHONY: generate-bindings | ||||||
| generate-bindings: | generate-bindings: .install.golangci-lint | ||||||
| ifneq ($(GOOS),darwin) | ifneq ($(GOOS),darwin) | ||||||
| 	$(GOCMD) generate ./pkg/bindings/... ; | 	$(GOCMD) generate ./pkg/bindings/... ; | ||||||
| endif | endif | ||||||
|  | @ -1023,10 +1023,6 @@ endif | ||||||
| install.tools: .install.golangci-lint ## Install needed tools
 | install.tools: .install.golangci-lint ## Install needed tools
 | ||||||
| 	$(MAKE) -C test/tools | 	$(MAKE) -C test/tools | ||||||
| 
 | 
 | ||||||
| .PHONY: .install.goimports |  | ||||||
| .install.goimports: |  | ||||||
| 	$(MAKE) -C test/tools build/goimports |  | ||||||
| 
 |  | ||||||
| .PHONY: .install.ginkgo | .PHONY: .install.ginkgo | ||||||
| .install.ginkgo: | .install.ginkgo: | ||||||
| 	$(GO) build -o $(GINKGO) ./vendor/github.com/onsi/ginkgo/v2/ginkgo | 	$(GO) build -o $(GINKGO) ./vendor/github.com/onsi/ginkgo/v2/ginkgo | ||||||
|  |  | ||||||
|  | @ -38,7 +38,6 @@ cd $CIRRUS_WORKING_DIR | ||||||
| showrun make -C test/tools vendor | showrun make -C test/tools vendor | ||||||
| SUGGESTION="run 'make vendor', 'make -C test/tools vendor' and 'make completions' and commit all changes" ./hack/tree_status.sh | SUGGESTION="run 'make vendor', 'make -C test/tools vendor' and 'make completions' and commit all changes" ./hack/tree_status.sh | ||||||
| 
 | 
 | ||||||
| showrun make .install.goimports |  | ||||||
| showrun make generate-bindings | showrun make generate-bindings | ||||||
| SUGGESTION="run 'make generate-bindings' and commit all changes" ./hack/tree_status.sh | SUGGESTION="run 'make generate-bindings' and commit all changes" ./hack/tree_status.sh | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -160,16 +160,8 @@ func main() { | ||||||
| 		} | 		} | ||||||
| 		closed = true | 		closed = true | ||||||
| 
 | 
 | ||||||
| 		// go fmt file
 | 		// Format file.
 | ||||||
| 		gofmt := exec.Command("go", "fmt", out.Name()) | 		goimport := exec.Command("../../../bin/golangci-lint", "fmt", out.Name()) | ||||||
| 		gofmt.Stderr = os.Stdout |  | ||||||
| 		if err := gofmt.Run(); err != nil { |  | ||||||
| 			fmt.Println(err) |  | ||||||
| 			os.Exit(1) |  | ||||||
| 		} |  | ||||||
| 
 |  | ||||||
| 		// go import file
 |  | ||||||
| 		goimport := exec.Command("../../../test/tools/build/goimports", "-w", out.Name()) |  | ||||||
| 		goimport.Stderr = os.Stdout | 		goimport.Stderr = os.Stdout | ||||||
| 		if err := goimport.Run(); err != nil { | 		if err := goimport.Run(); err != nil { | ||||||
| 			fmt.Println(err) | 			fmt.Println(err) | ||||||
|  |  | ||||||
|  | @ -20,14 +20,10 @@ clean: | ||||||
| 
 | 
 | ||||||
| .PHONY: $(BUILDDIR) | .PHONY: $(BUILDDIR) | ||||||
| $(BUILDDIR): \ | $(BUILDDIR): \ | ||||||
| 	$(BUILDDIR)/goimports \
 |  | ||||||
| 	$(BUILDDIR)/go-md2man \
 | 	$(BUILDDIR)/go-md2man \
 | ||||||
| 	$(BUILDDIR)/git-validation \
 | 	$(BUILDDIR)/git-validation \
 | ||||||
| 	$(BUILDDIR)/swagger | 	$(BUILDDIR)/swagger | ||||||
| 
 | 
 | ||||||
| $(BUILDDIR)/goimports: $(SOURCES) |  | ||||||
| 	$(GO_BUILD) -o $@ ./vendor/golang.org/x/tools/cmd/goimports |  | ||||||
| 
 |  | ||||||
| $(BUILDDIR)/go-md2man: $(SOURCES) | $(BUILDDIR)/go-md2man: $(SOURCES) | ||||||
| 	$(GO_BUILD) -o $@ ./vendor/github.com/cpuguy83/go-md2man/v2 | 	$(GO_BUILD) -o $@ ./vendor/github.com/cpuguy83/go-md2man/v2 | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -9,7 +9,6 @@ require ( | ||||||
| 	github.com/cpuguy83/go-md2man/v2 v2.0.6 | 	github.com/cpuguy83/go-md2man/v2 v2.0.6 | ||||||
| 	github.com/go-swagger/go-swagger v0.30.5 | 	github.com/go-swagger/go-swagger v0.30.5 | ||||||
| 	github.com/vbatts/git-validation v1.2.2 | 	github.com/vbatts/git-validation v1.2.2 | ||||||
| 	golang.org/x/tools v0.30.0 |  | ||||||
| ) | ) | ||||||
| 
 | 
 | ||||||
| require ( | require ( | ||||||
|  | @ -69,6 +68,7 @@ require ( | ||||||
| 	golang.org/x/sync v0.11.0 // indirect | 	golang.org/x/sync v0.11.0 // indirect | ||||||
| 	golang.org/x/sys v0.30.0 // indirect | 	golang.org/x/sys v0.30.0 // indirect | ||||||
| 	golang.org/x/text v0.21.0 // indirect | 	golang.org/x/text v0.21.0 // indirect | ||||||
|  | 	golang.org/x/tools v0.30.0 // indirect | ||||||
| 	gopkg.in/ini.v1 v1.67.0 // indirect | 	gopkg.in/ini.v1 v1.67.0 // indirect | ||||||
| 	gopkg.in/yaml.v2 v2.4.0 // indirect | 	gopkg.in/yaml.v2 v2.4.0 // indirect | ||||||
| 	gopkg.in/yaml.v3 v3.0.1 // indirect | 	gopkg.in/yaml.v3 v3.0.1 // indirect | ||||||
|  |  | ||||||
|  | @ -9,5 +9,4 @@ import ( | ||||||
| 	_ "github.com/cpuguy83/go-md2man/v2" | 	_ "github.com/cpuguy83/go-md2man/v2" | ||||||
| 	_ "github.com/go-swagger/go-swagger/cmd/swagger" | 	_ "github.com/go-swagger/go-swagger/cmd/swagger" | ||||||
| 	_ "github.com/vbatts/git-validation" | 	_ "github.com/vbatts/git-validation" | ||||||
| 	_ "golang.org/x/tools/cmd/goimports" |  | ||||||
| ) | ) | ||||||
|  |  | ||||||
|  | @ -1,50 +0,0 @@ | ||||||
| // Copyright 2013 The Go Authors. All rights reserved.
 |  | ||||||
| // Use of this source code is governed by a BSD-style
 |  | ||||||
| // license that can be found in the LICENSE file.
 |  | ||||||
| 
 |  | ||||||
| /* |  | ||||||
| Command goimports updates your Go import lines, |  | ||||||
| adding missing ones and removing unreferenced ones. |  | ||||||
| 
 |  | ||||||
| 	$ go install golang.org/x/tools/cmd/goimports@latest |  | ||||||
| 
 |  | ||||||
| In addition to fixing imports, goimports also formats |  | ||||||
| your code in the same style as gofmt so it can be used |  | ||||||
| as a replacement for your editor's gofmt-on-save hook. |  | ||||||
| 
 |  | ||||||
| For emacs, make sure you have the latest go-mode.el: |  | ||||||
| 
 |  | ||||||
| 	https://github.com/dominikh/go-mode.el
 |  | ||||||
| 
 |  | ||||||
| Then in your .emacs file: |  | ||||||
| 
 |  | ||||||
| 	(setq gofmt-command "goimports") |  | ||||||
| 	(add-hook 'before-save-hook 'gofmt-before-save) |  | ||||||
| 
 |  | ||||||
| For vim, set "gofmt_command" to "goimports": |  | ||||||
| 
 |  | ||||||
| 	https://golang.org/change/39c724dd7f252
 |  | ||||||
| 	https://golang.org/wiki/IDEsAndTextEditorPlugins
 |  | ||||||
| 	etc |  | ||||||
| 
 |  | ||||||
| For GoSublime, follow the steps described here: |  | ||||||
| 
 |  | ||||||
| 	http://michaelwhatcott.com/gosublime-goimports/
 |  | ||||||
| 
 |  | ||||||
| For other editors, you probably know what to do. |  | ||||||
| 
 |  | ||||||
| To exclude directories in your $GOPATH from being scanned for Go |  | ||||||
| files, goimports respects a configuration file at |  | ||||||
| $GOPATH/src/.goimportsignore which may contain blank lines, comment |  | ||||||
| lines (beginning with '#'), or lines naming a directory relative to |  | ||||||
| the configuration file to ignore when scanning. No globbing or regex |  | ||||||
| patterns are allowed. Use the "-v" verbose flag to verify it's |  | ||||||
| working and see what goimports is doing. |  | ||||||
| 
 |  | ||||||
| File bugs or feature requests at: |  | ||||||
| 
 |  | ||||||
| 	https://golang.org/issues/new?title=x/tools/cmd/goimports:+
 |  | ||||||
| 
 |  | ||||||
| Happy hacking! |  | ||||||
| */ |  | ||||||
| package main // import "golang.org/x/tools/cmd/goimports"
 |  | ||||||
|  | @ -1,379 +0,0 @@ | ||||||
| // Copyright 2013 The Go Authors. All rights reserved.
 |  | ||||||
| // Use of this source code is governed by a BSD-style
 |  | ||||||
| // license that can be found in the LICENSE file.
 |  | ||||||
| 
 |  | ||||||
| package main |  | ||||||
| 
 |  | ||||||
| import ( |  | ||||||
| 	"bufio" |  | ||||||
| 	"bytes" |  | ||||||
| 	"errors" |  | ||||||
| 	"flag" |  | ||||||
| 	"fmt" |  | ||||||
| 	"go/scanner" |  | ||||||
| 	"io" |  | ||||||
| 	"log" |  | ||||||
| 	"os" |  | ||||||
| 	"os/exec" |  | ||||||
| 	"path/filepath" |  | ||||||
| 	"runtime" |  | ||||||
| 	"runtime/pprof" |  | ||||||
| 	"strings" |  | ||||||
| 
 |  | ||||||
| 	"golang.org/x/tools/internal/gocommand" |  | ||||||
| 	"golang.org/x/tools/internal/imports" |  | ||||||
| ) |  | ||||||
| 
 |  | ||||||
| var ( |  | ||||||
| 	// main operation modes
 |  | ||||||
| 	list   = flag.Bool("l", false, "list files whose formatting differs from goimport's") |  | ||||||
| 	write  = flag.Bool("w", false, "write result to (source) file instead of stdout") |  | ||||||
| 	doDiff = flag.Bool("d", false, "display diffs instead of rewriting files") |  | ||||||
| 	srcdir = flag.String("srcdir", "", "choose imports as if source code is from `dir`. When operating on a single file, dir may instead be the complete file name.") |  | ||||||
| 
 |  | ||||||
| 	verbose bool // verbose logging
 |  | ||||||
| 
 |  | ||||||
| 	cpuProfile     = flag.String("cpuprofile", "", "CPU profile output") |  | ||||||
| 	memProfile     = flag.String("memprofile", "", "memory profile output") |  | ||||||
| 	memProfileRate = flag.Int("memrate", 0, "if > 0, sets runtime.MemProfileRate") |  | ||||||
| 
 |  | ||||||
| 	options = &imports.Options{ |  | ||||||
| 		TabWidth:  8, |  | ||||||
| 		TabIndent: true, |  | ||||||
| 		Comments:  true, |  | ||||||
| 		Fragment:  true, |  | ||||||
| 		Env: &imports.ProcessEnv{ |  | ||||||
| 			GocmdRunner: &gocommand.Runner{}, |  | ||||||
| 		}, |  | ||||||
| 	} |  | ||||||
| 	exitCode = 0 |  | ||||||
| ) |  | ||||||
| 
 |  | ||||||
| func init() { |  | ||||||
| 	flag.BoolVar(&options.AllErrors, "e", false, "report all errors (not just the first 10 on different lines)") |  | ||||||
| 	flag.StringVar(&options.LocalPrefix, "local", "", "put imports beginning with this string after 3rd-party packages; comma-separated list") |  | ||||||
| 	flag.BoolVar(&options.FormatOnly, "format-only", false, "if true, don't fix imports and only format. In this mode, goimports is effectively gofmt, with the addition that imports are grouped into sections.") |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func report(err error) { |  | ||||||
| 	scanner.PrintError(os.Stderr, err) |  | ||||||
| 	exitCode = 2 |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func usage() { |  | ||||||
| 	fmt.Fprintf(os.Stderr, "usage: goimports [flags] [path ...]\n") |  | ||||||
| 	flag.PrintDefaults() |  | ||||||
| 	os.Exit(2) |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func isGoFile(f os.FileInfo) bool { |  | ||||||
| 	// ignore non-Go files
 |  | ||||||
| 	name := f.Name() |  | ||||||
| 	return !f.IsDir() && !strings.HasPrefix(name, ".") && strings.HasSuffix(name, ".go") |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // argumentType is which mode goimports was invoked as.
 |  | ||||||
| type argumentType int |  | ||||||
| 
 |  | ||||||
| const ( |  | ||||||
| 	// fromStdin means the user is piping their source into goimports.
 |  | ||||||
| 	fromStdin argumentType = iota |  | ||||||
| 
 |  | ||||||
| 	// singleArg is the common case from editors, when goimports is run on
 |  | ||||||
| 	// a single file.
 |  | ||||||
| 	singleArg |  | ||||||
| 
 |  | ||||||
| 	// multipleArg is when the user ran "goimports file1.go file2.go"
 |  | ||||||
| 	// or ran goimports on a directory tree.
 |  | ||||||
| 	multipleArg |  | ||||||
| ) |  | ||||||
| 
 |  | ||||||
| func processFile(filename string, in io.Reader, out io.Writer, argType argumentType) error { |  | ||||||
| 	opt := options |  | ||||||
| 	if argType == fromStdin { |  | ||||||
| 		nopt := *options |  | ||||||
| 		nopt.Fragment = true |  | ||||||
| 		opt = &nopt |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if in == nil { |  | ||||||
| 		f, err := os.Open(filename) |  | ||||||
| 		if err != nil { |  | ||||||
| 			return err |  | ||||||
| 		} |  | ||||||
| 		defer f.Close() |  | ||||||
| 		in = f |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	src, err := io.ReadAll(in) |  | ||||||
| 	if err != nil { |  | ||||||
| 		return err |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	target := filename |  | ||||||
| 	if *srcdir != "" { |  | ||||||
| 		// Determine whether the provided -srcdirc is a directory or file
 |  | ||||||
| 		// and then use it to override the target.
 |  | ||||||
| 		//
 |  | ||||||
| 		// See https://github.com/dominikh/go-mode.el/issues/146
 |  | ||||||
| 		if isFile(*srcdir) { |  | ||||||
| 			if argType == multipleArg { |  | ||||||
| 				return errors.New("-srcdir value can't be a file when passing multiple arguments or when walking directories") |  | ||||||
| 			} |  | ||||||
| 			target = *srcdir |  | ||||||
| 		} else if argType == singleArg && strings.HasSuffix(*srcdir, ".go") && !isDir(*srcdir) { |  | ||||||
| 			// For a file which doesn't exist on disk yet, but might shortly.
 |  | ||||||
| 			// e.g. user in editor opens $DIR/newfile.go and newfile.go doesn't yet exist on disk.
 |  | ||||||
| 			// The goimports on-save hook writes the buffer to a temp file
 |  | ||||||
| 			// first and runs goimports before the actual save to newfile.go.
 |  | ||||||
| 			// The editor's buffer is named "newfile.go" so that is passed to goimports as:
 |  | ||||||
| 			//      goimports -srcdir=/gopath/src/pkg/newfile.go /tmp/gofmtXXXXXXXX.go
 |  | ||||||
| 			// and then the editor reloads the result from the tmp file and writes
 |  | ||||||
| 			// it to newfile.go.
 |  | ||||||
| 			target = *srcdir |  | ||||||
| 		} else { |  | ||||||
| 			// Pretend that file is from *srcdir in order to decide
 |  | ||||||
| 			// visible imports correctly.
 |  | ||||||
| 			target = filepath.Join(*srcdir, filepath.Base(filename)) |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	res, err := imports.Process(target, src, opt) |  | ||||||
| 	if err != nil { |  | ||||||
| 		return err |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if !bytes.Equal(src, res) { |  | ||||||
| 		// formatting has changed
 |  | ||||||
| 		if *list { |  | ||||||
| 			fmt.Fprintln(out, filename) |  | ||||||
| 		} |  | ||||||
| 		if *write { |  | ||||||
| 			if argType == fromStdin { |  | ||||||
| 				// filename is "<standard input>"
 |  | ||||||
| 				return errors.New("can't use -w on stdin") |  | ||||||
| 			} |  | ||||||
| 			// On Windows, we need to re-set the permissions from the file. See golang/go#38225.
 |  | ||||||
| 			var perms os.FileMode |  | ||||||
| 			if fi, err := os.Stat(filename); err == nil { |  | ||||||
| 				perms = fi.Mode() & os.ModePerm |  | ||||||
| 			} |  | ||||||
| 			err = os.WriteFile(filename, res, perms) |  | ||||||
| 			if err != nil { |  | ||||||
| 				return err |  | ||||||
| 			} |  | ||||||
| 		} |  | ||||||
| 		if *doDiff { |  | ||||||
| 			if argType == fromStdin { |  | ||||||
| 				filename = "stdin.go" // because <standard input>.orig looks silly
 |  | ||||||
| 			} |  | ||||||
| 			data, err := diff(src, res, filename) |  | ||||||
| 			if err != nil { |  | ||||||
| 				return fmt.Errorf("computing diff: %s", err) |  | ||||||
| 			} |  | ||||||
| 			fmt.Printf("diff -u %s %s\n", filepath.ToSlash(filename+".orig"), filepath.ToSlash(filename)) |  | ||||||
| 			out.Write(data) |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if !*list && !*write && !*doDiff { |  | ||||||
| 		_, err = out.Write(res) |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	return err |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func visitFile(path string, f os.FileInfo, err error) error { |  | ||||||
| 	if err == nil && isGoFile(f) { |  | ||||||
| 		err = processFile(path, nil, os.Stdout, multipleArg) |  | ||||||
| 	} |  | ||||||
| 	if err != nil { |  | ||||||
| 		report(err) |  | ||||||
| 	} |  | ||||||
| 	return nil |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func walkDir(path string) { |  | ||||||
| 	filepath.Walk(path, visitFile) |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func main() { |  | ||||||
| 	runtime.GOMAXPROCS(runtime.NumCPU()) |  | ||||||
| 
 |  | ||||||
| 	// call gofmtMain in a separate function
 |  | ||||||
| 	// so that it can use defer and have them
 |  | ||||||
| 	// run before the exit.
 |  | ||||||
| 	gofmtMain() |  | ||||||
| 	os.Exit(exitCode) |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // parseFlags parses command line flags and returns the paths to process.
 |  | ||||||
| // It's a var so that custom implementations can replace it in other files.
 |  | ||||||
| var parseFlags = func() []string { |  | ||||||
| 	flag.BoolVar(&verbose, "v", false, "verbose logging") |  | ||||||
| 
 |  | ||||||
| 	flag.Parse() |  | ||||||
| 	return flag.Args() |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func bufferedFileWriter(dest string) (w io.Writer, close func()) { |  | ||||||
| 	f, err := os.Create(dest) |  | ||||||
| 	if err != nil { |  | ||||||
| 		log.Fatal(err) |  | ||||||
| 	} |  | ||||||
| 	bw := bufio.NewWriter(f) |  | ||||||
| 	return bw, func() { |  | ||||||
| 		if err := bw.Flush(); err != nil { |  | ||||||
| 			log.Fatalf("error flushing %v: %v", dest, err) |  | ||||||
| 		} |  | ||||||
| 		if err := f.Close(); err != nil { |  | ||||||
| 			log.Fatal(err) |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func gofmtMain() { |  | ||||||
| 	flag.Usage = usage |  | ||||||
| 	paths := parseFlags() |  | ||||||
| 
 |  | ||||||
| 	if *cpuProfile != "" { |  | ||||||
| 		bw, flush := bufferedFileWriter(*cpuProfile) |  | ||||||
| 		pprof.StartCPUProfile(bw) |  | ||||||
| 		defer flush() |  | ||||||
| 		defer pprof.StopCPUProfile() |  | ||||||
| 	} |  | ||||||
| 	// doTrace is a conditionally compiled wrapper around runtime/trace. It is
 |  | ||||||
| 	// used to allow goimports to compile under gccgo, which does not support
 |  | ||||||
| 	// runtime/trace. See https://golang.org/issue/15544.
 |  | ||||||
| 	defer doTrace()() |  | ||||||
| 	if *memProfileRate > 0 { |  | ||||||
| 		runtime.MemProfileRate = *memProfileRate |  | ||||||
| 		bw, flush := bufferedFileWriter(*memProfile) |  | ||||||
| 		defer func() { |  | ||||||
| 			runtime.GC() // materialize all statistics
 |  | ||||||
| 			if err := pprof.WriteHeapProfile(bw); err != nil { |  | ||||||
| 				log.Fatal(err) |  | ||||||
| 			} |  | ||||||
| 			flush() |  | ||||||
| 		}() |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if verbose { |  | ||||||
| 		log.SetFlags(log.LstdFlags | log.Lmicroseconds) |  | ||||||
| 		options.Env.Logf = log.Printf |  | ||||||
| 	} |  | ||||||
| 	if options.TabWidth < 0 { |  | ||||||
| 		fmt.Fprintf(os.Stderr, "negative tabwidth %d\n", options.TabWidth) |  | ||||||
| 		exitCode = 2 |  | ||||||
| 		return |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if len(paths) == 0 { |  | ||||||
| 		if err := processFile("<standard input>", os.Stdin, os.Stdout, fromStdin); err != nil { |  | ||||||
| 			report(err) |  | ||||||
| 		} |  | ||||||
| 		return |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	argType := singleArg |  | ||||||
| 	if len(paths) > 1 { |  | ||||||
| 		argType = multipleArg |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	for _, path := range paths { |  | ||||||
| 		switch dir, err := os.Stat(path); { |  | ||||||
| 		case err != nil: |  | ||||||
| 			report(err) |  | ||||||
| 		case dir.IsDir(): |  | ||||||
| 			walkDir(path) |  | ||||||
| 		default: |  | ||||||
| 			if err := processFile(path, nil, os.Stdout, argType); err != nil { |  | ||||||
| 				report(err) |  | ||||||
| 			} |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func writeTempFile(dir, prefix string, data []byte) (string, error) { |  | ||||||
| 	file, err := os.CreateTemp(dir, prefix) |  | ||||||
| 	if err != nil { |  | ||||||
| 		return "", err |  | ||||||
| 	} |  | ||||||
| 	_, err = file.Write(data) |  | ||||||
| 	if err1 := file.Close(); err == nil { |  | ||||||
| 		err = err1 |  | ||||||
| 	} |  | ||||||
| 	if err != nil { |  | ||||||
| 		os.Remove(file.Name()) |  | ||||||
| 		return "", err |  | ||||||
| 	} |  | ||||||
| 	return file.Name(), nil |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| func diff(b1, b2 []byte, filename string) (data []byte, err error) { |  | ||||||
| 	f1, err := writeTempFile("", "gofmt", b1) |  | ||||||
| 	if err != nil { |  | ||||||
| 		return |  | ||||||
| 	} |  | ||||||
| 	defer os.Remove(f1) |  | ||||||
| 
 |  | ||||||
| 	f2, err := writeTempFile("", "gofmt", b2) |  | ||||||
| 	if err != nil { |  | ||||||
| 		return |  | ||||||
| 	} |  | ||||||
| 	defer os.Remove(f2) |  | ||||||
| 
 |  | ||||||
| 	cmd := "diff" |  | ||||||
| 	if runtime.GOOS == "plan9" { |  | ||||||
| 		cmd = "/bin/ape/diff" |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	data, err = exec.Command(cmd, "-u", f1, f2).CombinedOutput() |  | ||||||
| 	if len(data) > 0 { |  | ||||||
| 		// diff exits with a non-zero status when the files don't match.
 |  | ||||||
| 		// Ignore that failure as long as we get output.
 |  | ||||||
| 		return replaceTempFilename(data, filename) |  | ||||||
| 	} |  | ||||||
| 	return |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // replaceTempFilename replaces temporary filenames in diff with actual one.
 |  | ||||||
| //
 |  | ||||||
| // --- /tmp/gofmt316145376	2017-02-03 19:13:00.280468375 -0500
 |  | ||||||
| // +++ /tmp/gofmt617882815	2017-02-03 19:13:00.280468375 -0500
 |  | ||||||
| // ...
 |  | ||||||
| // ->
 |  | ||||||
| // --- path/to/file.go.orig	2017-02-03 19:13:00.280468375 -0500
 |  | ||||||
| // +++ path/to/file.go	2017-02-03 19:13:00.280468375 -0500
 |  | ||||||
| // ...
 |  | ||||||
| func replaceTempFilename(diff []byte, filename string) ([]byte, error) { |  | ||||||
| 	bs := bytes.SplitN(diff, []byte{'\n'}, 3) |  | ||||||
| 	if len(bs) < 3 { |  | ||||||
| 		return nil, fmt.Errorf("got unexpected diff for %s", filename) |  | ||||||
| 	} |  | ||||||
| 	// Preserve timestamps.
 |  | ||||||
| 	var t0, t1 []byte |  | ||||||
| 	if i := bytes.LastIndexByte(bs[0], '\t'); i != -1 { |  | ||||||
| 		t0 = bs[0][i:] |  | ||||||
| 	} |  | ||||||
| 	if i := bytes.LastIndexByte(bs[1], '\t'); i != -1 { |  | ||||||
| 		t1 = bs[1][i:] |  | ||||||
| 	} |  | ||||||
| 	// Always print filepath with slash separator.
 |  | ||||||
| 	f := filepath.ToSlash(filename) |  | ||||||
| 	bs[0] = []byte(fmt.Sprintf("--- %s%s", f+".orig", t0)) |  | ||||||
| 	bs[1] = []byte(fmt.Sprintf("+++ %s%s", f, t1)) |  | ||||||
| 	return bytes.Join(bs, []byte{'\n'}), nil |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // isFile reports whether name is a file.
 |  | ||||||
| func isFile(name string) bool { |  | ||||||
| 	fi, err := os.Stat(name) |  | ||||||
| 	return err == nil && fi.Mode().IsRegular() |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // isDir reports whether name is a directory.
 |  | ||||||
| func isDir(name string) bool { |  | ||||||
| 	fi, err := os.Stat(name) |  | ||||||
| 	return err == nil && fi.IsDir() |  | ||||||
| } |  | ||||||
|  | @ -1,27 +0,0 @@ | ||||||
| // Copyright 2016 The Go Authors. All rights reserved.
 |  | ||||||
| // Use of this source code is governed by a BSD-style
 |  | ||||||
| // license that can be found in the LICENSE file.
 |  | ||||||
| 
 |  | ||||||
| //go:build gc
 |  | ||||||
| // +build gc
 |  | ||||||
| 
 |  | ||||||
| package main |  | ||||||
| 
 |  | ||||||
| import ( |  | ||||||
| 	"flag" |  | ||||||
| 	"runtime/trace" |  | ||||||
| ) |  | ||||||
| 
 |  | ||||||
| var traceProfile = flag.String("trace", "", "trace profile output") |  | ||||||
| 
 |  | ||||||
| func doTrace() func() { |  | ||||||
| 	if *traceProfile != "" { |  | ||||||
| 		bw, flush := bufferedFileWriter(*traceProfile) |  | ||||||
| 		trace.Start(bw) |  | ||||||
| 		return func() { |  | ||||||
| 			trace.Stop() |  | ||||||
| 			flush() |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	return func() {} |  | ||||||
| } |  | ||||||
|  | @ -1,12 +0,0 @@ | ||||||
| // Copyright 2016 The Go Authors. All rights reserved.
 |  | ||||||
| // Use of this source code is governed by a BSD-style
 |  | ||||||
| // license that can be found in the LICENSE file.
 |  | ||||||
| 
 |  | ||||||
| //go:build !gc
 |  | ||||||
| // +build !gc
 |  | ||||||
| 
 |  | ||||||
| package main |  | ||||||
| 
 |  | ||||||
| func doTrace() func() { |  | ||||||
| 	return func() {} |  | ||||||
| } |  | ||||||
|  | @ -1,12 +0,0 @@ | ||||||
| // Copyright 2024 The Go Authors. All rights reserved.
 |  | ||||||
| // Use of this source code is governed by a BSD-style
 |  | ||||||
| // license that can be found in the LICENSE file.
 |  | ||||||
| 
 |  | ||||||
| //go:build go1.23
 |  | ||||||
| 
 |  | ||||||
| //go:debug gotypesalias=1
 |  | ||||||
| 
 |  | ||||||
| package main |  | ||||||
| 
 |  | ||||||
| // Materialize aliases whenever the go toolchain version is after 1.23 (#69772).
 |  | ||||||
| // Remove this file after go.mod >= 1.23 (which implies gotypesalias=1).
 |  | ||||||
|  | @ -244,7 +244,6 @@ golang.org/x/text/transform | ||||||
| golang.org/x/text/unicode/norm | golang.org/x/text/unicode/norm | ||||||
| # golang.org/x/tools v0.30.0 | # golang.org/x/tools v0.30.0 | ||||||
| ## explicit; go 1.22.0 | ## explicit; go 1.22.0 | ||||||
| golang.org/x/tools/cmd/goimports |  | ||||||
| golang.org/x/tools/go/ast/astutil | golang.org/x/tools/go/ast/astutil | ||||||
| golang.org/x/tools/go/buildutil | golang.org/x/tools/go/buildutil | ||||||
| golang.org/x/tools/go/gcexportdata | golang.org/x/tools/go/gcexportdata | ||||||
|  |  | ||||||
		Loading…
	
		Reference in New Issue