diff options
author | Bjørn Erik Pedersen <bjorn.erik.pedersen@gmail.com> | 2022-03-21 09:35:15 +0100 |
---|---|---|
committer | Bjørn Erik Pedersen <bjorn.erik.pedersen@gmail.com> | 2022-04-08 13:26:17 +0200 |
commit | d070bdf10f14d233288f7318a4e9f7555f070a65 (patch) | |
tree | fff8d59f98bdab3027bb45c4e10ca88594332872 /commands | |
parent | b08193971a821fc27e549a73120c15e5e5186775 (diff) |
Rework the Destination filesystem to make --renderStaticToDisk work
See #9626
Diffstat (limited to 'commands')
-rw-r--r-- | commands/commandeer.go | 78 | ||||
-rw-r--r-- | commands/commands.go | 9 | ||||
-rw-r--r-- | commands/commands_test.go | 124 | ||||
-rw-r--r-- | commands/hugo.go | 12 | ||||
-rw-r--r-- | commands/hugo_test.go | 6 | ||||
-rw-r--r-- | commands/list_test.go | 5 | ||||
-rw-r--r-- | commands/new_site.go | 6 | ||||
-rw-r--r-- | commands/server.go | 18 | ||||
-rw-r--r-- | commands/server_test.go | 12 | ||||
-rw-r--r-- | commands/static_syncer.go | 21 |
10 files changed, 155 insertions, 136 deletions
diff --git a/commands/commandeer.go b/commands/commandeer.go index ced149e7a..1162a4b70 100644 --- a/commands/commandeer.go +++ b/commands/commandeer.go @@ -30,6 +30,7 @@ import ( "github.com/gohugoio/hugo/common/herrors" "github.com/gohugoio/hugo/common/hugo" + "github.com/gohugoio/hugo/common/paths" jww "github.com/spf13/jwalterweatherman" @@ -42,6 +43,7 @@ import ( "github.com/spf13/afero" "github.com/bep/debounce" + "github.com/bep/overlayfs" "github.com/gohugoio/hugo/common/types" "github.com/gohugoio/hugo/deps" "github.com/gohugoio/hugo/helpers" @@ -73,8 +75,10 @@ type commandeer struct { // be fast enough that we could maybe just add it for all server modes. changeDetector *fileChangeDetector - // We need to reuse this on server rebuilds. - destinationFs afero.Fs + // We need to reuse these on server rebuilds. + // These 2 will be different if --renderStaticToDisk is set. + publishDirFs afero.Fs + publishDirServerFs afero.Fs h *hugoBuilderCommon ftch flagsToConfigHandler @@ -162,7 +166,8 @@ func (c *commandeer) Set(key string, value any) { } func (c *commandeer) initFs(fs *hugofs.Fs) error { - c.destinationFs = fs.Destination + c.publishDirFs = fs.PublishDir + c.publishDirServerFs = fs.PublishDirServer c.DepsCfg.Fs = fs return nil @@ -378,28 +383,63 @@ func (c *commandeer) loadConfig() error { createMemFs := config.GetBool("renderToMemory") c.renderStaticToDisk = config.GetBool("renderStaticToDisk") - if createMemFs && !c.renderStaticToDisk { + if createMemFs { // Rendering to memoryFS, publish to Root regardless of publishDir. config.Set("publishDir", "/") + config.Set("publishDirStatic", "/") + } else if c.renderStaticToDisk { + // Hybrid, render dynamic content to Root. + config.Set("publishDirStatic", config.Get("publishDir")) + config.Set("publishDir", "/") + } c.fsCreate.Do(func() { fs := hugofs.NewFrom(sourceFs, config) - if c.destinationFs != nil { + if c.publishDirFs != nil { // Need to reuse the destination on server rebuilds. - fs.Destination = c.destinationFs - } else if createMemFs && c.renderStaticToDisk { - // Writes the dynamic output on memory, - // while serve others directly from publishDir + fs.PublishDir = c.publishDirFs + fs.PublishDirServer = c.publishDirServerFs + } else { publishDir := config.GetString("publishDir") - writableFs := afero.NewBasePathFs(afero.NewMemMapFs(), publishDir) - publicFs := afero.NewOsFs() - fs.Destination = afero.NewCopyOnWriteFs(afero.NewReadOnlyFs(publicFs), writableFs) - fs.DestinationStatic = publicFs - } else if createMemFs { - // Hugo writes the output to memory instead of the disk. - fs.Destination = new(afero.MemMapFs) + publishDirStatic := config.GetString("publishDirStatic") + workingDir := config.GetString("workingDir") + absPublishDir := paths.AbsPathify(workingDir, publishDir) + absPublishDirStatic := paths.AbsPathify(workingDir, publishDirStatic) + + if c.renderStaticToDisk { + // Writes the dynamic output oton memory, + // while serve others directly from /public on disk. + dynamicFs := afero.NewMemMapFs() + staticFs := afero.NewBasePathFs(afero.NewOsFs(), absPublishDirStatic) + + // Serve from both the static and dynamic fs, + // the first will take priority. + // THis is a read-only filesystem, + // we do all the writes to + // fs.Destination and fs.DestinationStatic. + fs.PublishDirServer = overlayfs.New( + overlayfs.Options{ + Fss: []afero.Fs{ + dynamicFs, + staticFs, + }, + }, + ) + fs.PublishDir = dynamicFs + fs.PublishDirStatic = staticFs + } else if createMemFs { + // Hugo writes the output to memory instead of the disk. + fs.PublishDir = new(afero.MemMapFs) + fs.PublishDirServer = fs.PublishDir + fs.PublishDirStatic = fs.PublishDir + } else { + // Write everything to disk. + fs.PublishDir = afero.NewBasePathFs(afero.NewOsFs(), absPublishDir) + fs.PublishDirServer = fs.PublishDir + fs.PublishDirStatic = fs.PublishDir + } } if c.fastRenderMode { @@ -413,15 +453,15 @@ func (c *commandeer) loadConfig() error { } changeDetector.PrepareNew() - fs.Destination = hugofs.NewHashingFs(fs.Destination, changeDetector) - fs.DestinationStatic = hugofs.NewHashingFs(fs.DestinationStatic, changeDetector) + fs.PublishDir = hugofs.NewHashingFs(fs.PublishDir, changeDetector) + fs.PublishDirStatic = hugofs.NewHashingFs(fs.PublishDirStatic, changeDetector) c.changeDetector = changeDetector } if c.Cfg.GetBool("logPathWarnings") { // Note that we only care about the "dynamic creates" here, // so skip the static fs. - fs.Destination = hugofs.NewCreateCountingFs(fs.Destination) + fs.PublishDir = hugofs.NewCreateCountingFs(fs.PublishDir) } // To debug hard-to-find path issues. diff --git a/commands/commands.go b/commands/commands.go index 01f076d1a..99b0866e5 100644 --- a/commands/commands.go +++ b/commands/commands.go @@ -18,10 +18,9 @@ import ( "os" "time" - "github.com/gohugoio/hugo/hugolib/paths" - "github.com/gohugoio/hugo/common/hugo" "github.com/gohugoio/hugo/common/loggers" + hpaths "github.com/gohugoio/hugo/common/paths" "github.com/gohugoio/hugo/config" "github.com/gohugoio/hugo/helpers" "github.com/spf13/cobra" @@ -243,14 +242,14 @@ func (cc *hugoBuilderCommon) timeTrack(start time.Time, name string) { func (cc *hugoBuilderCommon) getConfigDir(baseDir string) string { if cc.cfgDir != "" { - return paths.AbsPathify(baseDir, cc.cfgDir) + return hpaths.AbsPathify(baseDir, cc.cfgDir) } if v, found := os.LookupEnv("HUGO_CONFIGDIR"); found { - return paths.AbsPathify(baseDir, v) + return hpaths.AbsPathify(baseDir, v) } - return paths.AbsPathify(baseDir, "config") + return hpaths.AbsPathify(baseDir, "config") } func (cc *hugoBuilderCommon) getEnvironment(isServer bool) string { diff --git a/commands/commands_test.go b/commands/commands_test.go index 43c7f8520..e3ec7bd99 100644 --- a/commands/commands_test.go +++ b/commands/commands_test.go @@ -22,8 +22,6 @@ import ( "github.com/gohugoio/hugo/config" - "github.com/gohugoio/hugo/htesting" - "github.com/spf13/afero" "github.com/gohugoio/hugo/hugofs" @@ -38,15 +36,13 @@ import ( func TestExecute(t *testing.T) { c := qt.New(t) - createSite := func(c *qt.C) (string, func()) { - dir, clean, err := createSimpleTestSite(t, testSiteConfig{}) - c.Assert(err, qt.IsNil) - return dir, clean + createSite := func(c *qt.C) string { + dir := createSimpleTestSite(t, testSiteConfig{}) + return dir } c.Run("hugo", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) resp := Execute([]string{"-s=" + dir}) c.Assert(resp.Err, qt.IsNil) result := resp.Result @@ -56,8 +52,7 @@ func TestExecute(t *testing.T) { }) c.Run("hugo, set environment", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) resp := Execute([]string{"-s=" + dir, "-e=staging"}) c.Assert(resp.Err, qt.IsNil) result := resp.Result @@ -65,9 +60,8 @@ func TestExecute(t *testing.T) { }) c.Run("convert toJSON", func(c *qt.C) { - dir, clean := createSite(c) + dir := createSite(c) output := filepath.Join(dir, "myjson") - defer clean() resp := Execute([]string{"convert", "toJSON", "-s=" + dir, "-e=staging", "-o=" + output}) c.Assert(resp.Err, qt.IsNil) converted := readFileFrom(c, filepath.Join(output, "content", "p1.md")) @@ -75,8 +69,7 @@ func TestExecute(t *testing.T) { }) c.Run("config, set environment", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) out, err := captureStdout(func() error { resp := Execute([]string{"config", "-s=" + dir, "-e=staging"}) return resp.Err @@ -86,16 +79,14 @@ func TestExecute(t *testing.T) { }) c.Run("deploy, environment set", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) resp := Execute([]string{"deploy", "-s=" + dir, "-e=staging", "--target=mydeployment", "--dryRun"}) c.Assert(resp.Err, qt.Not(qt.IsNil)) c.Assert(resp.Err.Error(), qt.Contains, `no driver registered for "hugocloud"`) }) c.Run("list", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) out, err := captureStdout(func() error { resp := Execute([]string{"list", "all", "-s=" + dir, "-e=staging"}) return resp.Err @@ -105,8 +96,7 @@ func TestExecute(t *testing.T) { }) c.Run("new theme", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) themesDir := filepath.Join(dir, "mythemes") resp := Execute([]string{"new", "theme", "mytheme", "-s=" + dir, "-e=staging", "--themesDir=" + themesDir}) c.Assert(resp.Err, qt.IsNil) @@ -115,8 +105,7 @@ func TestExecute(t *testing.T) { }) c.Run("new site", func(c *qt.C) { - dir, clean := createSite(c) - defer clean() + dir := createSite(c) siteDir := filepath.Join(dir, "mysite") resp := Execute([]string{"new", "site", siteDir, "-e=staging"}) c.Assert(resp.Err, qt.IsNil) @@ -167,7 +156,7 @@ func TestFlags(t *testing.T) { name: "ignoreVendorPaths", args: []string{"server", "--ignoreVendorPaths=github.com/**"}, check: func(c *qt.C, cmd *serverCmd) { - cfg := config.New() + cfg := config.NewWithTestDefaults() cmd.flagsToConfig(cfg) c.Assert(cfg.Get("ignoreVendorPaths"), qt.Equals, "github.com/**") }, @@ -208,7 +197,7 @@ func TestFlags(t *testing.T) { c.Assert(sc.serverPort, qt.Equals, 1366) c.Assert(sc.environment, qt.Equals, "testing") - cfg := config.New() + cfg := config.NewWithTestDefaults() sc.flagsToConfig(cfg) c.Assert(cfg.GetString("publishDir"), qt.Equals, "/tmp/mydestination") c.Assert(cfg.GetString("contentDir"), qt.Equals, "mycontent") @@ -253,14 +242,8 @@ func TestFlags(t *testing.T) { func TestCommandsExecute(t *testing.T) { c := qt.New(t) - dir, clean, err := createSimpleTestSite(t, testSiteConfig{}) - c.Assert(err, qt.IsNil) - - dirOut, clean2, err := htesting.CreateTempDir(hugofs.Os, "hugo-cli-out") - c.Assert(err, qt.IsNil) - - defer clean() - defer clean2() + dir := createSimpleTestSite(t, testSiteConfig{}) + dirOut := t.TempDir() sourceFlag := fmt.Sprintf("-s=%s", dir) @@ -297,29 +280,35 @@ func TestCommandsExecute(t *testing.T) { } for _, test := range tests { - b := newCommandsBuilder().addAll().build() - hugoCmd := b.getCommand() - test.flags = append(test.flags, "--quiet") - hugoCmd.SetArgs(append(test.commands, test.flags...)) - - // TODO(bep) capture output and add some simple asserts - // TODO(bep) misspelled subcommands does not return an error. We should investigate this - // but before that, check for "Error: unknown command". - - _, err := hugoCmd.ExecuteC() - if test.expectErrToContain != "" { - c.Assert(err, qt.Not(qt.IsNil)) - c.Assert(err.Error(), qt.Contains, test.expectErrToContain) - } else { - c.Assert(err, qt.IsNil) + name := "hugo" + if len(test.commands) > 0 { + name = test.commands[0] } + c.Run(name, func(c *qt.C) { + b := newCommandsBuilder().addAll().build() + hugoCmd := b.getCommand() + test.flags = append(test.flags, "--quiet") + hugoCmd.SetArgs(append(test.commands, test.flags...)) + + // TODO(bep) capture output and add some simple asserts + // TODO(bep) misspelled subcommands does not return an error. We should investigate this + // but before that, check for "Error: unknown command". + + _, err := hugoCmd.ExecuteC() + if test.expectErrToContain != "" { + c.Assert(err, qt.Not(qt.IsNil)) + c.Assert(err.Error(), qt.Contains, test.expectErrToContain) + } else { + c.Assert(err, qt.IsNil) + } - // Assert that we have not left any development debug artifacts in - // the code. - if b.c != nil { - _, ok := b.c.destinationFs.(types.DevMarker) - c.Assert(ok, qt.Equals, false) - } + // Assert that we have not left any development debug artifacts in + // the code. + if b.c != nil { + _, ok := b.c.publishDirFs.(types.DevMarker) + c.Assert(ok, qt.Equals, false) + } + }) } } @@ -329,11 +318,8 @@ type testSiteConfig struct { contentDir string } -func createSimpleTestSite(t testing.TB, cfg testSiteConfig) (string, func(), error) { - d, clean, e := htesting.CreateTempDir(hugofs.Os, "hugo-cli") - if e != nil { - return "", nil, e - } +func createSimpleTestSite(t testing.TB, cfg testSiteConfig) string { + dir := t.TempDir() cfgStr := ` @@ -352,23 +338,23 @@ title = "Hugo Commands" contentDir = cfg.contentDir } - os.MkdirAll(filepath.Join(d, "public"), 0777) + os.MkdirAll(filepath.Join(dir, "public"), 0777) // Just the basic. These are for CLI tests, not site testing. - writeFile(t, filepath.Join(d, "config.toml"), cfgStr) - writeFile(t, filepath.Join(d, "config", "staging", "params.toml"), `myparam="paramstaging"`) - writeFile(t, filepath.Join(d, "config", "staging", "deployment.toml"), ` + writeFile(t, filepath.Join(dir, "config.toml"), cfgStr) + writeFile(t, filepath.Join(dir, "config", "staging", "params.toml"), `myparam="paramstaging"`) + writeFile(t, filepath.Join(dir, "config", "staging", "deployment.toml"), ` [[targets]] name = "mydeployment" URL = "hugocloud://hugotestbucket" `) - writeFile(t, filepath.Join(d, "config", "testing", "params.toml"), `myparam="paramtesting"`) - writeFile(t, filepath.Join(d, "config", "production", "params.toml"), `myparam="paramproduction"`) + writeFile(t, filepath.Join(dir, "config", "testing", "params.toml"), `myparam="paramtesting"`) + writeFile(t, filepath.Join(dir, "config", "production", "params.toml"), `myparam="paramproduction"`) - writeFile(t, filepath.Join(d, "static", "myfile.txt"), `Hello World!`) + writeFile(t, filepath.Join(dir, "static", "myfile.txt"), `Hello World!`) - writeFile(t, filepath.Join(d, contentDir, "p1.md"), ` + writeFile(t, filepath.Join(dir, contentDir, "p1.md"), ` --- title: "P1" weight: 1 @@ -378,20 +364,20 @@ Content `) - writeFile(t, filepath.Join(d, "layouts", "_default", "single.html"), ` + writeFile(t, filepath.Join(dir, "layouts", "_default", "single.html"), ` Single: {{ .Title }} `) - writeFile(t, filepath.Join(d, "layouts", "_default", "list.html"), ` + writeFile(t, filepath.Join(dir, "layouts", "_default", "list.html"), ` List: {{ .Title }} Environment: {{ hugo.Environment }} `) - return d, clean, nil + return dir } func writeFile(t testing.TB, filename, content string) { diff --git a/commands/hugo.go b/commands/hugo.go index 21140fa43..9033fac90 100644 --- a/commands/hugo.go +++ b/commands/hugo.go @@ -508,7 +508,7 @@ func (c *commandeer) build() error { c.hugo().PrintProcessingStats(os.Stdout) fmt.Println() - if createCounter, ok := c.destinationFs.(hugofs.DuplicatesReporter); ok { + if createCounter, ok := c.publishDirFs.(hugofs.DuplicatesReporter); ok { dupes := createCounter.ReportDuplicates() if dupes != "" { c.logger.Warnln("Duplicate target paths:", dupes) @@ -634,11 +634,7 @@ func chmodFilter(dst, src os.FileInfo) bool { } func (c *commandeer) copyStaticTo(sourceFs *filesystems.SourceFilesystem) (uint64, error) { - publishDir := c.hugo().PathSpec.PublishDir - // If root, remove the second '/' - if publishDir == "//" { - publishDir = helpers.FilePathSeparator - } + publishDir := helpers.FilePathSeparator if sourceFs.PublishFolder != "" { publishDir = filepath.Join(publishDir, sourceFs.PublishFolder) @@ -651,9 +647,9 @@ func (c *commandeer) copyStaticTo(sourceFs *filesystems.SourceFilesystem) (uint6 syncer.NoChmod = c.Cfg.GetBool("noChmod") syncer.ChmodFilter = chmodFilter syncer.SrcFs = fs - syncer.DestFs = c.Fs.Destination + syncer.DestFs = c.Fs.PublishDir if c.renderStaticToDisk { - syncer.DestFs = c.Fs.DestinationStatic + syncer.DestFs = c.Fs.PublishDirStatic } // Now that we are using a unionFs for the static directories // We can effectively clean the publishDir on initial sync diff --git a/commands/hugo_test.go b/commands/hugo_test.go index 4bead09f0..aca3de2fd 100644 --- a/commands/hugo_test.go +++ b/commands/hugo_test.go @@ -36,12 +36,10 @@ title = "Hugo Commands" contentDir = "thisdoesnotexist" ` - dir, clean, err := createSimpleTestSite(t, testSiteConfig{configTOML: cfgStr, contentDir: contentDir}) - c.Assert(err, qt.IsNil) - defer clean() + dir := createSimpleTestSite(t, testSiteConfig{configTOML: cfgStr, contentDir: contentDir}) cmd.SetArgs([]string{"-s=" + dir, "-c=" + contentDir}) - _, err = cmd.ExecuteC() + _, err := cmd.ExecuteC() c.Assert(err, qt.IsNil) } diff --git a/commands/list_test.go b/commands/list_test.go index 6f3d6c74d..56a3ee9b9 100644 --- a/commands/list_test.go +++ b/commands/list_test.go @@ -29,10 +29,7 @@ func captureStdout(f func() error) (string, error) { func TestListAll(t *testing.T) { c := qt.New(t) - dir, clean, err := createSimpleTestSite(t, testSiteConfig{}) - defer clean() - - c.Assert(err, qt.IsNil) + dir := createSimpleTestSite(t, testSiteConfig{}) hugoCmd := newCommandsBuilder().addAll().build() cmd := hugoCmd.getCommand() diff --git a/commands/new_site.go b/commands/new_site.go index 1e3ed710b..e49a60202 100644 --- a/commands/new_site.go +++ b/commands/new_site.go @@ -122,8 +122,10 @@ func (n *newSiteCmd) newSite(cmd *cobra.Command, args []string) error { } forceNew, _ := cmd.Flags().GetBool("force") - - return n.doNewSite(hugofs.NewDefault(config.New()), createpath, forceNew) + cfg := config.New() + cfg.Set("workingDir", createpath) + cfg.Set("publishDir", "public") + return n.doNewSite(hugofs.NewDefault(cfg), createpath, forceNew) } func createConfig(fs *hugofs.Fs, inpath string, kind string) (err error) { diff --git a/commands/server.go b/commands/server.go index da1918ede..145a889bb 100644 --- a/commands/server.go +++ b/commands/server.go @@ -23,6 +23,7 @@ import ( "net/url" "os" "os/signal" + "path" "path/filepath" "regexp" "runtime" @@ -148,7 +149,7 @@ func (sc *serverCmd) server(cmd *cobra.Command, args []string) error { var serverCfgInit sync.Once cfgInit := func(c *commandeer) (rerr error) { - c.Set("renderToMemory", !sc.renderToDisk) + c.Set("renderToMemory", !(sc.renderToDisk || sc.renderStaticToDisk)) c.Set("renderStaticToDisk", sc.renderStaticToDisk) if cmd.Flags().Changed("navigateToChanged") { c.Set("navigateToChanged", sc.navigateToChanged) @@ -330,13 +331,18 @@ func (f *fileServer) createEndpoint(i int) (*http.ServeMux, net.Listener, string port := f.c.serverPorts[i].p listener := f.c.serverPorts[i].ln + // For logging only. + // TODO(bep) consolidate. publishDir := f.c.Cfg.GetString("publishDir") + publishDirStatic := f.c.Cfg.GetString("publishDirStatic") + workingDir := f.c.Cfg.GetString("workingDir") if root != "" { publishDir = filepath.Join(publishDir, root) + publishDirStatic = filepath.Join(publishDirStatic, root) } - - absPublishDir := f.c.hugo().PathSpec.AbsPathify(publishDir) + absPublishDir := paths.AbsPathify(workingDir, publishDir) + absPublishDirStatic := paths.AbsPathify(workingDir, publishDirStatic) jww.FEEDBACK.Printf("Environment: %q", f.c.hugo().Deps.Site.Hugo().Environment) @@ -344,14 +350,14 @@ func (f *fileServer) createEndpoint(i int) (*http.ServeMux, net.Listener, string if f.s.renderToDisk { jww.FEEDBACK.Println("Serving pages from " + absPublishDir) } else if f.s.renderStaticToDisk { - jww.FEEDBACK.Println("Serving pages from memory and static files from " + absPublishDir) + jww.FEEDBACK.Println("Serving pages from memory and static files from " + absPublishDirStatic) } else { jww.FEEDBACK.Println("Serving pages from memory") } } - httpFs := afero.NewHttpFs(f.c.destinationFs) - fs := filesOnlyFs{httpFs.Dir(absPublishDir)} + httpFs := afero.NewHttpFs(f.c.publishDirServerFs) + fs := filesOnlyFs{httpFs.Dir(path.Join("/", root))} if i == 0 && f.c.fastRenderMode { jww.FEEDBACK.Println("Running in Fast Render Mode. For full rebuilds on change: hugo server --disableFastRender") diff --git a/commands/server_test.go b/commands/server_test.go index 6972bbe69..ea50afd94 100644 --- a/commands/server_test.go +++ b/commands/server_test.go @@ -77,6 +77,9 @@ func TestServerFlags(t *testing.T) { {"--renderToDisk", func(c *qt.C, r serverTestResult) { assertPublic(c, r, true) }}, + {"--renderStaticToDisk", func(c *qt.C, r serverTestResult) { + assertPublic(c, r, true) + }}, } { c.Run(test.flag, func(c *qt.C) { config := ` @@ -105,9 +108,7 @@ type serverTestResult struct { } func runServerTest(c *qt.C, getHome bool, config string, args ...string) (result serverTestResult) { - dir, clean, err := createSimpleTestSite(c, testSiteConfig{configTOML: config}) - defer clean() - c.Assert(err, qt.IsNil) + dir := createSimpleTestSite(c, testSiteConfig{configTOML: config}) sp, err := helpers.FindAvailablePort() c.Assert(err, qt.IsNil) @@ -141,12 +142,15 @@ func runServerTest(c *qt.C, getHome bool, config string, args ...string) (result time.Sleep(567 * time.Millisecond) resp, err := http.Get(fmt.Sprintf("http://localhost:%d/", port)) c.Check(err, qt.IsNil) + c.Check(resp.StatusCode, qt.Equals, http.StatusOK) if err == nil { defer resp.Body.Close() result.homeContent = helpers.ReaderToString(resp.Body) } } + time.Sleep(1 * time.Second) + select { case <-stop: case stop <- true: @@ -191,7 +195,7 @@ func TestFixURL(t *testing.T) { t.Run(test.TestName, func(t *testing.T) { b := newCommandsBuilder() s := b.newServerCmd() - v := config.New() + v := config.NewWithTestDefaults() baseURL := test.CLIBaseURL v.Set("baseURL", test.CfgBaseURL) s.serverAppend = test.AppendPort diff --git a/commands/static_syncer.go b/commands/static_syncer.go index 2eb2b6662..b97c4df7a 100644 --- a/commands/static_syncer.go +++ b/commands/static_syncer.go @@ -40,11 +40,7 @@ func (s *staticSyncer) syncsStaticEvents(staticEvents []fsnotify.Event) error { c := s.c syncFn := func(sourceFs *filesystems.SourceFilesystem) (uint64, error) { - publishDir := c.hugo().PathSpec.PublishDir - // If root, remove the second '/' - if publishDir == "//" { - publishDir = helpers.FilePathSeparator - } + publishDir := helpers.FilePathSeparator if sourceFs.PublishFolder != "" { publishDir = filepath.Join(publishDir, sourceFs.PublishFolder) @@ -55,9 +51,9 @@ func (s *staticSyncer) syncsStaticEvents(staticEvents []fsnotify.Event) error { syncer.NoChmod = c.Cfg.GetBool("noChmod") syncer.ChmodFilter = chmodFilter syncer.SrcFs = sourceFs.Fs - syncer.DestFs = c.Fs.Destination + syncer.DestFs = c.Fs.PublishDir if c.renderStaticToDisk { - syncer.DestFs = c.Fs.DestinationStatic + syncer.DestFs = c.Fs.PublishDirStatic } // prevent spamming the log on changes @@ -101,19 +97,14 @@ func (s *staticSyncer) syncsStaticEvents(staticEvents []fsnotify.Event) error { if ev.Op&fsnotify.Rename == fsnotify.Rename || ev.Op&fsnotify.Remove == fsnotify.Remove { if _, err := sourceFs.Fs.Stat(relPath); os.IsNotExist(err) { // If file doesn't exist in any static dir, remove it - toRemove := filepath.Join(publishDir, relPath) + logger.Println("File no longer exists in static dir, removing", relPath) + _ = c.Fs.PublishDirStatic.RemoveAll(relPath) - logger.Println("File no longer exists in static dir, removing", toRemove) - if c.renderStaticToDisk { - _ = c.Fs.DestinationStatic.RemoveAll(toRemove) - } else { - _ = c.Fs.Destination.RemoveAll(toRemove) - } } else if err == nil { // If file still exists, sync it logger.Println("Syncing", relPath, "to", publishDir) - if err := syncer.Sync(filepath.Join(publishDir, relPath), relPath); err != nil { + if err := syncer.Sync(relPath, relPath); err != nil { c.logger.Errorln(err) } } else { |