commands: Make the --poll flag a duration

So you can do:

```
hugo server --poll 700ms
```

See #8720
This commit is contained in:
Bjørn Erik Pedersen 2021-07-05 10:13:41 +02:00
parent 43a23239b2
commit e31b1d1946
No known key found for this signature in database
GPG key ID: 330E6E2BD4859D8F
9 changed files with 56 additions and 18 deletions

View file

@ -204,7 +204,7 @@ type hugoBuilderCommon struct {
environment string environment string
buildWatch bool buildWatch bool
poll bool poll string
gc bool gc bool
@ -292,7 +292,7 @@ func (cc *hugoBuilderCommon) handleFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&cc.baseURL, "baseURL", "b", "", "hostname (and path) to the root, e.g. http://spf13.com/") cmd.Flags().StringVarP(&cc.baseURL, "baseURL", "b", "", "hostname (and path) to the root, e.g. http://spf13.com/")
cmd.Flags().Bool("enableGitInfo", false, "add Git revision, date and author info to the pages") cmd.Flags().Bool("enableGitInfo", false, "add Git revision, date and author info to the pages")
cmd.Flags().BoolVar(&cc.gc, "gc", false, "enable to run some cleanup tasks (remove unused cache files) after the build") cmd.Flags().BoolVar(&cc.gc, "gc", false, "enable to run some cleanup tasks (remove unused cache files) after the build")
cmd.Flags().BoolVar(&cc.poll, "poll", false, "use a poll based approach to watch for file system changes") cmd.Flags().StringVar(&cc.poll, "poll", "", "set this to a poll interval, e.g --poll 700ms, to use a poll based approach to watch for file system changes")
cmd.Flags().Bool("templateMetrics", false, "display metrics about template executions") cmd.Flags().Bool("templateMetrics", false, "display metrics about template executions")
cmd.Flags().Bool("templateMetricsHints", false, "calculate some improvement hints when combined with --templateMetrics") cmd.Flags().Bool("templateMetricsHints", false, "calculate some improvement hints when combined with --templateMetrics")

View file

@ -30,6 +30,8 @@ import (
"syscall" "syscall"
"time" "time"
"github.com/gohugoio/hugo/common/types"
"github.com/gohugoio/hugo/hugofs" "github.com/gohugoio/hugo/hugofs"
"github.com/gohugoio/hugo/resources/page" "github.com/gohugoio/hugo/resources/page"
@ -820,7 +822,7 @@ func (c *commandeer) fullRebuild(changeType string) {
} }
// newWatcher creates a new watcher to watch filesystem events. // newWatcher creates a new watcher to watch filesystem events.
func (c *commandeer) newWatcher(poll bool, dirList ...string) (*watcher.Batcher, error) { func (c *commandeer) newWatcher(pollIntervalStr string, dirList ...string) (*watcher.Batcher, error) {
if runtime.GOOS == "darwin" { if runtime.GOOS == "darwin" {
tweakLimit() tweakLimit()
} }
@ -830,10 +832,17 @@ func (c *commandeer) newWatcher(poll bool, dirList ...string) (*watcher.Batcher,
return nil, err return nil, err
} }
// The second interval is used by the poll based watcher. var pollInterval time.Duration
// Setting a shorter interval would make it snappier, poll := pollIntervalStr != ""
// but it would consume more CPU. if poll {
watcher, err := watcher.New(500*time.Millisecond, 700*time.Millisecond, poll) pollInterval, err = types.ToDurationE(pollIntervalStr)
if err != nil {
return nil, fmt.Errorf("invalid value for flag poll: %s", err)
}
c.logger.Printf("Use watcher with poll interval %v", pollInterval)
}
watcher, err := watcher.New(500*time.Millisecond, pollInterval, poll)
if err != nil { if err != nil {
return nil, err return nil, err
} }

View file

@ -18,10 +18,30 @@ import (
"fmt" "fmt"
"html/template" "html/template"
"reflect" "reflect"
"time"
"github.com/spf13/cast" "github.com/spf13/cast"
) )
// ToDuration converts v to time.Duration.
// See ToDurationE if you need to handle errors.
func ToDuration(v interface{}) time.Duration {
d, _ := ToDurationE(v)
return d
}
// ToDurationE converts v to time.Duration.
func ToDurationE(v interface{}) (time.Duration, error) {
if n := cast.ToInt(v); n > 0 {
return time.Duration(n) * time.Millisecond, nil
}
d, err := time.ParseDuration(cast.ToString(v))
if err != nil {
return 0, fmt.Errorf("cannot convert %v to time.Duration", v)
}
return d, nil
}
// ToStringSlicePreserveString is the same as ToStringSlicePreserveStringE, // ToStringSlicePreserveString is the same as ToStringSlicePreserveStringE,
// but it never fails. // but it never fails.
func ToStringSlicePreserveString(v interface{}) []string { func ToStringSlicePreserveString(v interface{}) []string {

View file

@ -16,6 +16,7 @@ package types
import ( import (
"encoding/json" "encoding/json"
"testing" "testing"
"time"
qt "github.com/frankban/quicktest" qt "github.com/frankban/quicktest"
) )
@ -36,3 +37,13 @@ func TestToString(t *testing.T) {
c.Assert(ToString([]byte("Hugo")), qt.Equals, "Hugo") c.Assert(ToString([]byte("Hugo")), qt.Equals, "Hugo")
c.Assert(ToString(json.RawMessage("Hugo")), qt.Equals, "Hugo") c.Assert(ToString(json.RawMessage("Hugo")), qt.Equals, "Hugo")
} }
func TestToDuration(t *testing.T) {
c := qt.New(t)
c.Assert(ToDuration("200ms"), qt.Equals, 200*time.Millisecond)
c.Assert(ToDuration("200"), qt.Equals, 200*time.Millisecond)
c.Assert(ToDuration("4m"), qt.Equals, 4*time.Minute)
c.Assert(ToDuration("asdfadf"), qt.Equals, time.Duration(0))
}

View file

@ -51,7 +51,7 @@ hugo [flags]
--noChmod don't sync permission mode of files --noChmod don't sync permission mode of files
--noTimes don't sync modification time of files --noTimes don't sync modification time of files
--path-warnings print warnings on duplicate target paths etc. --path-warnings print warnings on duplicate target paths etc.
--poll use a poll based approach to watch for file system changes --poll string set this to a poll interval, e.g --poll 700ms, to use a poll based approach to watch for file system changes
--print-mem print memory usage to screen at intervals --print-mem print memory usage to screen at intervals
--quiet build in quiet mode --quiet build in quiet mode
--renderToMemory render to memory (only useful for benchmark testing) --renderToMemory render to memory (only useful for benchmark testing)

View file

@ -46,7 +46,7 @@ See https://gohugo.io/hugo-modules/ for more information.
--noChmod don't sync permission mode of files --noChmod don't sync permission mode of files
--noTimes don't sync modification time of files --noTimes don't sync modification time of files
--path-warnings print warnings on duplicate target paths etc. --path-warnings print warnings on duplicate target paths etc.
--poll use a poll based approach to watch for file system changes --poll string set this to a poll interval, e.g --poll 700ms, to use a poll based approach to watch for file system changes
--print-mem print memory usage to screen at intervals --print-mem print memory usage to screen at intervals
--templateMetrics display metrics about template executions --templateMetrics display metrics about template executions
--templateMetricsHints calculate some improvement hints when combined with --templateMetrics --templateMetricsHints calculate some improvement hints when combined with --templateMetrics

View file

@ -47,7 +47,7 @@ hugo new [path] [flags]
--noChmod don't sync permission mode of files --noChmod don't sync permission mode of files
--noTimes don't sync modification time of files --noTimes don't sync modification time of files
--path-warnings print warnings on duplicate target paths etc. --path-warnings print warnings on duplicate target paths etc.
--poll use a poll based approach to watch for file system changes --poll string set this to a poll interval, e.g --poll 700ms, to use a poll based approach to watch for file system changes
--print-mem print memory usage to screen at intervals --print-mem print memory usage to screen at intervals
--templateMetrics display metrics about template executions --templateMetrics display metrics about template executions
--templateMetricsHints calculate some improvement hints when combined with --templateMetrics --templateMetricsHints calculate some improvement hints when combined with --templateMetrics

View file

@ -59,7 +59,7 @@ hugo server [flags]
--noHTTPCache prevent HTTP caching --noHTTPCache prevent HTTP caching
--noTimes don't sync modification time of files --noTimes don't sync modification time of files
--path-warnings print warnings on duplicate target paths etc. --path-warnings print warnings on duplicate target paths etc.
--poll use a poll based approach to watch for file system changes --poll string set this to a poll interval, e.g --poll 700ms, to use a poll based approach to watch for file system changes
-p, --port int port on which the server will listen (default 1313) -p, --port int port on which the server will listen (default 1313)
--print-mem print memory usage to screen at intervals --print-mem print memory usage to screen at intervals
--renderToDisk render to Destination path (default is render to memory & serve from there) --renderToDisk render to Destination path (default is render to memory & serve from there)

View file

@ -29,6 +29,8 @@ import (
"strings" "strings"
"time" "time"
"github.com/gohugoio/hugo/common/types"
"github.com/gohugoio/hugo/common/paths" "github.com/gohugoio/hugo/common/paths"
"github.com/gohugoio/hugo/common/constants" "github.com/gohugoio/hugo/common/constants"
@ -523,15 +525,11 @@ But this also means that your site configuration may not do what you expect. If
timeout := 30 * time.Second timeout := 30 * time.Second
if cfg.Language.IsSet("timeout") { if cfg.Language.IsSet("timeout") {
v := cfg.Language.Get("timeout") v := cfg.Language.Get("timeout")
if n := cast.ToInt(v); n > 0 { d, err := types.ToDurationE(v)
timeout = time.Duration(n) * time.Millisecond
} else {
d, err := time.ParseDuration(cast.ToString(v))
if err == nil { if err == nil {
timeout = d timeout = d
} }
} }
}
siteConfig := siteConfigHolder{ siteConfig := siteConfigHolder{
sitemap: config.DecodeSitemap(config.Sitemap{Priority: -1, Filename: "sitemap.xml"}, cfg.Language.GetStringMap("sitemap")), sitemap: config.DecodeSitemap(config.Sitemap{Priority: -1, Filename: "sitemap.xml"}, cfg.Language.GetStringMap("sitemap")),