gohugoio/hugo · error

could not determine content directory for

Error message

could not determine content directory for %q

What it means

Returned by BaseFs content-directory resolution when no project content mount can host the given filename. Hugo tries every content mount: absolute paths must match a mount's BaseDir/Filename, relative paths go into the first project content directory. If none qualifies, it gives up with this error.

Solutions

  1. Inspect the %q filename in the message and compare it against your [[mounts]] source/target in hugo config — the absolute path must be inside a mount's source.
  2. Add or fix a content mount so the offending path is covered: target = "content", source = "<dir-containing-the-file>".
  3. If the path is correct, ensure the mount is marked as a project mount and the directory exists.
  4. Avoid passing absolute paths that are not under any module/project root.

Example fix

// before
[[mounts]]
source = "/srv/site/pages"
target = "content"
// file at /srv/site/posts/x.md -> no match (outside /srv/site/pages)

// after: make the mount cover the real content root
[[mounts]]
source = "/srv/site"
target = "content"
Defensive patterns

Strategy: validation

Validate before calling

// Validate before resolving: ensure an absolute path is under a content mount.
func underContentMount(absPath string, mounts []Mount) bool {
    for _, m := range mounts {
        if m.Target == "content" && strings.HasPrefix(absPath, m.Source) {
            return true
        }
    }
    return false
}

Try / catch

rel, abs, err := b.Paths().FilenameFromBase(filename)
if err != nil {
    // surface the unresolvable path and skip/abort
    h.Log.Errorf("content resolution: %v", err)
    return
}

Prevention

When it happens

Trigger: Raised when resolving where to place a content file whose absolute path does not fall under any configured content mount (no mount's Filename/BaseDir prefix matches), and the path is absolute so the 'first project dir' fallback is skipped.

Common situations: Misconfigured module mounts where source paths don't align with the actual filesystem layout; an absolute path passed from a tool/plugin that lives outside all mounted content roots; theme/content mount `source` pointing at the wrong directory after a repo restructure.

Related errors


AI-assisted analysis of gohugoio/hugo@52c9bd7908 (2026-08-09). Data as JSON: /api/errors/b4dfcd3fc423140d. Report an issue: GitHub.

Appendix: source

Thrown at hugolib/filesystems/basefs.go:210

	}

	if !isAbs {
		// A filename on the form "posts/mypage.md", put it inside
		// the first content folder, usually <workDir>/content.
		// Pick the first project dir (which is probably the most important one).
		for _, dir := range b.SourceFilesystems.Content.mounts() {
			if !dir.IsDir() {
				continue
			}
			meta := dir.Meta()
			if meta.IsProject {
				return filename, filepath.Join(meta.Filename, filename), nil
			}
		}
	}

	return "", "", fmt.Errorf("could not determine content directory for %q", filename)
}

// ResolveJSConfigFile resolves the JS-related config file to a absolute
// filename. One example of such would be postcss.config.js.
func (b *BaseFs) ResolveJSConfigFile(name string) string {
	// First look in assets/_jsconfig
	fi, err := b.Assets.Fs.Stat(filepath.Join(files.FolderJSConfig, name))
	if err == nil {
		return fi.(hugofs.FileMetaInfo).Meta().Filename
	}
	// Fall back to the work dir.
	fi, err = b.Work.Stat(name)
	if err == nil {
		return fi.(hugofs.FileMetaInfo).Meta().Filename
	}

	return ""
}

View on GitHub (pinned to 52c9bd7908)