hugolib: Move site.Data to hugo.Data, deprecate Site.AllPages/BuildDrafts/Languages

This moves Site.Data to the hugo namespace as hugo.Data, following the
same pattern used for hugo.Sites. Also deprecate Site.AllPages,
Site.BuildDrafts, and Site.Languages.

Closes #14521

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Bjørn Erik Pedersen
2026-02-18 11:15:47 +01:00
parent d8ec0eeeaf
commit 86aa62524f
6 changed files with 111 additions and 21 deletions
+11 -3
View File
@@ -102,9 +102,13 @@ type HugoSites struct {
previousPageTreesWalkContext *doctree.WalkContext[contentNode] // Set for rebuilds only.
previousSeenTerms *hmaps.Map[term, sitesmatrix.Vectors] // Set for rebuilds only.
printUnusedTemplatesInit sync.Once
printPathWarningsInit sync.Once
printSiteSitesDeprecationInit sync.Once
printUnusedTemplatesInit sync.Once
printPathWarningsInit sync.Once
printSiteSitesDeprecationInit sync.Once
printSiteDataDeprecationInit sync.Once
printSiteAllPagesDeprecationInit sync.Once
printSiteBuildDraftsDeprecationInit sync.Once
printSiteLanguagesDeprecationInit sync.Once
// File change events with filename stored in this map will be skipped.
skipRebuildForFilenamesMu sync.Mutex
@@ -133,6 +137,10 @@ func (sp hugoSitesSitesProvider) Sites() page.Sites {
return slices.Collect(sp.h.allSitesInterface(nil))
}
func (sp hugoSitesSitesProvider) Data() map[string]any {
return sp.h.Data()
}
type progressReporter struct {
mu sync.Mutex
t time.Time
+20 -4
View File
@@ -517,13 +517,13 @@ func newHugoSites(
dependencies = append(dependencies, depFromMod(m))
}
// Create a sites provider that avoids naming conflict with HugoSites.Sites field.
// Create providers that avoid naming conflicts with HugoSites fields.
sp := hugoSitesSitesProvider{h: h}
opts := page.HugoInfoOptions{
Conf: h.Configs.GetFirstLanguageConfig(),
SitesProvider: sp,
Deps: dependencies,
Conf: h.Configs.GetFirstLanguageConfig(),
HugoInfoHugoSitesProvider: sp,
Deps: dependencies,
}
if bi := hugo.GetBuildInfo(); bi != nil {
@@ -692,11 +692,19 @@ func (s *Site) Param(key any) (any, error) {
}
// Returns a map of all the data inside /data.
// Deprecated: Use hugo.Data instead.
func (s *Site) Data() map[string]any {
s.h.printSiteDataDeprecationInit.Do(func() {
hugo.Deprecate(".Site.Data", "Use hugo.Data instead.", "v0.156.0")
})
return s.h.Data()
}
// Deprecated: See https://discourse.gohugo.io/t/56732.
func (s *Site) BuildDrafts() bool {
s.h.printSiteBuildDraftsDeprecationInit.Do(func() {
hugo.Deprecate(".Site.BuildDrafts", "See https://discourse.gohugo.io/t/56732.", "v0.156.0")
})
return s.conf.BuildDrafts
}
@@ -754,7 +762,11 @@ func (s *Site) RegularPages() page.Pages {
}
// AllPages returns all pages for all sites.
// Deprecated: See https://discourse.gohugo.io/t/56732.
func (s *Site) AllPages() page.Pages {
s.h.printSiteAllPagesDeprecationInit.Do(func() {
hugo.Deprecate(".Site.AllPages", "See https://discourse.gohugo.io/t/56732.", "v0.156.0")
})
s.CheckReady()
return s.h.Pages()
}
@@ -975,7 +987,11 @@ func (s *Site) Language() *langs.Language {
return s.language
}
// Deprecated: See https://discourse.gohugo.io/t/56732.
func (s *Site) Languages() langs.Languages {
s.h.printSiteLanguagesDeprecationInit.Do(func() {
hugo.Deprecate(".Site.Languages", "See https://discourse.gohugo.io/t/56732.", "v0.156.0")
})
return s.h.Configs.Languages
}
+50
View File
@@ -156,3 +156,53 @@ weight = 2
b.AssertFileContent("public/guest/v1.0.0/fr/index.html", "en-guest-v1.0.0|en-member-v1.0.0|en-guest-v2.0.0|en-member-v2.0.0|fr-guest-v1.0.0|fr-member-v1.0.0|fr-guest-v2.0.0|fr-member-v2.0.0|de-guest-v1.0.0|de-member-v1.0.0|de-guest-v2.0.0|de-member-v2.0.0|")
b.AssertLogContains(".Site.Sites and .Page.Sites was deprecated")
}
func TestHugoDataDeprecation(t *testing.T) {
files := `
-- hugo.toml --
disableKinds = ['page','rss','section','sitemap','taxonomy','term']
-- data/mydata.toml --
v1 = "myvalue"
-- layouts/home.html --
hugo.Data: {{ hugo.Data.mydata.v1 }}|
site.Data: {{ site.Data.mydata.v1 }}|
`
b := Test(t, files, TestOptInfo())
b.AssertFileContent("public/index.html",
"hugo.Data: myvalue|",
"site.Data: myvalue|",
)
b.AssertLogContains(".Site.Data was deprecated")
}
func TestSiteDeprecations(t *testing.T) {
files := `
-- hugo.toml --
disableKinds = ['rss','sitemap','taxonomy','term']
buildDrafts = true
[languages]
[languages.en]
weight = 1
[languages.fr]
weight = 2
-- content/p1.md --
---
title: Page 1
---
-- layouts/home.html --
AllPages: {{ len .Site.AllPages }}|
BuildDrafts: {{ .Site.BuildDrafts }}|
Languages: {{ len .Site.Languages }}|
`
b := Test(t, files, TestOptInfo())
b.AssertFileContent("public/index.html",
"AllPages: 3|",
"BuildDrafts: true|",
"Languages: 2|",
)
b.AssertLogContains(".Site.AllPages was deprecated")
b.AssertLogContains(".Site.BuildDrafts was deprecated")
b.AssertLogContains(".Site.Languages was deprecated")
}
+17 -10
View File
@@ -25,7 +25,7 @@ import (
var _ hstore.StoreProvider = (*HugoInfo)(nil)
type hugoInfoProviders struct {
SitesProvider
HugoInfoHugoSitesProvider
}
// HugoInfo contains information about the current Hugo environment.
@@ -123,14 +123,21 @@ type HugoInfoConfigProvider interface {
IsMultilingual() bool
}
// HugoInfoHugoSitesProvider provides what HugoInfo needs from hugolib.HugoSites.
type HugoInfoHugoSitesProvider interface {
SitesProvider
DataProvider
}
// HugoInfoOptions defines the providers required to initialize HugoInfo.
type HugoInfoOptions struct {
Conf HugoInfoConfigProvider
Deps []*hugo.Dependency
SitesProvider SitesProvider
CommitHash string
BuildDate string
GoVersion string
Conf HugoInfoConfigProvider
HugoInfoHugoSitesProvider HugoInfoHugoSitesProvider
Deps []*hugo.Dependency
CommitHash string
BuildDate string
GoVersion string
}
// NewHugoInfo creates a new Hugo Info object.
@@ -141,8 +148,8 @@ func NewHugoInfo(opts HugoInfoOptions) HugoInfo {
if opts.Conf.Environment() == "" {
panic("environment not set")
}
if opts.SitesProvider == nil {
opts.SitesProvider = nopSitesProvider{}
if opts.HugoInfoHugoSitesProvider == nil {
opts.HugoInfoHugoSitesProvider = nopHugoSitesProvider{}
}
return HugoInfo{
@@ -150,7 +157,7 @@ func NewHugoInfo(opts HugoInfoOptions) HugoInfo {
BuildDate: opts.BuildDate,
GoVersion: opts.GoVersion,
hugoInfoProviders: hugoInfoProviders{SitesProvider: opts.SitesProvider},
hugoInfoProviders: hugoInfoProviders{HugoInfoHugoSitesProvider: opts.HugoInfoHugoSitesProvider},
opts: opts,
store: hstore.NewScratch(),
+11 -2
View File
@@ -454,9 +454,13 @@ type ShortcodeInfoProvider interface {
HasShortcode(name string) bool
}
type nopSitesProvider struct{}
type nopHugoSitesProvider struct{}
func (nopSitesProvider) Sites() Sites {
func (nopHugoSitesProvider) Sites() Sites {
return nil
}
func (nopHugoSitesProvider) Data() map[string]any {
return nil
}
@@ -466,6 +470,11 @@ type SitesProvider interface {
Sites() Sites
}
// DataProvider provides access to the data directory.
type DataProvider interface {
Data() map[string]any
}
// SiteProvider provides access to the current site.
type SiteProvider interface {
Site() Site
+2 -2
View File
@@ -18,9 +18,9 @@ import (
)
const (
// Identifies site.Data.
// Identifies hugo.Data.
// The change detection in /data is currently very coarse grained.
Data = identity.StringIdentity("site.Data")
Data = identity.StringIdentity("hugo.Data")
)
// FromString returns the identity from the given string,