add new slice type parser, add help flag
Some checks failed
continuous-integration/drone/push Build is failing
Some checks failed
continuous-integration/drone/push Build is failing
This commit is contained in:
parent
c1f8fa376a
commit
b619f2f11e
112
argparse.go
112
argparse.go
@ -3,22 +3,30 @@ package argparse
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"reflect"
|
||||
"strings"
|
||||
)
|
||||
|
||||
type Parser struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
args []*arg
|
||||
showHelp bool
|
||||
parsed bool
|
||||
}
|
||||
|
||||
type Option struct {
|
||||
Require bool
|
||||
}
|
||||
|
||||
type arg struct {
|
||||
sname string
|
||||
lname string
|
||||
// value number count
|
||||
// value item count
|
||||
size int
|
||||
value interface{}
|
||||
unique bool
|
||||
parsed bool
|
||||
opts *Option
|
||||
}
|
||||
|
||||
func New() *Parser {
|
||||
@ -29,7 +37,7 @@ func New() *Parser {
|
||||
|
||||
func (p *Parser) addArg(a *arg) error {
|
||||
for _, v := range p.args {
|
||||
if (v.sname == a.sname || v.lname == a.lname) && (a.unique || v.unique) {
|
||||
if v.sname == a.sname || v.lname == a.lname {
|
||||
return errors.New("option name dup")
|
||||
}
|
||||
}
|
||||
@ -38,11 +46,14 @@ func (p *Parser) addArg(a *arg) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (p *Parser) typeVar(i interface{}, short, long string, size int, unique bool) {
|
||||
func (p *Parser) typeVar(i interface{}, short, long string, size int, unique bool, opts *Option) {
|
||||
t := reflect.ValueOf(i)
|
||||
if t.Kind() != reflect.Ptr {
|
||||
panic(errors.New("var type not ptr"))
|
||||
}
|
||||
if short == "" && long == "" {
|
||||
panic(errors.New("short name and long name is empty"))
|
||||
}
|
||||
|
||||
a := &arg{
|
||||
sname: short,
|
||||
@ -50,6 +61,7 @@ func (p *Parser) typeVar(i interface{}, short, long string, size int, unique boo
|
||||
value: i,
|
||||
size: size,
|
||||
unique: unique,
|
||||
opts: opts,
|
||||
}
|
||||
|
||||
if err := p.addArg(a); err != nil {
|
||||
@ -57,6 +69,24 @@ func (p *Parser) typeVar(i interface{}, short, long string, size int, unique boo
|
||||
}
|
||||
}
|
||||
|
||||
func (p *Parser) Help(short, long string) {
|
||||
p.typeVar(&p.showHelp, short, long, 0, true, nil)
|
||||
}
|
||||
|
||||
func (p *Parser) printHelp() {
|
||||
sb := &strings.Builder{}
|
||||
sb.WriteString("Usage:\n")
|
||||
for _, v := range p.args {
|
||||
if _, err := sb.WriteString(fmt.Sprintf("\t%s\t%s\n", v.name(), v.getType())); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
}
|
||||
fmt.Println(sb.String())
|
||||
// if flag.Lookup("test.v") == nil {
|
||||
os.Exit(2)
|
||||
// }
|
||||
}
|
||||
|
||||
func (p *Parser) Parse(a []string) error {
|
||||
copyArg := make([]string, len(a))
|
||||
copy(copyArg, a)
|
||||
@ -84,6 +114,10 @@ func (p *Parser) parse(args *[]string) error {
|
||||
}
|
||||
|
||||
p.parsed = true
|
||||
|
||||
if p.showHelp == true {
|
||||
p.printHelp()
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
@ -117,52 +151,88 @@ func (p *Parser) parseArguemtns(args *[]string) error {
|
||||
continue
|
||||
}
|
||||
}
|
||||
if oarg.opts != nil && oarg.opts.Require && !oarg.parsed {
|
||||
return fmt.Errorf("[%s] is required", oarg.name())
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (p *Parser) String(short, long string) *string {
|
||||
func (p *Parser) String(short, long string, opts *Option) *string {
|
||||
var result string
|
||||
|
||||
p.typeVar(&result, short, long, 1, true)
|
||||
p.typeVar(&result, short, long, 1, true, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) StringVar(i *string, short, long string) {
|
||||
p.typeVar(i, short, long, 1, true)
|
||||
func (p *Parser) StringVar(i *string, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 1, true, opts)
|
||||
}
|
||||
|
||||
func (p *Parser) Int(short, long string) *int {
|
||||
func (p *Parser) Int(short, long string, opts *Option) *int {
|
||||
var result int
|
||||
|
||||
p.typeVar(&result, short, long, 1, true)
|
||||
p.typeVar(&result, short, long, 1, true, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) IntVar(i *int, short, long string) {
|
||||
p.typeVar(i, short, long, 1, true)
|
||||
func (p *Parser) IntVar(i *int, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 1, true, opts)
|
||||
}
|
||||
|
||||
func (p *Parser) Bool(short, long string) *bool {
|
||||
func (p *Parser) Bool(short, long string, opts *Option) *bool {
|
||||
var result bool
|
||||
|
||||
p.typeVar(&result, short, long, 0, true)
|
||||
p.typeVar(&result, short, long, 0, true, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) BoolVar(i *bool, short, long string) {
|
||||
p.typeVar(i, short, long, 0, true)
|
||||
func (p *Parser) BoolVar(i *bool, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 0, true, opts)
|
||||
}
|
||||
|
||||
func (p *Parser) Float(short, long string) *float64 {
|
||||
func (p *Parser) Float(short, long string, opts *Option) *float64 {
|
||||
var result float64
|
||||
|
||||
p.typeVar(&result, short, long, 1, true)
|
||||
p.typeVar(&result, short, long, 1, true, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) FloatVar(i *float64, short, long string) {
|
||||
p.typeVar(i, short, long, 1, true)
|
||||
func (p *Parser) FloatVar(i *float64, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 1, true, opts)
|
||||
}
|
||||
|
||||
func (p *Parser) StringSlice(short, long string, opts *Option) *[]string {
|
||||
var result []string
|
||||
|
||||
p.typeVar(&result, short, long, 1, false, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) StringSliceVar(i *[]string, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 1, false, opts)
|
||||
}
|
||||
|
||||
func (p *Parser) IntSlice(short, long string, opts *Option) *[]int {
|
||||
var result []int
|
||||
|
||||
p.typeVar(&result, short, long, 1, false, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) IntSliceVar(i *[]int, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 1, false, opts)
|
||||
}
|
||||
|
||||
func (p *Parser) FloatSlice(short, long string, opts *Option) *[]float64 {
|
||||
var result []float64
|
||||
|
||||
p.typeVar(&result, short, long, 1, false, opts)
|
||||
|
||||
return &result
|
||||
}
|
||||
func (p *Parser) FloatSliceVar(i *[]float64, short, long string, opts *Option) {
|
||||
p.typeVar(i, short, long, 1, false, opts)
|
||||
}
|
||||
|
285
argparse_test.go
285
argparse_test.go
@ -99,7 +99,7 @@ func TestParser_typeVar(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.typeVar(tt.args.i, tt.args.short, tt.args.long, tt.args.size, tt.args.unique)
|
||||
p.typeVar(tt.args.i, tt.args.short, tt.args.long, tt.args.size, tt.args.unique, nil)
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -277,7 +277,7 @@ func TestParser_String(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.String(tt.args.short, tt.args.long); got == nil {
|
||||
if got := p.String(tt.args.short, tt.args.long, nil); got == nil {
|
||||
t.Errorf("Parser.String() = %v", got)
|
||||
}
|
||||
})
|
||||
@ -316,7 +316,7 @@ func TestParser_StringVar(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.StringVar(tt.args.i, tt.args.short, tt.args.long)
|
||||
p.StringVar(tt.args.i, tt.args.short, tt.args.long, nil)
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -350,7 +350,7 @@ func TestParser_Int(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.Int(tt.args.short, tt.args.long); got == nil {
|
||||
if got := p.Int(tt.args.short, tt.args.long, nil); got == nil {
|
||||
t.Errorf("Parser.Int() = %v", got)
|
||||
}
|
||||
})
|
||||
@ -389,7 +389,7 @@ func TestParser_IntVar(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.IntVar(tt.args.i, tt.args.short, tt.args.long)
|
||||
p.IntVar(tt.args.i, tt.args.short, tt.args.long, nil)
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -423,7 +423,7 @@ func TestParser_Bool(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.Bool(tt.args.short, tt.args.long); got == nil {
|
||||
if got := p.Bool(tt.args.short, tt.args.long, nil); got == nil {
|
||||
t.Errorf("Parser.Bool() = %v", got)
|
||||
}
|
||||
})
|
||||
@ -462,7 +462,7 @@ func TestParser_BoolVar(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.BoolVar(tt.args.i, tt.args.short, tt.args.long)
|
||||
p.BoolVar(tt.args.i, tt.args.short, tt.args.long, nil)
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -496,7 +496,7 @@ func TestParser_Float(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.Float(tt.args.short, tt.args.long); got == nil {
|
||||
if got := p.Float(tt.args.short, tt.args.long, nil); got == nil {
|
||||
t.Errorf("Parser.Float() = %v", got)
|
||||
}
|
||||
})
|
||||
@ -535,7 +535,274 @@ func TestParser_FloatVar(t *testing.T) {
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.FloatVar(tt.args.i, tt.args.short, tt.args.long)
|
||||
p.FloatVar(tt.args.i, tt.args.short, tt.args.long, nil)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_StringSlice(t *testing.T) {
|
||||
type fields struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
short string
|
||||
long string
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add string slice to parser",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
short: "d",
|
||||
long: "",
|
||||
opts: nil,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.StringSlice(tt.args.short, tt.args.long, tt.args.opts); got == nil {
|
||||
t.Errorf("Parser.StringSlice() = %v", got)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_StringSliceVar(t *testing.T) {
|
||||
var s []string
|
||||
type fields struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
i *[]string
|
||||
short string
|
||||
long string
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add string slice to parser (ptr)",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
i: &s,
|
||||
short: "d",
|
||||
long: "",
|
||||
opts: nil,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.StringSliceVar(tt.args.i, tt.args.short, tt.args.long, tt.args.opts)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_IntSlice(t *testing.T) {
|
||||
type fields struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
short string
|
||||
long string
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add int slice to parser",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
short: "i",
|
||||
long: "",
|
||||
opts: nil,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.IntSlice(tt.args.short, tt.args.long, tt.args.opts); got == nil {
|
||||
t.Errorf("Parser.IntSlice() = %v", got)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_IntSliceVar(t *testing.T) {
|
||||
var i []int
|
||||
type fields struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
i *[]int
|
||||
short string
|
||||
long string
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add int slice to parser (ptr)",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
i: &i,
|
||||
short: "i",
|
||||
long: "",
|
||||
opts: nil,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.IntSliceVar(tt.args.i, tt.args.short, tt.args.long, tt.args.opts)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_FloatSliceVar(t *testing.T) {
|
||||
var f []float64
|
||||
type fields struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
i *[]float64
|
||||
short string
|
||||
long string
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add float slice to parser (ptr)",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
i: &f,
|
||||
short: "f",
|
||||
long: "",
|
||||
opts: nil,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.FloatSliceVar(tt.args.i, tt.args.short, tt.args.long, tt.args.opts)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_FloatSlice(t *testing.T) {
|
||||
type fields struct {
|
||||
args []*arg
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
short string
|
||||
long string
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add float slice to parser",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
short: "f",
|
||||
long: "",
|
||||
opts: nil,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
if got := p.FloatSlice(tt.args.short, tt.args.long, tt.args.opts); got == nil {
|
||||
t.Errorf("Parser.FloatSlice() = %v", got)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestParser_Help(t *testing.T) {
|
||||
type fields struct {
|
||||
args []*arg
|
||||
showHelp bool
|
||||
parsed bool
|
||||
}
|
||||
type args struct {
|
||||
short string
|
||||
long string
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
}{
|
||||
{
|
||||
name: "test add help flag to parser",
|
||||
fields: fields{},
|
||||
args: args{
|
||||
short: "h",
|
||||
long: "",
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
p := &Parser{
|
||||
args: tt.fields.args,
|
||||
showHelp: tt.fields.showHelp,
|
||||
parsed: tt.fields.parsed,
|
||||
}
|
||||
p.Help(tt.args.short, tt.args.long)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
76
argument.go
76
argument.go
@ -83,7 +83,28 @@ func (a *arg) name() string {
|
||||
} else if a.lname == "" {
|
||||
return fmt.Sprintf("-%s", a.sname)
|
||||
} else {
|
||||
return fmt.Sprintf("-%s|--%s", a.sname, a.lname)
|
||||
return fmt.Sprintf("-%s | --%s", a.sname, a.lname)
|
||||
}
|
||||
}
|
||||
|
||||
func (a *arg) getType() string {
|
||||
switch a.value.(type) {
|
||||
case *string:
|
||||
return "string"
|
||||
case *int:
|
||||
return "int"
|
||||
case *bool:
|
||||
return "bool"
|
||||
case *float64:
|
||||
return "float"
|
||||
case *[]string:
|
||||
return "[]string"
|
||||
case *[]int:
|
||||
return "[]int"
|
||||
case *[]float64:
|
||||
return "[]float"
|
||||
default:
|
||||
return "not support"
|
||||
}
|
||||
}
|
||||
|
||||
@ -106,8 +127,11 @@ func (a *arg) parseType(args []string) error {
|
||||
case *float64:
|
||||
return a.parseFloat(args)
|
||||
case *[]string:
|
||||
return a.parseStringSlice(args)
|
||||
case *[]int:
|
||||
return a.parseIntSlice(args)
|
||||
case *[]float64:
|
||||
return a.parseFloatSlice(args)
|
||||
default:
|
||||
err = fmt.Errorf("unsupport type [%t]", a.value)
|
||||
}
|
||||
@ -130,6 +154,17 @@ func (a *arg) parseString(args []string) error {
|
||||
return err
|
||||
}
|
||||
|
||||
func (a *arg) parseStringSlice(args []string) (err error) {
|
||||
if len(args) == 0 {
|
||||
return ErrNoArg
|
||||
}
|
||||
|
||||
*((a.value).(*[]string)) = append(*((a.value).(*[]string)), args...)
|
||||
a.parsed = true
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (a *arg) parseInt(args []string) error {
|
||||
var err error
|
||||
|
||||
@ -144,12 +179,30 @@ func (a *arg) parseInt(args []string) error {
|
||||
*((a.value).(*int)) = i
|
||||
a.parsed = true
|
||||
} else {
|
||||
return fmt.Errorf("[%s] bad int value", a.name())
|
||||
return fmt.Errorf("[%s] bad int value (%v)", a.name(), args[0])
|
||||
}
|
||||
|
||||
return err
|
||||
}
|
||||
|
||||
func (a *arg) parseIntSlice(args []string) (err error) {
|
||||
if len(args) == 0 {
|
||||
return ErrNoArg
|
||||
}
|
||||
|
||||
for _, v := range args {
|
||||
if i, err := strconv.Atoi(v); err == nil {
|
||||
*((a.value).(*[]int)) = append(*((a.value).(*[]int)), i)
|
||||
} else {
|
||||
return fmt.Errorf("[%s] bad int value (%v)", a.name(), v)
|
||||
}
|
||||
}
|
||||
|
||||
a.parsed = true
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (a *arg) parseBool(args []string) error {
|
||||
*a.value.(*bool) = true
|
||||
a.parsed = true
|
||||
@ -168,7 +221,24 @@ func (a *arg) parseFloat(args []string) (err error) {
|
||||
*a.value.(*float64) = f
|
||||
a.parsed = true
|
||||
} else {
|
||||
return fmt.Errorf("[%s] bad float value", a.name())
|
||||
return fmt.Errorf("[%s] bad float value (%v)", a.name(), args[0])
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
func (a *arg) parseFloatSlice(args []string) (err error) {
|
||||
if len(args) == 0 {
|
||||
return ErrNoArg
|
||||
}
|
||||
|
||||
for _, v := range args {
|
||||
if f, err := strconv.ParseFloat(v, 64); err == nil {
|
||||
*((a.value).(*[]float64)) = append(*((a.value).(*[]float64)), f)
|
||||
} else {
|
||||
return fmt.Errorf("[%s] bad float value (%v)", a.name(), v)
|
||||
}
|
||||
}
|
||||
a.parsed = true
|
||||
|
||||
return
|
||||
}
|
||||
|
217
argument_test.go
217
argument_test.go
@ -1,6 +1,8 @@
|
||||
package argparse
|
||||
|
||||
import "testing"
|
||||
import (
|
||||
"testing"
|
||||
)
|
||||
|
||||
func Test_arg_check(t *testing.T) {
|
||||
type fields struct {
|
||||
@ -698,3 +700,216 @@ func Test_arg_parseFloat(t *testing.T) {
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func Test_arg_parseStringSlice(t *testing.T) {
|
||||
var s []string
|
||||
type fields struct {
|
||||
sname string
|
||||
lname string
|
||||
size int
|
||||
value interface{}
|
||||
unique bool
|
||||
parsed bool
|
||||
opts *Option
|
||||
}
|
||||
type args struct {
|
||||
args []string
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
wantErr bool
|
||||
}{
|
||||
{
|
||||
name: "test argument parseStringSlice",
|
||||
fields: fields{
|
||||
size: 1,
|
||||
value: &s,
|
||||
unique: false,
|
||||
},
|
||||
args: args{
|
||||
args: []string{
|
||||
"a", "b", "c",
|
||||
},
|
||||
},
|
||||
wantErr: false,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
a := &arg{
|
||||
sname: tt.fields.sname,
|
||||
lname: tt.fields.lname,
|
||||
size: tt.fields.size,
|
||||
value: tt.fields.value,
|
||||
unique: tt.fields.unique,
|
||||
parsed: tt.fields.parsed,
|
||||
opts: tt.fields.opts,
|
||||
}
|
||||
if err := a.parseStringSlice(tt.args.args); (err != nil) != tt.wantErr {
|
||||
t.Errorf("arg.parseStringSlice() error = %v, wantErr %v", err, tt.wantErr)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func Test_arg_parseIntSlice(t *testing.T) {
|
||||
var i []int
|
||||
type fields struct {
|
||||
sname string
|
||||
lname string
|
||||
size int
|
||||
value interface{}
|
||||
unique bool
|
||||
parsed bool
|
||||
opts *Option
|
||||
}
|
||||
type args struct {
|
||||
args []string
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
wantErr bool
|
||||
}{
|
||||
{
|
||||
name: "test argument parseIntSlice",
|
||||
fields: fields{
|
||||
value: &i,
|
||||
size: 1,
|
||||
unique: false,
|
||||
},
|
||||
args: args{
|
||||
args: []string{"1", "2", "3"},
|
||||
},
|
||||
wantErr: false,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
a := &arg{
|
||||
sname: tt.fields.sname,
|
||||
lname: tt.fields.lname,
|
||||
size: tt.fields.size,
|
||||
value: tt.fields.value,
|
||||
unique: tt.fields.unique,
|
||||
parsed: tt.fields.parsed,
|
||||
opts: tt.fields.opts,
|
||||
}
|
||||
if err := a.parseIntSlice(tt.args.args); (err != nil) != tt.wantErr {
|
||||
t.Errorf("arg.parseIntSlice() error = %v, wantErr %v", err, tt.wantErr)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func Test_arg_parseFloatSlice(t *testing.T) {
|
||||
var f []float64
|
||||
type fields struct {
|
||||
sname string
|
||||
lname string
|
||||
size int
|
||||
value interface{}
|
||||
unique bool
|
||||
parsed bool
|
||||
opts *Option
|
||||
}
|
||||
type args struct {
|
||||
args []string
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
args args
|
||||
wantErr bool
|
||||
}{
|
||||
{
|
||||
name: "test argument parseFloatSlice",
|
||||
fields: fields{
|
||||
value: &f,
|
||||
size: 1,
|
||||
unique: false,
|
||||
},
|
||||
args: args{
|
||||
args: []string{"1.2", "2.3", "3.5"},
|
||||
},
|
||||
wantErr: false,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
a := &arg{
|
||||
sname: tt.fields.sname,
|
||||
lname: tt.fields.lname,
|
||||
size: tt.fields.size,
|
||||
value: tt.fields.value,
|
||||
unique: tt.fields.unique,
|
||||
parsed: tt.fields.parsed,
|
||||
opts: tt.fields.opts,
|
||||
}
|
||||
if err := a.parseFloatSlice(tt.args.args); (err != nil) != tt.wantErr {
|
||||
t.Errorf("arg.parseFloatSlice() error = %v, wantErr %v", err, tt.wantErr)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func Test_arg_getType(t *testing.T) {
|
||||
var s string
|
||||
var b bool
|
||||
var i int
|
||||
var f float64
|
||||
type fields struct {
|
||||
sname string
|
||||
lname string
|
||||
size int
|
||||
value interface{}
|
||||
unique bool
|
||||
parsed bool
|
||||
opts *Option
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
fields fields
|
||||
want string
|
||||
}{
|
||||
{
|
||||
name: "test get argument type 1",
|
||||
fields: fields{value: &s},
|
||||
want: "string",
|
||||
},
|
||||
{
|
||||
name: "test get argument type 2",
|
||||
fields: fields{value: &b},
|
||||
want: "bool",
|
||||
},
|
||||
{
|
||||
name: "test get argument type 3",
|
||||
fields: fields{value: &i},
|
||||
want: "int",
|
||||
},
|
||||
{
|
||||
name: "test get argument type 4",
|
||||
fields: fields{value: &f},
|
||||
want: "float",
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
a := &arg{
|
||||
sname: tt.fields.sname,
|
||||
lname: tt.fields.lname,
|
||||
size: tt.fields.size,
|
||||
value: tt.fields.value,
|
||||
unique: tt.fields.unique,
|
||||
parsed: tt.fields.parsed,
|
||||
opts: tt.fields.opts,
|
||||
}
|
||||
if got := a.getType(); got != tt.want {
|
||||
t.Errorf("arg.getType() = %v, want %v", got, tt.want)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
@ -2,6 +2,7 @@ package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log"
|
||||
|
||||
"git.trj.tw/golang/argparse"
|
||||
)
|
||||
@ -14,6 +15,9 @@ func main() {
|
||||
"--port", "3000",
|
||||
"--float", "1.23",
|
||||
"-n", "name!!",
|
||||
"-i", "item1",
|
||||
"-i", "item2",
|
||||
"-h",
|
||||
}
|
||||
|
||||
p := argparse.New()
|
||||
@ -23,15 +27,33 @@ func main() {
|
||||
var port int
|
||||
var floatVal float64
|
||||
var name *string
|
||||
var sarr []string
|
||||
var missReq int
|
||||
_ = missReq
|
||||
|
||||
p.BoolVar(&versionFlag, "v", "version")
|
||||
p.StringVar(&configPath, "f", "config")
|
||||
p.IntVar(&port, "p", "port")
|
||||
p.FloatVar(&floatVal, "ff", "float")
|
||||
p.BoolVar(&versionFlag, "v", "version", nil)
|
||||
p.StringVar(&configPath, "f", "config", nil)
|
||||
p.IntVar(&port, "p", "port", nil)
|
||||
p.FloatVar(&floatVal, "ff", "float", nil)
|
||||
p.StringSliceVar(&sarr, "i", "item", nil)
|
||||
// uncomment to test required arg missing
|
||||
// p.IntVar(&missReq, "m", "miss", &argparse.Option{Require: true})
|
||||
p.Help("h", "help")
|
||||
|
||||
name = p.String("n", "name")
|
||||
name = p.String("n", "name", nil)
|
||||
|
||||
p.Parse(opts)
|
||||
err := p.Parse(opts)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
fmt.Printf("Config: %s\nVersionFlag: %v\nPort: %d\nFloatVal: %f\nName: %s\n", configPath, versionFlag, port, floatVal, *name)
|
||||
fmt.Printf(
|
||||
"Config: %s\nVersionFlag: %v\nPort: %d\nFloatVal: %f\nName: %s\nItems: %v\n",
|
||||
configPath,
|
||||
versionFlag,
|
||||
port,
|
||||
floatVal,
|
||||
*name,
|
||||
sarr,
|
||||
)
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user