urfave-cli/flag_timestamp.go

181 lines
3.9 KiB
Go
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package cli
import (
"flag"
"fmt"
"time"
)
// Timestamp wrap to satisfy golang's flag interface.
type Timestamp struct {
timestamp *time.Time
hasBeenSet bool
layout string
location *time.Location
}
// Timestamp constructor
func NewTimestamp(timestamp time.Time) *Timestamp {
return &Timestamp{timestamp: &timestamp}
}
// Set the timestamp value directly
func (t *Timestamp) SetTimestamp(value time.Time) {
if !t.hasBeenSet {
t.timestamp = &value
t.hasBeenSet = true
}
}
// Set the timestamp string layout for future parsing
func (t *Timestamp) SetLayout(layout string) {
t.layout = layout
}
// Set perceived timezone of the to-be parsed time string
func (t *Timestamp) SetLocation(loc *time.Location) {
t.location = loc
}
// Parses the string value to timestamp
func (t *Timestamp) Set(value string) error {
var timestamp time.Time
var err error
if t.location != nil {
timestamp, err = time.ParseInLocation(t.layout, value, t.location)
} else {
timestamp, err = time.Parse(t.layout, value)
}
if err != nil {
return err
}
t.timestamp = &timestamp
t.hasBeenSet = true
return nil
}
// String returns a readable representation of this value (for usage defaults)
func (t *Timestamp) String() string {
return fmt.Sprintf("%#v", t.timestamp)
}
// Value returns the timestamp value stored in the flag
func (t *Timestamp) Value() *time.Time {
return t.timestamp
}
// Get returns the flag structure
func (t *Timestamp) Get() interface{} {
return *t
}
// clone timestamp
func (t *Timestamp) clone() *Timestamp {
tc := &Timestamp{
timestamp: nil,
hasBeenSet: t.hasBeenSet,
layout: t.layout,
location: nil,
}
if t.timestamp != nil {
tts := *t.timestamp
tc.timestamp = &tts
}
if t.location != nil {
loc := *t.location
tc.location = &loc
}
return tc
}
// GetValue returns the flags value as string representation and an empty
// string if the flag takes no value at all.
func (f *TimestampFlag) GetValue() string {
if f.Value != nil && f.Value.timestamp != nil {
return f.Value.timestamp.String()
}
return ""
}
// GetDefaultText returns the default text for this flag
func (f *TimestampFlag) GetDefaultText() string {
if f.DefaultText != "" {
return f.DefaultText
}
if f.defaultValue != nil && f.defaultValue.timestamp != nil {
return f.defaultValue.timestamp.String()
}
return ""
}
// Apply populates the flag given the flag set and environment
func (f *TimestampFlag) Apply(set *flag.FlagSet) error {
if f.Layout == "" {
return fmt.Errorf("timestamp Layout is required")
}
if f.Value == nil {
f.Value = &Timestamp{}
}
f.Value.SetLayout(f.Layout)
f.Value.SetLocation(f.Timezone)
f.defaultValue = f.Value.clone()
if f.Destination != nil {
f.Destination.SetLayout(f.Layout)
f.Destination.SetLocation(f.Timezone)
}
if val, source, found := flagFromEnvOrFile(f.EnvVars, f.FilePath); found {
if err := f.Value.Set(val); err != nil {
return fmt.Errorf("could not parse %q as timestamp value from %s for flag %s: %s", val, source, f.Name, err)
}
f.HasBeenSet = true
}
for _, name := range f.Names() {
if f.Destination != nil {
set.Var(f.Destination, name, f.Usage)
continue
}
set.Var(f.Value, name, f.Usage)
}
return nil
}
// Get returns the flags value in the given Context.
func (f *TimestampFlag) Get(ctx *Context) *time.Time {
return ctx.Timestamp(f.Name)
}
// RunAction executes flag action if set
func (f *TimestampFlag) RunAction(c *Context) error {
if f.Action != nil {
return f.Action(c, c.Timestamp(f.Name))
}
return nil
}
// Timestamp gets the timestamp from a flag name
func (cCtx *Context) Timestamp(name string) *time.Time {
if fs := cCtx.lookupFlagSet(name); fs != nil {
return lookupTimestamp(name, fs)
}
return nil
}
// Fetches the timestamp value from the local timestampWrap
func lookupTimestamp(name string, set *flag.FlagSet) *time.Time {
f := set.Lookup(name)
if f != nil {
return (f.Value.(*Timestamp)).Value()
}
return nil
}