opts

package
v0.0.0-...-4bc4959 Latest Latest
Warning

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

Go to latest
Published: Jun 30, 2016 License: MIT, MIT Imports: 18 Imported by: 0

README

opts

A low friction command-line interface library for Go (Golang)

GoDoc CircleCI

Command-line parsing should be easy. Use configuration structs:

package main

import (
	"fmt"

	"github.com/jpillora/opts"
)

func main() {
	config := struct {
		File  string `help:"file to load"`
		Lines int    `help:"number of lines to show"`
	}{}
	opts.Parse(&config)
	fmt.Println(config)
}
$ go run main.go -f foo -l 12
{foo 12}
Features (with examples)
  • Easy to use (simple)
  • Promotes separation of CLI code and library code (separation)
  • Automatically generated --help text via struct tags help:"Foo bar" (help)
  • Commands by nesting structs (cmds)
  • Default values by modifying the struct prior to Parse() (defaults)
  • Default values from a JSON config file, unmarshalled via your config struct (config)
  • Default values from environment, defined by your field names (env)
  • Infers program name from package name (and optional repository link)
  • Extensible via flag.Value (customtypes)
  • Customizable help text by modifying the default templates (customhelp)
Overview

Internally, opts creates flag.FlagSets from your configuration structs using pkg/reflect. So, given the following program:

type Config struct {
	Alpha   string        `help:"a string"`
	Bravo   int           `help:"an int"`
	Charlie bool          `help:"a bool"`
	Delta   time.Duration `help:"a duration"`
}

c := Config{
	Bravo: 42,
	Delta: 2 * time.Minute,
}
opts.Parse(&c)

At this point, opts.Parse will approximately perform:

foo := Config{}
set := flag.NewFlagSet("Config")
set.StringVar(&foo.Alpha, "", "a string")
set.IntVar(&foo.Bravo, 42, "an int")
set.BoolVar(&foo.Charlie, false, "a bool")
set.DurationVar(&foo.Delta, 2 * time.Minute, "a duration")
set.Parse(os.Args)

And, you get pretty --help output:

$ ./foo --help

  Usage: foo [options]

  Options:
  --alpha, -a    a string
  --bravo, -b    an int (default 42)
  --charlie, -c  an bool
  --delta, -d    a duration (default 2m0s)
  --help, -h

All Examples

See all examples here

Package API

See GoDoc

Struct Tag API

opts tries to set sane defaults so, for the most part, you'll get the desired behaviour by simply providing a configuration struct. These defaults can be overridden using the struct tag key:"value"s outlined below.

Common tags

These tags are usable across all types:

  • name - Name is used to display the field in the help text (defaults to the field name converted to lowercase and dashes)
  • help - Help is used to describe the field (defaults to "")
  • type - The opts type assigned the field (defaults using the table below)
type defaults

All fields will have a opts type. By default a struct field will be assigned a type depending on its field type:

Field Type Default type Valid types
int opt opt, arg
string opt opt, arg, cmdname
bool opt opt, arg
flag.Value opt opt, arg
time.Duration opt opt, arg
[]string arglist arglist
struct cmd cmd, embedded

This default assignment can be overridden with a type struct tag. For example you could set a string struct field to be an arg field with type:"arg".

type specific properties
  • opt

    An option (opt) field will appear in the options list and by definition, be optional.

    • short - An alias or shortcut to this option (defaults to the first letter of the name property)
    • env - An environment variable to use to retrieve the default (when UseEnv() is set this defaults to name property converted to uppercase and underscores)

    Restricted to fields with type int,string,bool,time.Duration and flag.Value

  • arg

    An argument (arg) field will appear in the usage and will be required if it does not have a default value set.

    Restricted to fields with type string

  • arglist

    An argument list (arglist) field will appear in the usage. Useful for a you allow any number number of arguments. For example file and directory targets.

    • min - An integer representing the minimum number of args specified

    Restricted to fields with type []string

  • cmd

    A command is nested opts.Opt instance, so its fields behave in exactly the same way as the parent struct.

    You can access the options of a command with prog --prog-opt X cmd --cmd-opt Y

    Restricted to fields with type struct

  • cmdname

    A special type which will assume the name of the selected command

    Restricted to fields with type string

  • embedded

    A special type which causes the fields of struct to be used in the current struct. Useful if you want to extend existing structs with extra command-line options.

Other projects

Other CLI libraries which infer flags from struct tags:

Why

Why yet another struct-based command-line library? I started this project back in April when the only thing around was jessevdk/go-flags and I wanted more customization. Now there is tj/go-config and alexflint/go-arg and still, these don't yet include nested structs and customizable help text.

Todo
  • More tests
  • Option groups (Separate sets of options in --help)
  • Bash completion
  • Multiple short options -aux (Requires a non-pkg/flag parser)
MIT License

Copyright © 2015 <dev@jpillora.com>

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the 'Software'), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

Documentation

Index

Constants

This section is empty.

Variables

View Source
var DefaultOrder = []string{
	"usage",
	"args",
	"arglist",
	"options",
	"cmds",
	"author",
	"version",
	"repo",
	"errmsg",
}
View Source
var DefaultTemplates = map[string]string{

	"help": `{{ $root := . }}` +
		`{{range $t := .Order}}{{ templ $t $root }}{{end}}`,

	"usage": `Usage: {{.Name }}` +
		`{{template "usageoptions" .}}` +
		`{{template "usageargs" .}}` +
		`{{template "usagearglist" .}}` +
		`{{template "usagecmd" .}}` + "\n",
	"usageoptions": `{{if .Opts}} [options]{{end}}`,
	"usageargs":    `{{range .Args}} {{.Name}}{{end}}`,
	"usagearglist": `{{if .ArgList}} {{.ArgList.Name}}{{end}}`,
	"usagecmd":     `{{if .Cmds}} <command>{{end}}`,

	"helpextra": `{{if .Def}}default {{.Def}}{{end}}` +
		`{{if and .Def .Env}}, {{end}}` +
		`{{if .Env}}env {{.Env}}{{end}}`,

	"args":    `{{range .Args}}{{template "arg" .}}{{end}}`,
	"arg":     "{{if .Help}}\n{{.Help}}\n{{end}}",
	"arglist": "{{if .ArgList}}{{ if .ArgList.Help}}\n{{.ArgList.Help}}\n{{end}}{{end}}",

	"options": `{{if .Opts}}` + "\nOptions:\n" +
		`{{ range $opt := .Opts}}{{template "option" $opt}}{{end}}{{end}}`,
	"option": `{{.Name}}{{if .Help}}{{.Pad}}{{.Help}}{{end}}` + "\n",

	"cmds": "{{if .Cmds}}\nCommands:\n" +
		`{{ range $sub := .Cmds}}{{template "cmd" $sub}}{{end}}{{end}}`,
	"cmd": "• {{ .Name }}{{if .Help}} - {{ .Help }}{{end}}\n",

	"version": "{{if .Version}}\nVersion:\n{{.Pad}}{{.Version}}\n{{end}}",
	"repo":    "{{if .Repo}}\nRead more:\n{{.Pad}}{{.Repo}}\n{{end}}",
	"author":  "{{if .Author}}\nAuthor:\n{{.Pad}}{{.Author}}\n{{end}}",
	"errmsg":  "{{if .ErrMsg}}\nError:\n{{.Pad}}{{.ErrMsg}}\n{{end}}",
}

Functions

This section is empty.

Types

type Opts

type Opts struct {

	//LineWidth defines where new-lines
	//are inserted into the help text
	//(defaults to 42)
	LineWidth int
	//PadAll enables padding around the
	//help text (defaults to true)
	PadAll bool
	//PadWidth defines the amount padding
	//when rendering help text (defaults to 2)
	PadWidth int
	// contains filtered or unexported fields
}

Opts is the main class, it contains all parsing state for a single set of arguments

func New

func New(config interface{}) *Opts

New creates a new Opts instance

func Parse

func Parse(config interface{}) *Opts

Parse(&config) is shorthand for New(&config).Parse()

func (*Opts) Author

func (o *Opts) Author(author string) *Opts

Author sets the author of the program and renders the 'author' template in the help text

func (*Opts) ConfigPath

func (o *Opts) ConfigPath(path string) *Opts

ConfigPath defines a path to a JSON file which matches the structure of the provided config. Environment variables override JSON Config variables.

func (*Opts) DocAfter

func (o *Opts) DocAfter(target, newid, template string) *Opts

DocAfter inserts a text block after the specified template

func (*Opts) DocBefore

func (o *Opts) DocBefore(target, newid, template string) *Opts

DocBefore inserts a text block before the specified template

func (*Opts) DocSet

func (o *Opts) DocSet(id, template string) *Opts

DecSet replaces the specified template

func (*Opts) Help

func (o *Opts) Help() string

Help renders the help text as a string

func (*Opts) Name

func (o *Opts) Name(name string) *Opts

Name sets the name of the program

func (*Opts) Parse

func (o *Opts) Parse() *Opts

Parse with os.Args

func (*Opts) ParseArgs

func (o *Opts) ParseArgs(args []string) *Opts

ParseArgs with the provided arguments

func (*Opts) PkgAuthor

func (o *Opts) PkgAuthor() *Opts

PkgRepo infers the repository link of the program from the package import path of the struct (So note, this will not work for 'main' packages)

func (*Opts) PkgRepo

func (o *Opts) PkgRepo() *Opts

PkgRepo infers the repository link of the program from the package import path of the struct (So note, this will not work for 'main' packages)

func (*Opts) Process

func (o *Opts) Process(args []string) error

Process is the same as ParseArgs except it returns an error on failure

func (*Opts) Repo

func (o *Opts) Repo(repo string) *Opts

Repo sets the repository link of the program and renders the 'repo' template in the help text

func (*Opts) UseEnv

func (o *Opts) UseEnv() *Opts

UseEnv enables an implicit "env" struct tag option on all struct fields, the name of the field is converted into an environment variable with the transform `FooBar` -> `FOO_BAR`.

func (*Opts) Version

func (o *Opts) Version(version string) *Opts

Version sets the version of the program and renders the 'version' template in the help text

Directories

Path Synopsis
example
arg
env

Jump to

Keyboard shortcuts

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