mirror of
https://github.com/gohugoio/hugo.git
synced 2024-11-07 20:30:36 -05:00
tpl: Refactor time.AsTime location implementation
This commit is contained in:
parent
26eeb29147
commit
807db97af8
2 changed files with 51 additions and 55 deletions
|
@ -13,13 +13,13 @@ menu:
|
|||
keywords: [dates,time,location]
|
||||
signature: ["time INPUT [LOCATION]"]
|
||||
workson: []
|
||||
hugoversion:
|
||||
hugoversion: "v0.77.0"
|
||||
relatedfuncs: []
|
||||
deprecated: false
|
||||
aliases: []
|
||||
---
|
||||
|
||||
`time` converts a timestamp string with an optional timezone into a [`time.Time`](https://godoc.org/time#Time) structure so you can access its fields:
|
||||
`time` converts a timestamp string with an optional default location into a [`time.Time`](https://godoc.org/time#Time) structure so you can access its fields:
|
||||
|
||||
```
|
||||
{{ time "2016-05-28" }} → "2016-05-28T00:00:00Z"
|
||||
|
@ -27,9 +27,11 @@ aliases: []
|
|||
{{ mul 1000 (time "2016-05-28T10:30:00.00+10:00").Unix }} → 1464395400000, or Unix time in milliseconds
|
||||
```
|
||||
|
||||
## Using Timezone
|
||||
## Using Locations
|
||||
|
||||
The optional 2nd parameter [LOCATION] argument is a string that references a timezone that is associated with the specified time value. If the time value has an explicit timezone or offset specified, it will take precedence over an explicit [LOCATION].
|
||||
The optional `LOCATION` parameter is a string that sets a default location that is associated with the specified time value. If the time value has an explicit timezone or offset specified, it will take precedence over the `LOCATION` parameter.
|
||||
|
||||
The list of valid locations may be system dependent, but should include `UTC`, `Local`, or any location in the [IANA Time Zone database](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones).
|
||||
|
||||
```
|
||||
{{ time "2020-10-20" }} → 2020-10-20 00:00:00 +0000 UTC
|
||||
|
@ -37,8 +39,6 @@ The optional 2nd parameter [LOCATION] argument is a string that references a tim
|
|||
{{ time "2020-01-20" "America/Los_Angeles" }} → 2020-01-20 00:00:00 -0800 PST
|
||||
```
|
||||
|
||||
> **Note**: Timezone support via the [LOCATION] parameter is included with Hugo `0.77`.
|
||||
|
||||
## Example: Using `time` to get Month Index
|
||||
|
||||
The following example takes a UNIX timestamp---set as `utimestamp: "1489276800"` in a content's front matter---converts the timestamp (string) to an integer using the [`int` function][int], and then uses [`printf`][] to convert the `Month` property of `time` into an index.
|
||||
|
|
|
@ -21,49 +21,7 @@ import (
|
|||
"github.com/spf13/cast"
|
||||
)
|
||||
|
||||
// New returns a new instance of the time-namespaced template functions.
|
||||
func New() *Namespace {
|
||||
return &Namespace{}
|
||||
}
|
||||
|
||||
// Namespace provides template functions for the "time" namespace.
|
||||
type Namespace struct{}
|
||||
|
||||
// AsTime converts the textual representation of the datetime string into
|
||||
// a time.Time interface.
|
||||
func (ns *Namespace) AsTime(v interface{}, args ...interface{}) (interface{}, error) {
|
||||
t, err := cast.ToTimeE(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if len(args) == 0 {
|
||||
return t, nil
|
||||
}
|
||||
|
||||
// Otherwise, if a location is specified, attempt to parse the time using the location specified.
|
||||
// Note: In this case, we require the input variable to be a string for proper parsing.
|
||||
// Note: We can't convert an existing parsed time by using the `Time.In()` as this CONVERTS/MODIFIES
|
||||
// the resulting time.
|
||||
|
||||
switch givenType := v.(type) {
|
||||
case string:
|
||||
// Good, we only support strings
|
||||
break
|
||||
|
||||
default:
|
||||
return nil, fmt.Errorf("Creating a time instance with location requires a value of type String. Given type: %s", givenType)
|
||||
}
|
||||
|
||||
location, err := _time.LoadLocation(args[0].(string))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Note: Cast currently doesn't support time with non-default locations. For now, just inlining this.
|
||||
// Reference: https://github.com/spf13/cast/pull/80
|
||||
|
||||
fmts := []string{
|
||||
var timeFormats = []string{
|
||||
_time.RFC3339,
|
||||
"2006-01-02T15:04:05", // iso8601 without timezone
|
||||
_time.RFC1123Z,
|
||||
|
@ -88,16 +46,54 @@ func (ns *Namespace) AsTime(v interface{}, args ...interface{}) (interface{}, er
|
|||
_time.StampMilli,
|
||||
_time.StampMicro,
|
||||
_time.StampNano,
|
||||
}
|
||||
|
||||
// New returns a new instance of the time-namespaced template functions.
|
||||
func New() *Namespace {
|
||||
return &Namespace{}
|
||||
}
|
||||
|
||||
// Namespace provides template functions for the "time" namespace.
|
||||
type Namespace struct{}
|
||||
|
||||
// AsTime converts the textual representation of the datetime string into
|
||||
// a time.Time interface.
|
||||
func (ns *Namespace) AsTime(v interface{}, args ...interface{}) (interface{}, error) {
|
||||
if len(args) == 0 {
|
||||
t, err := cast.ToTimeE(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
for _, dateType := range fmts {
|
||||
t, err := _time.ParseInLocation(dateType, v.(string), location)
|
||||
if err == nil {
|
||||
return t, nil
|
||||
}
|
||||
|
||||
timeStr, err := cast.ToStringE(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
locStr, err := cast.ToStringE(args[0])
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
loc, err := _time.LoadLocation(locStr)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Note: Cast currently doesn't support time with non-default locations. For now, just inlining this.
|
||||
// Reference: https://github.com/spf13/cast/pull/80
|
||||
|
||||
for _, dateType := range timeFormats {
|
||||
t, err2 := _time.ParseInLocation(dateType, timeStr, loc)
|
||||
if err2 == nil {
|
||||
return t, nil
|
||||
}
|
||||
}
|
||||
|
||||
return nil, fmt.Errorf("Unable to ParseInLocation using date \"%s\" with timezone \"%s\"", v, location)
|
||||
return nil, fmt.Errorf("Unable to ParseInLocation using date %q with timezone %q", v, loc)
|
||||
}
|
||||
|
||||
// Format converts the textual representation of the datetime string into
|
||||
|
|
Loading…
Reference in a new issue