largo

package module
v0.0.0-...-29754d2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 18, 2021 License: MIT Imports: 11 Imported by: 3

README

largo - Yet another arg parser of Go in a flexible way

Go codecov Go Report Card Maintainability Go Reference

Motivation

# Let's say your are building `greet`, and can receive any command arg as message.
% greet hello
hello
% greet thanks
thanks

What if greet can accept some flags, but would receive unordered way like below.

# 1) BSD style
% greet -count 3 -upper hello
# 2) GNU style
% greet hello -count 3 -upper
# 3) Mixed...
% greet -count 3 hello -upper

# All output should be
HELLO HELLO HELLO

The problem is that the standard flag package ignores all flags of case (2) and -upper flag of case (3). How can we keep flexibility to parse those flags, even if they are NOT urdered in BSD-style?

Idea

Basically flag.FlagSet works fine, however, we like to keep parsing all given flags until the end of line, and retrieve all remaining args as Rest().

greet -count 3 hello -upper
-----
 cmd
      --------       ------
      int flag      bool flag
               -----
               rest

Usage

import (
  "github.com/otiai10/largo"
)

var (
  count int
  upper bool
)

func main() {
  fset := largo.NewFlaggSet("greet")
  fset.IntVar(&count, "count", 1, "Number of count to say it").Alias("c")
  fset.BoolVar(&upper, "upper", false, "Say it in upper cases").Alias("u")

  // In most cases, it is given as os.Args[1:] or something.
  fset.Parse([]string{"greet", "-c", "3", "hello", "-upper"})

  fmt.Println("count:", count)   // count: 3
  fmt.Println("upper:", upper)   // upper: true
  fmt.Println("rest:", f.Rest()) // rest: [hello]
}

Reference projects using largo

Issues & Feedbacks

Any feedbacks will be welcomed!

Documentation

Overview

Package largo implements command-line-like string/[]string parsing. Unlike standard `flag` package, largo allows to provide flag args in **unordered** way, such as:

dosomething -upper -count 3 say hello
dosomething -upper say -count=3 hello
dosomething say -upper hello -count 3

All should be parsed and resulted to the same args, such as:

Command:	dosomething
Rest args:	[say, hello]
Flags:
	upper:	true
	count:	3

`largo` parses given string/[]string as follows:

dosomething say -count 3 hello -upper
-----------
  command
   	            -------        ------
                 flag           flag
            ----       --------
            rest         rest

// TODO: Add more information here in near future ;)

Index

Examples

Constants

This section is empty.

Variables

View Source
var ErrHelp = errors.New("flag: help requested")

Functions

func Tokenize

func Tokenize(s string) (tokens []string)

Parse ...

func TokenizeBytes

func TokenizeBytes(b []byte) (tokens []string)

Types

type ErrorHandling

type ErrorHandling int
const (
	ContinueOnError ErrorHandling = iota // Return a descriptive error.
	ExitOnError                          // Call os.Exit(2) or for -h/-help Exit(0).
	PanicOnError                         // Call panic with a descriptive error.
)

https://cs.opensource.google/go/go/+/refs/tags/go1.16.6:src/flag/flag.go;l=314-318;drc=refs%2Ftags%2Fgo1.16.6

type Flag

type Flag struct {
	Name  string
	Value Value
	Usage string
	// contains filtered or unexported fields
}

func (*Flag) Alias

func (f *Flag) Alias(aliases ...string) *Flag

Alias defines aliases for the flag.

Example
var verbose bool
fset := NewFlagSet("foo", ContinueOnError)
fset.BoolVar(&verbose, "verbose", false, "Show verbose log").Alias("V")
fset.Parse([]string{"baa", "-V", "baz"})
fmt.Println("verbose?", verbose)
Output:

verbose? true

func (*Flag) Aliases

func (f *Flag) Aliases() []string

func (*Flag) Given

func (f *Flag) Given() bool

type FlagSet

type FlagSet struct {
	Name string

	// Usage ...
	// FIXME: Write something here
	Usage       func()
	Output      io.Writer
	Description string
	// contains filtered or unexported fields
}

func NewFlagSet

func NewFlagSet(name string, errorHandling ErrorHandling) *FlagSet

func (*FlagSet) BoolVar

func (fset *FlagSet) BoolVar(dest *bool, name string, defaultval bool, usage string) *Flag

func (*FlagSet) HelpMessage

func (fset *FlagSet) HelpMessage() string

func (*FlagSet) HelpRequested

func (fset *FlagSet) HelpRequested() bool

func (*FlagSet) IntVar

func (fset *FlagSet) IntVar(dest *int, name string, defaultval int, usage string) *Flag

func (*FlagSet) List

func (fset *FlagSet) List() []*Flag

func (*FlagSet) Lookup

func (fset *FlagSet) Lookup(name string) *Flag

func (*FlagSet) Parse

func (fset *FlagSet) Parse(arguments []string) error

func (*FlagSet) ParseLine

func (fset *FlagSet) ParseLine(line string) error

func (*FlagSet) PrintDefaultUsage

func (fset *FlagSet) PrintDefaultUsage(w io.Writer) error

func (*FlagSet) Rest

func (fset *FlagSet) Rest() []string
Example
var upper bool
var count int
fset := NewFlagSet("say", ContinueOnError)
fset.BoolVar(&upper, "upper", false, "Make chars uppercase").Alias("U")
fset.IntVar(&count, "count", 1, "Count to say that word").Alias("c")

// In most cases, it comes from `os.Args`.
args := []string{"say", "-count", "3", "hello", "-upper", "hiromu"}

fset.Parse(args)
fmt.Printf("upper: %v\ncount: %v\nrest: %v\n", upper, count, fset.Rest())
Output:

upper: true
count: 3
rest: [hello hiromu]

func (*FlagSet) StringVar

func (fset *FlagSet) StringVar(dest *string, name string, defaultval string, usage string) *Flag

func (*FlagSet) Var

func (fset *FlagSet) Var(value Value, name string, usage string) *Flag

type Value

type Value interface {
	Set(s string) error
	Get() interface{}
	Type() string
}

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL