Skip to content

Commit b0f76a5

Browse files
committed
Adjust all + Make sure we warn about duplicate paths for v0.123.0.md vs v0.124.0.md
1 parent dabf7c6 commit b0f76a5

File tree

11 files changed

+98
-19
lines changed

11 files changed

+98
-19
lines changed

common/hstrings/strings.go

+5-5
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,11 @@ package hstrings
1616
import (
1717
"fmt"
1818
"regexp"
19+
"slices"
1920
"strings"
2021
"sync"
2122

2223
"github.com/gohugoio/hugo/compare"
23-
"slices"
2424
)
2525

2626
var _ compare.Eqer = StringEqualFold("")
@@ -128,7 +128,7 @@ func ToString(v any) (string, bool) {
128128
return "", false
129129
}
130130

131-
type Tuple struct {
132-
First string
133-
Second string
134-
}
131+
type (
132+
Strings2 [2]string
133+
Strings3 [3]string
134+
)

common/paths/pathparser.go

+13
Original file line numberDiff line numberDiff line change
@@ -704,6 +704,19 @@ func (p *Path) IdentifiersUnknown() []string {
704704
return ids
705705
}
706706

707+
func (p *Path) IdentifiersUnknownString() string {
708+
var sb strings.Builder
709+
710+
for i, id := range p.identifiersUnknown {
711+
if i > 0 {
712+
sb.WriteString(".")
713+
}
714+
sb.WriteString(p.s[p.identifiers[id].Low:p.identifiers[id].High])
715+
}
716+
717+
return sb.String()
718+
}
719+
707720
func (p *Path) Type() Type {
708721
return p.pathType
709722
}

create/content.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -291,7 +291,7 @@ func (b *contentBuilder) applyArcheType(contentFilename string, archetypeFi hugo
291291
func (b *contentBuilder) mapArcheTypeDir() error {
292292
var m archetypeMap
293293

294-
seen := map[hstrings.Tuple]bool{}
294+
seen := map[hstrings.Strings2]bool{}
295295

296296
walkFn := func(path string, fim hugofs.FileMetaInfo) error {
297297
if fim.IsDir() {
@@ -301,7 +301,7 @@ func (b *contentBuilder) mapArcheTypeDir() error {
301301
pi := fim.Meta().PathInfo
302302

303303
if pi.IsContent() {
304-
pathLang := hstrings.Tuple{First: pi.PathBeforeLangAndOutputFormatAndExt(), Second: fim.Meta().Lang}
304+
pathLang := hstrings.Strings2{pi.PathBeforeLangAndOutputFormatAndExt(), fim.Meta().Lang}
305305
if seen[pathLang] {
306306
// Duplicate content file, e.g. page.md and page.html.
307307
// In the regular build, we will filter out the duplicates, but

hugolib/pages_capture.go

+4-4
Original file line numberDiff line numberDiff line change
@@ -314,7 +314,7 @@ func (c *pagesCollector) collectDirDir(path string, root hugofs.FileMetaInfo, in
314314
return nil, filepath.SkipDir
315315
}
316316

317-
seen := map[hstrings.Tuple]bool{}
317+
seen := map[hstrings.Strings3]bool{}
318318
for _, fi := range readdir {
319319
if fi.IsDir() {
320320
continue
@@ -327,7 +327,7 @@ func (c *pagesCollector) collectDirDir(path string, root hugofs.FileMetaInfo, in
327327
// These would eventually have been filtered out as duplicates when
328328
// inserting them into the document store,
329329
// but doing it here will preserve a consistent ordering.
330-
baseLang := hstrings.Tuple{First: pi.Base(), Second: meta.Lang}
330+
baseLang := hstrings.Strings3{pi.Base(), pi.IdentifiersUnknownString(), meta.Lang}
331331
if seen[baseLang] {
332332
continue
333333
}
@@ -374,7 +374,7 @@ func (c *pagesCollector) collectDirDir(path string, root hugofs.FileMetaInfo, in
374374

375375
func (c *pagesCollector) handleBundleLeaf(dir, bundle hugofs.FileMetaInfo, inPath string, readdir []hugofs.FileMetaInfo) error {
376376
bundlePi := bundle.Meta().PathInfo
377-
seen := map[hstrings.Tuple]bool{}
377+
seen := map[hstrings.Strings2]bool{}
378378

379379
walk := func(path string, info hugofs.FileMetaInfo) error {
380380
if info.IsDir() {
@@ -396,7 +396,7 @@ func (c *pagesCollector) handleBundleLeaf(dir, bundle hugofs.FileMetaInfo, inPat
396396
// These would eventually have been filtered out as duplicates when
397397
// inserting them into the document store,
398398
// but doing it here will preserve a consistent ordering.
399-
baseLang := hstrings.Tuple{First: pi.Base(), Second: info.Meta().Lang}
399+
baseLang := hstrings.Strings2{pi.Base(), info.Meta().Lang}
400400
if seen[baseLang] {
401401
return nil
402402
}

hugolib/site.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -834,7 +834,7 @@ func (s *Site) initRenderFormats() {
834834
s.renderFormats = formats
835835
}
836836

837-
func (s *Site) GetRelatedDocsHandler() *page.RelatedDocsHandler {
837+
func (s *Site) GetInternalRelatedDocsHandler() *page.RelatedDocsHandler {
838838
return s.relatedDocsHandler
839839
}
840840

resources/page/page.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -150,8 +150,8 @@ type InSectionPositioner interface {
150150

151151
// InternalDependencies is considered an internal interface.
152152
type InternalDependencies interface {
153-
// GetRelatedDocsHandler is for internal use only.
154-
GetRelatedDocsHandler() *RelatedDocsHandler
153+
// GetInternalRelatedDocsHandler is for internal use only.
154+
GetInternalRelatedDocsHandler() *RelatedDocsHandler
155155
}
156156

157157
// OutputFormatsProvider provides the OutputFormats of a Page.

resources/page/pages_related.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -129,7 +129,7 @@ func (p Pages) withInvertedIndex(ctx context.Context, search func(idx *related.I
129129
return nil, fmt.Errorf("invalid type %T in related search", p[0])
130130
}
131131

132-
cache := d.GetRelatedDocsHandler()
132+
cache := d.GetInternalRelatedDocsHandler()
133133

134134
searchIndex, err := cache.getOrCreateIndex(ctx, p)
135135
if err != nil {

resources/page/testhelpers_test.go

+5-1
Original file line numberDiff line numberDiff line change
@@ -221,10 +221,14 @@ func (p *testPage) GetTerms(taxonomy string) Pages {
221221
panic("testpage: not implemented")
222222
}
223223

224-
func (p *testPage) GetRelatedDocsHandler() *RelatedDocsHandler {
224+
func (p *testPage) GetInternalRelatedDocsHandler() *RelatedDocsHandler {
225225
return relatedDocsHandler
226226
}
227227

228+
func (p *testPage) GetInternalTemplateBasePathAndDescriptor() (string, any) {
229+
return "", nil
230+
}
231+
228232
func (p *testPage) GitInfo() source.GitInfo {
229233
return source.GitInfo{}
230234
}

tpl/tplimpl/templatedescriptor.go

+3-3
Original file line numberDiff line numberDiff line change
@@ -141,7 +141,7 @@ func (this TemplateDescriptor) doCompare(category Category, other TemplateDescri
141141
const (
142142
weightKind = 3 // page, home, section, taxonomy, term (and only those)
143143
weightcustomLayout = 4 // custom layout (mylayout, set in e.g. front matter)
144-
weightLayout = 2 // standard layouts (single,list)
144+
weightLayout = 2 // standard layouts (single,list,all)
145145
weightOutputFormat = 2 // a configured output format (e.g. rss, html, json)
146146
weightMediaType = 1 // a configured media type (e.g. text/html, text/plain)
147147
weightLang = 1 // a configured language (e.g. en, nn, fr, ...)
@@ -155,7 +155,7 @@ func (this TemplateDescriptor) doCompare(category Category, other TemplateDescri
155155
// two templates /layouts/posts/single.html and /layouts/page.html,
156156
// the first one is the best match even if the second one
157157
// has a higher w1 value.
158-
weight2Group1 = 1 // kind, standardl layout (single,list)
158+
weight2Group1 = 1 // kind, standardl layout (single,list,all)
159159
weight2Group2 = 2 // custom layout (mylayout)
160160

161161
weight3 = 1 // for media type, lang, output format.
@@ -170,7 +170,7 @@ func (this TemplateDescriptor) doCompare(category Category, other TemplateDescri
170170
w.w2 = weight2Group1
171171
}
172172

173-
if other.Layout != "" && other.Layout == this.Layout {
173+
if other.Layout != "" && other.Layout == this.Layout || other.Layout == layoutAll {
174174
if isLayoutCustom(this.Layout) {
175175
w.w1 += weightcustomLayout
176176
w.w2 = weight2Group2

tpl/tplimpl/templatestore.go

+10
Original file line numberDiff line numberDiff line change
@@ -711,6 +711,7 @@ func (s *TemplateStore) findBestMatchWalkPath(q TemplateQuery, k1 string, slashC
711711
}
712712

713713
weight := s.dh.compareDescriptors(q.Category, q.Desc, k.d)
714+
714715
weight.distance = distance
715716

716717
if best.isBetter(weight, vv) {
@@ -1734,6 +1735,15 @@ func (best *bestMatch) isBetter(w weight, ti *TemplInfo) bool {
17341735
}
17351736

17361737
if w.isEqualWeights(best.w) {
1738+
// Tie breakers.
1739+
if w.distance < best.w.distance {
1740+
return true
1741+
}
1742+
1743+
if ti.D.Layout != "" && best.desc.Layout != "" {
1744+
return ti.D.Layout != layoutAll
1745+
}
1746+
17371747
return w.distance < best.w.distance || ti.PathInfo.Path() < best.templ.PathInfo.Path()
17381748
}
17391749

tpl/tplimpl/templatestore_integration_test.go

+52
Original file line numberDiff line numberDiff line change
@@ -769,6 +769,37 @@ All.
769769
b.AssertFileContent("public/index.html", "All.")
770770
}
771771

772+
func TestLayoutAllNested(t *testing.T) {
773+
t.Parallel()
774+
775+
files := `
776+
-- hugo.toml --
777+
disableKinds = ['rss','sitemap','taxonomy','term']
778+
-- content/s1/p1.md --
779+
---
780+
title: p1
781+
---
782+
-- content/s2/p2.md --
783+
---
784+
title: p2
785+
---
786+
-- layouts/single.html --
787+
layouts/single.html
788+
-- layouts/list.html --
789+
layouts/list.html
790+
-- layouts/s1/all.html --
791+
layouts/s1/all.html
792+
`
793+
794+
b := hugolib.Test(t, files)
795+
796+
b.AssertFileContent("public/index.html", "layouts/list.html")
797+
b.AssertFileContent("public/s1/index.html", "layouts/s1/all.html")
798+
b.AssertFileContent("public/s1/p1/index.html", "layouts/s1/all.html")
799+
b.AssertFileContent("public/s2/index.html", "layouts/list.html")
800+
b.AssertFileContent("public/s2/p2/index.html", "layouts/single.html")
801+
}
802+
772803
func TestPartialHTML(t *testing.T) {
773804
t.Parallel()
774805

@@ -788,3 +819,24 @@ func TestPartialHTML(t *testing.T) {
788819

789820
b.AssertFileContent("public/index.html", "<link rel=\"stylesheet\" href=\"/css/style.css\">")
790821
}
822+
823+
// Issue #13515
824+
func TestPrintPathWarningOnDotRemoval(t *testing.T) {
825+
t.Parallel()
826+
827+
files := `
828+
-- hugo.toml --
829+
baseURL = "https://example.com"
830+
printPathWarnings = true
831+
-- content/v0.124.0.md --
832+
-- content/v0.123.0.md --
833+
-- layouts/all.html --
834+
All.
835+
-- layouts/_default/single.html --
836+
{{ .Title }}|
837+
`
838+
839+
b := hugolib.Test(t, files, hugolib.TestOptWarn())
840+
841+
b.AssertLogContains("Duplicate content path")
842+
}

0 commit comments

Comments
 (0)