Skip to content

Commit

Permalink
Excavator: Manage go version (#134)
Browse files Browse the repository at this point in the history
  • Loading branch information
svc-excavator-bot authored Sep 12, 2022
1 parent d85f45f commit 206374e
Show file tree
Hide file tree
Showing 6 changed files with 242 additions and 68 deletions.
2 changes: 1 addition & 1 deletion .palantir/go-version
Original file line number Diff line number Diff line change
@@ -1 +1 @@
go1.18.5
go1.19.1
35 changes: 35 additions & 0 deletions generated_src/internal/amalgomated_flag/example_textvar_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
// Copyright 2022 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 flag_test

import (
"flag"
"fmt"
"net"
"os"
)

func ExampleTextVar() {
fs := flag.NewFlagSet("ExampleTextVar", flag.ContinueOnError)
fs.SetOutput(os.Stdout)
var ip net.IP
fs.TextVar(&ip, "ip", net.IPv4(192, 168, 0, 100), "`IP address` to parse")
fs.Parse([]string{"-ip", "127.0.0.1"})
fmt.Printf("{ip: %v}\n\n", ip)

// 256 is not a valid IPv4 component
ip = nil
fs.Parse([]string{"-ip", "256.0.0.1"})
fmt.Printf("{ip: %v}\n\n", ip)

// Output:
// {ip: 127.0.0.1}
//
// invalid value "256.0.0.1" for flag -ip: invalid IP address: 256.0.0.1
// Usage of ExampleTextVar:
// -ip IP address
// IP address to parse (default 192.168.0.100)
// {ip: <nil>}
}
6 changes: 5 additions & 1 deletion generated_src/internal/amalgomated_flag/export_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,10 @@

package flag

import "os"
import (
"io"
"os"
)

// Additional routines compiled into the package only during testing.

Expand All @@ -15,6 +18,7 @@ var DefaultUsage = Usage
// exit the program.
func ResetForTesting(usage func()) {
CommandLine = NewFlagSet(os.Args[0], ContinueOnError)
CommandLine.SetOutput(io.Discard)
CommandLine.Usage = commandLineUsage
Usage = usage
}
223 changes: 162 additions & 61 deletions generated_src/internal/amalgomated_flag/flag.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,71 +3,87 @@
// license that can be found in the LICENSE file.

/*
Package flag implements command-line flag parsing.
Package flag implements command-line flag parsing.
Usage
# Usage
Define flags using flag.String(), Bool(), Int(), etc.
Define flags using flag.String(), Bool(), Int(), etc.
This declares an integer flag, -n, stored in the pointer nFlag, with type *int:
import "flag"
var nFlag = flag.Int("n", 1234, "help message for flag n")
If you like, you can bind the flag to a variable using the Var() functions.
var flagvar int
func init() {
flag.IntVar(&flagvar, "flagname", 1234, "help message for flagname")
}
Or you can create custom flags that satisfy the Value interface (with
pointer receivers) and couple them to flag parsing by
flag.Var(&flagVal, "name", "help message for flagname")
For such flags, the default value is just the initial value of the variable.
After all flags are defined, call
flag.Parse()
to parse the command line into the defined flags.
Flags may then be used directly. If you're using the flags themselves,
they are all pointers; if you bind to variables, they're values.
fmt.Println("ip has value ", *ip)
fmt.Println("flagvar has value ", flagvar)
After parsing, the arguments following the flags are available as the
slice flag.Args() or individually as flag.Arg(i).
The arguments are indexed from 0 through flag.NArg()-1.
Command line flag syntax
The following forms are permitted:
-flag
-flag=x
-flag x // non-boolean flags only
One or two minus signs may be used; they are equivalent.
The last form is not permitted for boolean flags because the
meaning of the command
cmd -x *
where * is a Unix shell wildcard, will change if there is a file
called 0, false, etc. You must use the -flag=false form to turn
off a boolean flag.
Flag parsing stops just before the first non-flag argument
("-" is a non-flag argument) or after the terminator "--".
Integer flags accept 1234, 0664, 0x1234 and may be negative.
Boolean flags may be:
1, 0, t, f, T, F, true, false, TRUE, FALSE, True, False
Duration flags accept any input valid for time.ParseDuration.
The default set of command-line flags is controlled by
top-level functions. The FlagSet type allows one to define
independent sets of flags, such as to implement subcommands
in a command-line interface. The methods of FlagSet are
analogous to the top-level functions for the command-line
flag set.
This declares an integer flag, -n, stored in the pointer nFlag, with type *int:
import "flag"
var nFlag = flag.Int("n", 1234, "help message for flag n")
If you like, you can bind the flag to a variable using the Var() functions.
var flagvar int
func init() {
flag.IntVar(&flagvar, "flagname", 1234, "help message for flagname")
}
Or you can create custom flags that satisfy the Value interface (with
pointer receivers) and couple them to flag parsing by
flag.Var(&flagVal, "name", "help message for flagname")
For such flags, the default value is just the initial value of the variable.
After all flags are defined, call
flag.Parse()
to parse the command line into the defined flags.
Flags may then be used directly. If you're using the flags themselves,
they are all pointers; if you bind to variables, they're values.
fmt.Println("ip has value ", *ip)
fmt.Println("flagvar has value ", flagvar)
After parsing, the arguments following the flags are available as the
slice flag.Args() or individually as flag.Arg(i).
The arguments are indexed from 0 through flag.NArg()-1.
# Command line flag syntax
The following forms are permitted:
-flag
--flag // double dashes are also permitted
-flag=x
-flag x // non-boolean flags only
One or two dashes may be used; they are equivalent.
The last form is not permitted for boolean flags because the
meaning of the command
cmd -x *
where * is a Unix shell wildcard, will change if there is a file
called 0, false, etc. You must use the -flag=false form to turn
off a boolean flag.
Flag parsing stops just before the first non-flag argument
("-" is a non-flag argument) or after the terminator "--".
Integer flags accept 1234, 0664, 0x1234 and may be negative.
Boolean flags may be:
1, 0, t, f, T, F, true, false, TRUE, FALSE, True, False
Duration flags accept any input valid for time.ParseDuration.
The default set of command-line flags is controlled by
top-level functions. The FlagSet type allows one to define
independent sets of flags, such as to implement subcommands
in a command-line interface. The methods of FlagSet are
analogous to the top-level functions for the command-line
flag set.
*/
package flag

import (
"encoding"
"errors"
"fmt"
"io"
Expand Down Expand Up @@ -278,6 +294,43 @@ func (d *durationValue) Get() any { return time.Duration(*d) }

func (d *durationValue) String() string { return (*time.Duration)(d).String() }

// -- encoding.TextUnmarshaler Value
type textValue struct{ p encoding.TextUnmarshaler }

func newTextValue(val encoding.TextMarshaler, p encoding.TextUnmarshaler) textValue {
ptrVal := reflect.ValueOf(p)
if ptrVal.Kind() != reflect.Ptr {
panic("variable value type must be a pointer")
}
defVal := reflect.ValueOf(val)
if defVal.Kind() == reflect.Ptr {
defVal = defVal.Elem()
}
if defVal.Type() != ptrVal.Type().Elem() {
panic(fmt.Sprintf("default type does not match variable type: %v != %v", defVal.Type(), ptrVal.Type().Elem()))
}
ptrVal.Elem().Set(defVal)
return textValue{p}
}

func (v textValue) Set(s string) error {
return v.p.UnmarshalText([]byte(s))
}

func (v textValue) Get() interface{} {
return v.p
}

func (v textValue) String() string {
if m, ok := v.p.(encoding.TextMarshaler); ok {
if b, err := m.MarshalText(); err == nil {
return string(b)
}
}
return ""
}

// -- func Value
type funcValue func(string) error

func (f funcValue) Set(s string) error { return f(s) }
Expand Down Expand Up @@ -450,7 +503,7 @@ func Set(name, value string) error {

// isZeroValue determines whether the string represents the zero
// value for a flag.
func isZeroValue(flag *Flag, value string) bool {
func isZeroValue(flag *Flag, value string) (ok bool, err error) {
// Build a zero value of the flag's Value type, and see if the
// result of calling its String method equals the value passed in.
// This works unless the Value type is itself an interface type.
Expand All @@ -461,7 +514,18 @@ func isZeroValue(flag *Flag, value string) bool {
} else {
z = reflect.Zero(typ)
}
return value == z.Interface().(Value).String()
// Catch panics calling the String method, which shouldn't prevent the
// usage message from being printed, but that we should report to the
// user so that they know to fix their code.
defer func() {
if e := recover(); e != nil {
if typ.Kind() == reflect.Pointer {
typ = typ.Elem()
}
err = fmt.Errorf("panic calling String method on zero %v for flag %s: %v", typ, flag.Name, e)
}
}()
return value == z.Interface().(Value).String(), nil
}

// UnquoteUsage extracts a back-quoted name from the usage
Expand Down Expand Up @@ -507,6 +571,7 @@ func UnquoteUsage(flag *Flag) (name string, usage string) {
// default values of all defined command-line flags in the set. See the
// documentation for the global function PrintDefaults for more information.
func (f *FlagSet) PrintDefaults() {
var isZeroValueErrs []error
f.VisitAll(func(flag *Flag) {
var b strings.Builder
fmt.Fprintf(&b, " -%s", flag.Name) // Two spaces before -; see next two comments.
Expand All @@ -526,7 +591,11 @@ func (f *FlagSet) PrintDefaults() {
}
b.WriteString(strings.ReplaceAll(usage, "\n", "\n \t"))

if !isZeroValue(flag, flag.DefValue) {
// Print the default value only if it differs to the zero value
// for this flag type.
if isZero, err := isZeroValue(flag, flag.DefValue); err != nil {
isZeroValueErrs = append(isZeroValueErrs, err)
} else if !isZero {
if _, ok := flag.Value.(*stringValue); ok {
// put quotes on the value
fmt.Fprintf(&b, " (default %q)", flag.DefValue)
Expand All @@ -536,14 +605,25 @@ func (f *FlagSet) PrintDefaults() {
}
fmt.Fprint(f.Output(), b.String(), "\n")
})
// If calling String on any zero flag.Values triggered a panic, print
// the messages after the full set of defaults so that the programmer
// knows to fix the panic.
if errs := isZeroValueErrs; len(errs) > 0 {
fmt.Fprintln(f.Output())
for _, err := range errs {
fmt.Fprintln(f.Output(), err)
}
}
}

// PrintDefaults prints, to standard error unless configured otherwise,
// a usage message showing the default settings of all defined
// command-line flags.
// For an integer valued flag x, the default output has the form
//
// -x int
// usage-message-for-x (default 7)
//
// The usage message will appear on a separate line for anything but
// a bool flag with a one-byte name. For bool flags, the type is
// omitted and if the flag name is one byte the usage message appears
Expand All @@ -553,8 +633,11 @@ func (f *FlagSet) PrintDefaults() {
// string; the first such item in the message is taken to be a parameter
// name to show in the message and the back quotes are stripped from
// the message when displayed. For instance, given
//
// flag.String("I", "", "search `directory` for include files")
//
// the output will be
//
// -I directory
// search directory for include files.
//
Expand Down Expand Up @@ -838,6 +921,24 @@ func Duration(name string, value time.Duration, usage string) *time.Duration {
return CommandLine.Duration(name, value, usage)
}

// TextVar defines a flag with a specified name, default value, and usage string.
// The argument p must be a pointer to a variable that will hold the value
// of the flag, and p must implement encoding.TextUnmarshaler.
// If the flag is used, the flag value will be passed to p's UnmarshalText method.
// The type of the default value must be the same as the type of p.
func (f *FlagSet) TextVar(p encoding.TextUnmarshaler, name string, value encoding.TextMarshaler, usage string) {
f.Var(newTextValue(value, p), name, usage)
}

// TextVar defines a flag with a specified name, default value, and usage string.
// The argument p must be a pointer to a variable that will hold the value
// of the flag, and p must implement encoding.TextUnmarshaler.
// If the flag is used, the flag value will be passed to p's UnmarshalText method.
// The type of the default value must be the same as the type of p.
func TextVar(p encoding.TextUnmarshaler, name string, value encoding.TextMarshaler, usage string) {
CommandLine.Var(newTextValue(value, p), name, usage)
}

// Func defines a flag with the specified name and usage string.
// Each time the flag is seen, fn is called with the value of the flag.
// If fn returns a non-nil error, it will be treated as a flag value parsing error.
Expand Down
Loading

0 comments on commit 206374e

Please sign in to comment.