github.com/thanos-io/thanos@v0.32.5/pkg/model/timeduration.go (about) 1 // Copyright (c) The Thanos Authors. 2 // Licensed under the Apache License 2.0. 3 4 package model 5 6 import ( 7 "time" 8 9 "github.com/prometheus/common/model" 10 "github.com/prometheus/prometheus/model/timestamp" 11 "gopkg.in/alecthomas/kingpin.v2" 12 ) 13 14 // TimeOrDurationValue is a custom kingping parser for time in RFC3339 15 // or duration in Go's duration format, such as "300ms", "-1.5h" or "2h45m". 16 // Only one will be set. 17 type TimeOrDurationValue struct { 18 Time *time.Time 19 Dur *model.Duration 20 } 21 22 // Set converts string to TimeOrDurationValue. 23 func (tdv *TimeOrDurationValue) Set(s string) error { 24 t, err := time.Parse(time.RFC3339, s) 25 if err == nil { 26 tdv.Time = &t 27 return nil 28 } 29 30 // error parsing time, let's try duration. 31 var minus bool 32 if s[0] == '-' { 33 minus = true 34 s = s[1:] 35 } 36 dur, err := model.ParseDuration(s) 37 if err != nil { 38 return err 39 } 40 41 if minus { 42 dur = dur * -1 43 } 44 tdv.Dur = &dur 45 return nil 46 } 47 48 // String returns either time or duration. 49 func (tdv *TimeOrDurationValue) String() string { 50 switch { 51 case tdv.Time != nil: 52 return tdv.Time.String() 53 case tdv.Dur != nil: 54 if v := *tdv.Dur; v < 0 { 55 return "-" + (-v).String() 56 } 57 return tdv.Dur.String() 58 } 59 60 return "nil" 61 } 62 63 // PrometheusTimestamp returns TimeOrDurationValue converted to PrometheusTimestamp 64 // if duration is set now+duration is converted to Timestamp. 65 func (tdv *TimeOrDurationValue) PrometheusTimestamp() int64 { 66 switch { 67 case tdv.Time != nil: 68 return timestamp.FromTime(*tdv.Time) 69 case tdv.Dur != nil: 70 return timestamp.FromTime(time.Now().Add(time.Duration(*tdv.Dur))) 71 } 72 73 return 0 74 } 75 76 // TimeOrDuration helper for parsing TimeOrDuration with kingpin. 77 func TimeOrDuration(flags *kingpin.FlagClause) *TimeOrDurationValue { 78 value := new(TimeOrDurationValue) 79 flags.SetValue(value) 80 return value 81 }