diff options
42 files changed, 410 insertions, 320 deletions
diff --git a/commands/benchmark.go b/commands/benchmark.go index 88954ffd9..a879e8941 100644 --- a/commands/benchmark.go +++ b/commands/benchmark.go @@ -48,8 +48,8 @@ func init() { } func benchmark(cmd *cobra.Command, args []string) error { - var err error - if err = InitializeConfig(benchmarkCmd); err != nil { + cfg, err := InitializeConfig(benchmarkCmd) + if err != nil { return err } @@ -79,7 +79,7 @@ func benchmark(cmd *cobra.Command, args []string) error { t := time.Now() for i := 0; i < benchmarkTimes; i++ { - if err = resetAndBuildSites(false); err != nil { + if err = resetAndBuildSites(cfg, false); err != nil { return err } } diff --git a/commands/convert.go b/commands/convert.go index 6e5b5be85..79c3c75e8 100644 --- a/commands/convert.go +++ b/commands/convert.go @@ -80,13 +80,13 @@ func init() { convertCmd.PersistentFlags().SetAnnotation("source", cobra.BashCompSubdirsInDir, []string{}) } -func convertContents(mark rune) (err error) { - if err := InitializeConfig(); err != nil { +func convertContents(mark rune) error { + cfg, err := InitializeConfig() + if err != nil { return err } - h, err := hugolib.NewHugoSitesFromConfiguration() - + h, err := hugolib.NewHugoSitesFromConfiguration(cfg) if err != nil { return err } @@ -108,7 +108,7 @@ func convertContents(mark rune) (err error) { jww.FEEDBACK.Println("processing", len(site.Source.Files()), "content files") for _, file := range site.Source.Files() { jww.INFO.Println("Attempting to convert", file.LogicalName()) - page, err := hugolib.NewPage(file.LogicalName()) + page, err := site.NewPage(file.LogicalName()) if err != nil { return err } @@ -157,5 +157,5 @@ func convertContents(mark rune) (err error) { } } } - return + return nil } diff --git a/commands/hugo.go b/commands/hugo.go index 9347a5081..f4204cad1 100644 --- a/commands/hugo.go +++ b/commands/hugo.go @@ -18,6 +18,7 @@ package commands import ( "fmt" "io/ioutil" + "log" "net/http" "os" "path/filepath" @@ -113,16 +114,17 @@ built with love by spf13 and friends in Go. Complete documentation is available at http://gohugo.io/.`, RunE: func(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + cfg, err := InitializeConfig() + if err != nil { return err } if buildWatch { viper.Set("disableLiveReload", true) - watchConfig() + watchConfig(cfg) } - return build() + return build(cfg) }, } @@ -266,9 +268,12 @@ func init() { } // InitializeConfig initializes a config file with sensible default configuration flags. -func InitializeConfig(subCmdVs ...*cobra.Command) error { +func InitializeConfig(subCmdVs ...*cobra.Command) (hugolib.DepsCfg, error) { + + var cfg hugolib.DepsCfg + if err := hugolib.LoadGlobalConfig(source, cfgFile); err != nil { - return err + return cfg, err } for _, cmdV := range append([]*cobra.Command{hugoCmdV}, subCmdVs...) { @@ -333,37 +338,6 @@ func InitializeConfig(subCmdVs ...*cobra.Command) error { viper.Set("cacheDir", helpers.GetTempDir("hugo_cache", hugofs.Source())) } - logFile := ioutil.Discard - - if verboseLog || logging || (viper.IsSet("logFile") && viper.GetString("logFile") != "") { - - var err error - if viper.IsSet("logFile") && viper.GetString("logFile") != "" { - path := viper.GetString("logFile") - logFile, err = os.OpenFile(path, os.O_RDWR|os.O_APPEND|os.O_CREATE, 0666) - if err != nil { - return newSystemError("Failed to open log file:", path, err) - } - } else { - logFile, err = ioutil.TempFile(os.TempDir(), "hugo") - if err != nil { - return newSystemError(err) - } - } - } - - jww.SetLogOutput(logFile) - - if quiet { - jww.SetStdoutThreshold(jww.LevelError) - } else if viper.GetBool("verbose") { - jww.SetStdoutThreshold(jww.LevelInfo) - } - - if verboseLog { - jww.SetLogThreshold(jww.LevelInfo) - } - jww.INFO.Println("Using config file:", viper.ConfigFileUsed()) // Init file systems. This may be changed at a later point. @@ -372,7 +346,7 @@ func InitializeConfig(subCmdVs ...*cobra.Command) error { themeDir := helpers.GetThemeDir() if themeDir != "" { if _, err := hugofs.Source().Stat(themeDir); os.IsNotExist(err) { - return newSystemError("Unable to find theme Directory:", themeDir) + return cfg, newSystemError("Unable to find theme Directory:", themeDir) } } @@ -383,8 +357,49 @@ func InitializeConfig(subCmdVs ...*cobra.Command) error { helpers.HugoReleaseVersion(), minVersion) } - return nil + logger, err := createLogger() + if err != nil { + return cfg, err + } + + cfg.Logger = logger + + return cfg, nil + +} + +func createLogger() (*jww.Notepad, error) { + var ( + logHandle = ioutil.Discard + outHandle = os.Stdout + stdoutThreshold = jww.LevelError + logThreshold = jww.LevelWarn + ) + + if verboseLog || logging || (viper.IsSet("logFile") && viper.GetString("logFile") != "") { + + var err error + if viper.IsSet("logFile") && viper.GetString("logFile") != "" { + path := viper.GetString("logFile") + logHandle, err = os.OpenFile(path, os.O_RDWR|os.O_APPEND|os.O_CREATE, 0666) + if err != nil { + return nil, newSystemError("Failed to open log file:", path, err) + } + } else { + logHandle, err = ioutil.TempFile(os.TempDir(), "hugo") + if err != nil { + return nil, newSystemError(err) + } + } + } else if !quiet && viper.GetBool("verbose") { + stdoutThreshold = jww.LevelInfo + } + + if verboseLog { + logThreshold = jww.LevelInfo + } + return jww.NewNotepad(stdoutThreshold, logThreshold, outHandle, logHandle, "", log.Ldate|log.Ltime), nil } func initializeFlags(cmd *cobra.Command) { @@ -432,12 +447,12 @@ func flagChanged(flags *flag.FlagSet, key string) bool { return flag.Changed } -func watchConfig() { +func watchConfig(cfg hugolib.DepsCfg) { viper.WatchConfig() viper.OnConfigChange(func(e fsnotify.Event) { jww.FEEDBACK.Println("Config file changed:", e.Name) // Force a full rebuild - utils.CheckErr(recreateAndBuildSites(true)) + utils.CheckErr(recreateAndBuildSites(cfg, true)) if !viper.GetBool("disableLiveReload") { // Will block forever trying to write to a channel that nobody is reading if livereload isn't initialized livereload.ForceRefresh() @@ -445,7 +460,7 @@ func watchConfig() { }) } -func build(watches ...bool) error { +func build(cfg hugolib.DepsCfg, watches ...bool) error { // Hugo writes the output to memory instead of the disk. // This is only used for benchmark testing. Cause the content is only visible // in memory. @@ -462,14 +477,14 @@ func build(watches ...bool) error { if len(watches) > 0 && watches[0] { watch = true } - if err := buildSites(buildWatch || watch); err != nil { + if err := buildSites(cfg, buildWatch || watch); err != nil { return fmt.Errorf("Error building site: %s", err) } if buildWatch { jww.FEEDBACK.Println("Watching for changes in", helpers.AbsPathify(viper.GetString("contentDir"))) jww.FEEDBACK.Println("Press Ctrl+C to stop") - utils.CheckErr(NewWatcher(0)) + utils.CheckErr(newWatcher(cfg, 0)) } return nil @@ -644,8 +659,8 @@ func getDirList() []string { return a } -func recreateAndBuildSites(watching bool) (err error) { - if err := initSites(); err != nil { +func recreateAndBuildSites(cfg hugolib.DepsCfg, watching bool) (err error) { + if err := initSites(cfg); err != nil { return err } if !quiet { @@ -654,8 +669,8 @@ func recreateAndBuildSites(watching bool) (err error) { return Hugo.Build(hugolib.BuildCfg{CreateSitesFromConfig: true, Watching: watching, PrintStats: !quiet}) } -func resetAndBuildSites(watching bool) (err error) { - if err := initSites(); err != nil { +func resetAndBuildSites(cfg hugolib.DepsCfg, watching bool) (err error) { + if err := initSites(cfg); err != nil { return err } if !quiet { @@ -664,12 +679,12 @@ func resetAndBuildSites(watching bool) (err error) { return Hugo.Build(hugolib.BuildCfg{ResetState: true, Watching: watching, PrintStats: !quiet}) } -func initSites() error { +func initSites(cfg hugolib.DepsCfg) error { if Hugo != nil { return nil } - h, err := hugolib.NewHugoSitesFromConfiguration() + h, err := hugolib.NewHugoSitesFromConfiguration(cfg) if err != nil { return err @@ -679,8 +694,8 @@ func initSites() error { return nil } -func buildSites(watching bool) (err error) { - if err := initSites(); err != nil { +func buildSites(cfg hugolib.DepsCfg, watching bool) (err error) { + if err := initSites(cfg); err != nil { return err } if !quiet { @@ -689,15 +704,15 @@ func buildSites(watching bool) (err error) { return Hugo.Build(hugolib.BuildCfg{Watching: watching, PrintStats: !quiet}) } -func rebuildSites(events []fsnotify.Event) error { - if err := initSites(); err != nil { +func rebuildSites(cfg hugolib.DepsCfg, events []fsnotify.Event) error { + if err := initSites(cfg); err != nil { return err } return Hugo.Build(hugolib.BuildCfg{PrintStats: !quiet, Watching: true}, events...) } -// NewWatcher creates a new watcher to watch filesystem events. -func NewWatcher(port int) error { +// newWatcher creates a new watcher to watch filesystem events. +func newWatcher(cfg hugolib.DepsCfg, port int) error { if runtime.GOOS == "darwin" { tweakLimit() } @@ -910,7 +925,7 @@ func NewWatcher(port int) error { const layout = "2006-01-02 15:04 -0700" jww.FEEDBACK.Println(time.Now().Format(layout)) - rebuildSites(dynamicEvents) + rebuildSites(cfg, dynamicEvents) if !buildWatch && !viper.GetBool("disableLiveReload") { // Will block forever trying to write to a channel that nobody is reading if livereload isn't initialized diff --git a/commands/import_jekyll.go b/commands/import_jekyll.go index 87bd285f1..7e55e0670 100644 --- a/commands/import_jekyll.go +++ b/commands/import_jekyll.go @@ -83,8 +83,9 @@ func importFromJekyll(cmd *cobra.Command, args []string) error { } forceImport, _ := cmd.Flags().GetBool("force") - if err := createSiteFromJekyll(jekyllRoot, targetDir, forceImport); err != nil { - return newUserError(err) + site, err := createSiteFromJekyll(jekyllRoot, targetDir, forceImport) + if err != nil { + return err } jww.FEEDBACK.Println("Importing...") @@ -118,7 +119,7 @@ func importFromJekyll(cmd *cobra.Command, args []string) error { } fileCount++ - return convertJekyllPost(path, relPath, targetDir, draft) + return convertJekyllPost(site, path, relPath, targetDir, draft) } err = helpers.SymbolicWalk(hugofs.Os(), jekyllRoot, callback) @@ -135,17 +136,17 @@ func importFromJekyll(cmd *cobra.Command, args []string) error { } // TODO: Consider calling doNewSite() instead? -func createSiteFromJekyll(jekyllRoot, targetDir string, force bool) error { +func createSiteFromJekyll(jekyllRoot, targetDir string, force bool) (*hugolib.Site, error) { fs := hugofs.Source() if exists, _ := helpers.Exists(targetDir, fs); exists { if isDir, _ := helpers.IsDir(targetDir, fs); !isDir { - return errors.New("Target path \"" + targetDir + "\" already exists but not a directory") + return nil, errors.New("Target path \"" + targetDir + "\" already exists but not a directory") } isEmpty, _ := helpers.IsEmpty(targetDir, fs) if !isEmpty && !force { - return errors.New("Target path \"" + targetDir + "\" already exists and is not empty") + return nil, errors.New("Target path \"" + targetDir + "\" already exists and is not empty") } } @@ -166,7 +167,7 @@ func createSiteFromJekyll(jekyllRoot, targetDir string, force bool) error { } } if !hasPostsOrDrafts { - return errors.New("Your Jekyll root contains neither posts nor drafts, aborting.") + return nil, errors.New("Your Jekyll root contains neither posts nor drafts, aborting.") } mkdir(targetDir, "layouts") @@ -179,8 +180,9 @@ func createSiteFromJekyll(jekyllRoot, targetDir string, force bool) error { createConfigFromJekyll(targetDir, "yaml", jekyllConfig) copyJekyllFilesAndFolders(jekyllRoot, filepath.Join(targetDir, "static")) + site := hugolib.NewSiteDefaultLang() - return nil + return site, nil } func loadJekyllConfig(jekyllRoot string) map[string]interface{} { @@ -379,7 +381,7 @@ func parseJekyllFilename(filename string) (time.Time, string, error) { return postDate, postName, nil } -func convertJekyllPost(path, relPath, targetDir string, draft bool) error { +func convertJekyllPost(s *hugolib.Site, path, relPath, targetDir string, draft bool) error { jww.TRACE.Println("Converting", path) filename := filepath.Base(path) @@ -422,7 +424,7 @@ func convertJekyllPost(path, relPath, targetDir string, draft bool) error { jww.TRACE.Println(newmetadata) content := convertJekyllContent(newmetadata, string(psr.Content())) - page, err := hugolib.NewPage(filename) + page, err := s.NewPage(filename) if err != nil { jww.ERROR.Println("New page error", filename) return err diff --git a/commands/list.go b/commands/list.go index 7a1fbd55c..870370f71 100644 --- a/commands/list.go +++ b/commands/list.go @@ -45,13 +45,14 @@ var listDraftsCmd = &cobra.Command{ Long: `List all of the drafts in your content directory.`, RunE: func(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + cfg, err := InitializeConfig() + if err != nil { return err } viper.Set("buildDrafts", true) - sites, err := hugolib.NewHugoSitesFromConfiguration() + sites, err := hugolib.NewHugoSitesFromConfiguration(cfg) if err != nil { return newSystemError("Error creating sites", err) @@ -80,13 +81,14 @@ var listFutureCmd = &cobra.Command{ posted in the future.`, RunE: func(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + cfg, err := InitializeConfig() + if err != nil { return err } viper.Set("buildFuture", true) - sites, err := hugolib.NewHugoSitesFromConfiguration() + sites, err := hugolib.NewHugoSitesFromConfiguration(cfg) if err != nil { return newSystemError("Error creating sites", err) @@ -115,13 +117,14 @@ var listExpiredCmd = &cobra.Command{ expired.`, RunE: func(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + cfg, err := InitializeConfig() + if err != nil { return err } viper.Set("buildExpired", true) - sites, err := hugolib.NewHugoSitesFromConfiguration() + sites, err := hugolib.NewHugoSitesFromConfiguration(cfg) if err != nil { return newSystemError("Error creating sites", err) diff --git a/commands/list_config.go b/commands/list_config.go index 69822f38c..c04cb66be 100644 --- a/commands/list_config.go +++ b/commands/list_config.go @@ -33,7 +33,7 @@ func init() { } func config(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(configCmd); err != nil { + if _, err := InitializeConfig(configCmd); err != nil { return err } diff --git a/commands/new.go b/commands/new.go index 05b5ff4dd..3a3ec2e61 100644 --- a/commands/new.go +++ b/commands/new.go @@ -84,7 +84,7 @@ as you see fit.`, // NewContent adds new content to a Hugo site. func NewContent(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + if _, err := InitializeConfig(); err != nil { return err } @@ -195,7 +195,7 @@ func NewSite(cmd *cobra.Command, args []string) error { // NewTheme creates a new Hugo theme. func NewTheme(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + if _, err := InitializeConfig(); err != nil { return err } diff --git a/commands/server.go b/commands/server.go index 2a7230b52..b35b58bf8 100644 --- a/commands/server.go +++ b/commands/server.go @@ -104,7 +104,8 @@ func init() { } func server(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(serverCmd); err != nil { + cfg, err := InitializeConfig() + if err != nil { return err } @@ -118,7 +119,7 @@ func server(cmd *cobra.Command, args []string) error { if viper.GetBool("watch") { serverWatch = true - watchConfig() + watchConfig(cfg) } l, err := net.Listen("tcp", net.JoinHostPort(serverInterface, strconv.Itoa(serverPort))) @@ -161,7 +162,7 @@ func server(cmd *cobra.Command, args []string) error { viper.Set("publishDir", "/") } - if err := build(serverWatch); err != nil { + if err := build(cfg, serverWatch); err != nil { return err } @@ -176,7 +177,7 @@ func server(cmd *cobra.Command, args []string) error { rootWatchDirs := strings.Join(helpers.UniqueStrings(helpers.ExtractRootPaths(watchDirs)), ",") jww.FEEDBACK.Printf("Watching for changes in %s%s{%s}\n", baseWatchDir, helpers.FilePathSeparator, rootWatchDirs) - err := NewWatcher(serverPort) + err := newWatcher(cfg, serverPort) if err != nil { return err diff --git a/commands/undraft.go b/commands/undraft.go index 72f5b677d..8e287651f 100644 --- a/commands/undraft.go +++ b/commands/undraft.go @@ -37,7 +37,7 @@ If the content's draft status is 'False', nothing is done.`, // to false and setting its publish date to now. If the specified content is // not a draft, it will log an error. func Undraft(cmd *cobra.Command, args []string) error { - if err := InitializeConfig(); err != nil { + if _, err := InitializeConfig(); err != nil { return err } diff --git a/create/content.go b/create/content.go index d939cb6bf..195080d88 100644 --- a/create/content.go +++ b/create/content.go @@ -62,7 +62,9 @@ func NewContent(fs afero.Fs, kind, name string) (err error) { return err } - page, err := hugolib.NewPage(name) + site := hugolib.NewSiteDefaultLang() + + page, err := site.NewPage(name) if err != nil { return err } diff --git a/hugolib/alias_test.go b/hugolib/alias_test.go index 180fb553c..87bc9b130 100644 --- a/hugolib/alias_test.go +++ b/hugolib/alias_test.go @@ -33,7 +33,7 @@ func TestAlias(t *testing.T) { writeSource(t, filepath.Join("content", "page.md"), pageWithAlias) writeSource(t, filepath.Join("layouts", "_default", "single.html"), basicTemplate) - if err := buildAndRenderSite(newSiteDefaultLang()); err != nil { + if err := buildAndRenderSite(NewSiteDefaultLang()); err != nil { t.Fatalf("Failed to build site: %s", err) } @@ -49,7 +49,7 @@ func TestAliasTemplate(t *testing.T) { writeSource(t, filepath.Join("layouts", "_default", "single.html"), basicTemplate) writeSource(t, filepath.Join("layouts", "alias.html"), aliasTemplate) - if err := buildAndRenderSite(newSiteDefaultLang()); err != nil { + if err := buildAndRenderSite(NewSiteDefaultLang()); err != nil { t.Fatalf("Failed to build site: %s", err) } diff --git a/ |