Skip to content

Commit 7ef7d4a

Browse files
committed
Fix some RenderShortcodes error cases
This issue fixes two cases where `{{__hugo_ctx` artifacts were left in the rendered output: 1. Inclusion when `.RenderShortcodes` is wrapped in HTML. 2. Inclusion of Markdown file without a trailing newline in some cases. Closes gohugoio#12854 Updates gohugoio#12998
1 parent 72352f2 commit 7ef7d4a

14 files changed

+292
-141
lines changed

common/constants/constants.go

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ const (
2121
ErrRemoteGetCSV = "error-remote-getcsv"
2222

2323
WarnFrontMatterParamsOverrides = "warning-frontmatter-params-overrides"
24+
WarnRenderShortcodesInHTML = "warning-rendershortcodes-in-html"
2425
)
2526

2627
// Field/method names with special meaning.

hugolib/collections_test.go

+8-8
Original file line numberDiff line numberDiff line change
@@ -71,9 +71,9 @@ tags_weight: %d
7171
{{ $pageGroups := slice $cool $blue }}
7272
{{ $weighted := slice $wp1 $wp2 }}
7373
74-
{{ printf "pages:%d:%T:%v/%v" (len $pages) $pages (index $pages 0) (index $pages 1) }}
75-
{{ printf "pageGroups:%d:%T:%v/%v" (len $pageGroups) $pageGroups (index (index $pageGroups 0).Pages 0) (index (index $pageGroups 1).Pages 0)}}
76-
{{ printf "weightedPages:%d::%T:%v" (len $weighted) $weighted $weighted | safeHTML }}
74+
{{ printf "pages:%d:%T:%s|%s" (len $pages) $pages (index $pages 0).Path (index $pages 1).Path }}
75+
{{ printf "pageGroups:%d:%T:%s|%s" (len $pageGroups) $pageGroups (index (index $pageGroups 0).Pages 0).Path (index (index $pageGroups 1).Pages 0).Path}}
76+
{{ printf "weightedPages:%d:%T" (len $weighted) $weighted | safeHTML }}
7777
7878
`)
7979
b.CreateSites().Build(BuildCfg{})
@@ -82,9 +82,9 @@ tags_weight: %d
8282
c.Assert(len(b.H.Sites[0].RegularPages()), qt.Equals, 2)
8383

8484
b.AssertFileContent("public/index.html",
85-
"pages:2:page.Pages:Page(/page1)/Page(/page2)",
86-
"pageGroups:2:page.PagesGroup:Page(/page1)/Page(/page2)",
87-
`weightedPages:2::page.WeightedPages:[WeightedPage(10,"Page") WeightedPage(20,"Page")]`)
85+
"pages:2:page.Pages:/page1|/page2",
86+
"pageGroups:2:page.PagesGroup:/page1|/page2",
87+
`weightedPages:2:page.WeightedPages`)
8888
}
8989

9090
func TestUnionFunc(t *testing.T) {
@@ -189,7 +189,7 @@ tags_weight: %d
189189
{{ $appendStrings := slice "a" "b" | append "c" "d" "e" }}
190190
{{ $appendStringsSlice := slice "a" "b" "c" | append (slice "c" "d") }}
191191
192-
{{ printf "pages:%d:%T:%v/%v" (len $pages) $pages (index $pages 0) (index $pages 1) }}
192+
{{ printf "pages:%d:%T:%s|%s" (len $pages) $pages (index $pages 0).Path (index $pages 1).Path }}
193193
{{ printf "appendPages:%d:%T:%v/%v" (len $appendPages) $appendPages (index $appendPages 0).Kind (index $appendPages 8).Kind }}
194194
{{ printf "appendStrings:%T:%v" $appendStrings $appendStrings }}
195195
{{ printf "appendStringsSlice:%T:%v" $appendStringsSlice $appendStringsSlice }}
@@ -207,7 +207,7 @@ tags_weight: %d
207207
c.Assert(len(b.H.Sites[0].RegularPages()), qt.Equals, 2)
208208

209209
b.AssertFileContent("public/index.html",
210-
"pages:2:page.Pages:Page(/page2)/Page(/page1)",
210+
"pages:2:page.Pages:/page2|/page1",
211211
"appendPages:9:page.Pages:home/page",
212212
"appendStrings:[]string:[a b c d e]",
213213
"appendStringsSlice:[]string:[a b c c d]",

hugolib/integrationtest_builder.go

+23
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ package hugolib
22

33
import (
44
"bytes"
5+
"context"
56
"encoding/base64"
67
"errors"
78
"fmt"
@@ -32,6 +33,7 @@ import (
3233
"github.com/gohugoio/hugo/htesting"
3334
"github.com/gohugoio/hugo/hugofs"
3435
"github.com/spf13/afero"
36+
"github.com/spf13/cast"
3537
"golang.org/x/text/unicode/norm"
3638
"golang.org/x/tools/txtar"
3739
)
@@ -294,6 +296,12 @@ func (s *IntegrationTestBuilder) AssertFileContent(filename string, matches ...s
294296
}
295297
}
296298

299+
func (s *IntegrationTestBuilder) AssertFileContentEquals(filename string, match string) {
300+
s.Helper()
301+
content := s.FileContent(filename)
302+
s.Assert(content, qt.Equals, match, qt.Commentf(match))
303+
}
304+
297305
func (s *IntegrationTestBuilder) AssertFileContentExact(filename string, matches ...string) {
298306
s.Helper()
299307
content := s.FileContent(filename)
@@ -302,6 +310,16 @@ func (s *IntegrationTestBuilder) AssertFileContentExact(filename string, matches
302310
}
303311
}
304312

313+
func (s *IntegrationTestBuilder) AssertNoRenderShortcodesArtifacts() {
314+
s.Helper()
315+
for _, p := range s.H.Pages() {
316+
content, err := p.Content(context.Background())
317+
s.Assert(err, qt.IsNil)
318+
comment := qt.Commentf("Page: %s\n%s", p.Path(), content)
319+
s.Assert(strings.Contains(cast.ToString(content), "__hugo_ctx"), qt.IsFalse, comment)
320+
}
321+
}
322+
305323
func (s *IntegrationTestBuilder) AssertPublishDir(matches ...string) {
306324
s.AssertFs(s.fs.PublishDir, matches...)
307325
}
@@ -835,6 +853,11 @@ type IntegrationTestConfig struct {
835853

836854
// The files to use on txtar format, see
837855
// https://pkg.go.dev/golang.org/x/exp/cmd/txtar
856+
// There are some conentions used in this test setup.
857+
// - §§§ can be used to wrap code fences.
858+
// - §§ can be used to wrap multiline strings.
859+
// - filenames prefixed with sourcefilename: will be read from the file system relative to the current dir.
860+
// - filenames with a .png or .jpg extension will be treated as binary and base64 decoded.
838861
TxtarString string
839862

840863
// COnfig to use as the base. We will also read the config from the txtar.

hugolib/menu_test.go

+18-106
Original file line numberDiff line numberDiff line change
@@ -105,94 +105,6 @@ Menu Main: {{ partial "menu.html" (dict "page" . "menu" "main") }}`,
105105
"/sect3/|Sect3s|Sect3s|0|-|-|")
106106
}
107107

108-
// related issue #7594
109-
func TestMenusSort(t *testing.T) {
110-
b := newTestSitesBuilder(t).WithSimpleConfigFile()
111-
112-
b.WithTemplatesAdded("index.html", `
113-
{{ range $k, $v := .Site.Menus.main }}
114-
Default1|{{ $k }}|{{ $v.Weight }}|{{ $v.Name }}|{{ .URL }}|{{ $v.Page }}{{ end }}
115-
{{ range $k, $v := .Site.Menus.main.ByWeight }}
116-
ByWeight|{{ $k }}|{{ $v.Weight }}|{{ $v.Name }}|{{ .URL }}|{{ $v.Page }}{{ end }}
117-
{{ range $k, $v := (.Site.Menus.main.ByWeight).Reverse }}
118-
Reverse|{{ $k }}|{{ $v.Weight }}|{{ $v.Name }}|{{ .URL }}|{{ $v.Page }}{{ end }}
119-
{{ range $k, $v := .Site.Menus.main }}
120-
Default2|{{ $k }}|{{ $v.Weight }}|{{ $v.Name }}|{{ .URL }}|{{ $v.Page }}{{ end }}
121-
{{ range $k, $v := .Site.Menus.main.ByWeight }}
122-
ByWeight|{{ $k }}|{{ $v.Weight }}|{{ $v.Name }}|{{ .URL }}|{{ $v.Page }}{{ end }}
123-
{{ range $k, $v := .Site.Menus.main }}
124-
Default3|{{ $k }}|{{ $v.Weight }}|{{ $v.Name }}|{{ .URL }}|{{ $v.Page }}{{ end }}
125-
`)
126-
127-
b.WithContent("_index.md", `
128-
---
129-
title: Home
130-
menu:
131-
main:
132-
weight: 100
133-
---`)
134-
135-
b.WithContent("blog/A.md", `
136-
---
137-
title: "A"
138-
menu:
139-
main:
140-
weight: 10
141-
---
142-
`)
143-
144-
b.WithContent("blog/B.md", `
145-
---
146-
title: "B"
147-
menu:
148-
main:
149-
weight: 20
150-
---
151-
`)
152-
b.WithContent("blog/C.md", `
153-
---
154-
title: "C"
155-
menu:
156-
main:
157-
weight: 30
158-
---
159-
`)
160-
161-
b.Build(BuildCfg{})
162-
163-
b.AssertFileContent("public/index.html",
164-
`Default1|0|10|A|/blog/a/|Page(/blog/a)
165-
Default1|1|20|B|/blog/b/|Page(/blog/b)
166-
Default1|2|30|C|/blog/c/|Page(/blog/c)
167-
Default1|3|100|Home|/|Page(/)
168-
169-
ByWeight|0|10|A|/blog/a/|Page(/blog/a)
170-
ByWeight|1|20|B|/blog/b/|Page(/blog/b)
171-
ByWeight|2|30|C|/blog/c/|Page(/blog/c)
172-
ByWeight|3|100|Home|/|Page(/)
173-
174-
Reverse|0|100|Home|/|Page(/)
175-
Reverse|1|30|C|/blog/c/|Page(/blog/c)
176-
Reverse|2|20|B|/blog/b/|Page(/blog/b)
177-
Reverse|3|10|A|/blog/a/|Page(/blog/a)
178-
179-
Default2|0|10|A|/blog/a/|Page(/blog/a)
180-
Default2|1|20|B|/blog/b/|Page(/blog/b)
181-
Default2|2|30|C|/blog/c/|Page(/blog/c)
182-
Default2|3|100|Home|/|Page(/)
183-
184-
ByWeight|0|10|A|/blog/a/|Page(/blog/a)
185-
ByWeight|1|20|B|/blog/b/|Page(/blog/b)
186-
ByWeight|2|30|C|/blog/c/|Page(/blog/c)
187-
ByWeight|3|100|Home|/|Page(/)
188-
189-
Default3|0|10|A|/blog/a/|Page(/blog/a)
190-
Default3|1|20|B|/blog/b/|Page(/blog/b)
191-
Default3|2|30|C|/blog/c/|Page(/blog/c)
192-
Default3|3|100|Home|/|Page(/)`,
193-
)
194-
}
195-
196108
func TestMenusFrontMatter(t *testing.T) {
197109
b := newTestSitesBuilder(t).WithSimpleConfigFile()
198110

@@ -437,8 +349,8 @@ url = "/blog/post3"
437349
commonTempl := `
438350
Main: {{ len .Site.Menus.main }}
439351
{{ range .Site.Menus.main }}
440-
{{ .Title }}|HasMenuCurrent: {{ $.HasMenuCurrent "main" . }}|Page: {{ .Page }}
441-
{{ .Title }}|IsMenuCurrent: {{ $.IsMenuCurrent "main" . }}|Page: {{ .Page }}
352+
{{ .Title }}|HasMenuCurrent: {{ $.HasMenuCurrent "main" . }}|Page: {{ .Page.Path }}
353+
{{ .Title }}|IsMenuCurrent: {{ $.IsMenuCurrent "main" . }}|Page: {{ .Page.Path }}
442354
{{ end }}
443355
`
444356

@@ -494,34 +406,34 @@ title: "Contact: With No Menu Defined"
494406

495407
b.AssertFileContent("public/index.html", `
496408
Main: 5
497-
Home|HasMenuCurrent: false|Page: Page(/)
498-
Blog|HasMenuCurrent: false|Page: Page(/blog)
499-
My Post 2: With Menu Defined|HasMenuCurrent: false|Page: Page(/blog/post2)
500-
My Post 3|HasMenuCurrent: false|Page: Page(/blog/post3)
501-
Contact Us|HasMenuCurrent: false|Page: Page(/contact)
409+
Home|HasMenuCurrent: false|Page: /
410+
Blog|HasMenuCurrent: false|Page: /blog
411+
My Post 2: With Menu Defined|HasMenuCurrent: false|Page: /blog/post2
412+
My Post 3|HasMenuCurrent: false|Page: /blog/post3
413+
Contact Us|HasMenuCurrent: false|Page: /contact
502414
`)
503415

504416
b.AssertFileContent("public/blog/post1/index.html", `
505-
Home|HasMenuCurrent: false|Page: Page(/)
506-
Blog|HasMenuCurrent: true|Page: Page(/blog)
417+
Home|HasMenuCurrent: false|Page: /
418+
Blog|HasMenuCurrent: true|Page: /blog
507419
`)
508420

509421
b.AssertFileContent("public/blog/post2/index.html", `
510-
Home|HasMenuCurrent: false|Page: Page(/)
511-
Blog|HasMenuCurrent: true|Page: Page(/blog)
512-
Blog|IsMenuCurrent: false|Page: Page(/blog)
422+
Home|HasMenuCurrent: false|Page: /
423+
Blog|HasMenuCurrent: true|Page: /blog
424+
Blog|IsMenuCurrent: false|Page: /blog
513425
`)
514426

515427
b.AssertFileContent("public/blog/post3/index.html", `
516-
Home|HasMenuCurrent: false|Page: Page(/)
517-
Blog|HasMenuCurrent: true|Page: Page(/blog)
428+
Home|HasMenuCurrent: false|Page: /
429+
Blog|HasMenuCurrent: true|Page: /blog
518430
`)
519431

520432
b.AssertFileContent("public/contact/index.html", `
521-
Contact Us|HasMenuCurrent: false|Page: Page(/contact)
522-
Contact Us|IsMenuCurrent: true|Page: Page(/contact)
523-
Blog|HasMenuCurrent: false|Page: Page(/blog)
524-
Blog|IsMenuCurrent: false|Page: Page(/blog)
433+
Contact Us|HasMenuCurrent: false|Page: /contact
434+
Contact Us|IsMenuCurrent: true|Page: /contact
435+
Blog|HasMenuCurrent: false|Page: /blog
436+
Blog|IsMenuCurrent: false|Page: /blog
525437
`)
526438
}
527439

hugolib/page.go

+13-1
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ import (
1717
"context"
1818
"fmt"
1919
"strconv"
20+
"strings"
2021
"sync"
2122
"sync/atomic"
2223

@@ -358,7 +359,18 @@ func (p *pageState) Site() page.Site {
358359
}
359360

360361
func (p *pageState) String() string {
361-
return fmt.Sprintf("Page(%s)", p.Path())
362+
var sb strings.Builder
363+
if p.File() != nil {
364+
sb.WriteString(p.File().Filename())
365+
if p.File().IsContentAdapter() {
366+
// Also include the path.
367+
sb.WriteString(":")
368+
sb.WriteString(p.Path())
369+
}
370+
} else {
371+
sb.WriteString(p.Path())
372+
}
373+
return sb.String()
362374
}
363375

364376
// IsTranslated returns whether this content file is translated to

0 commit comments

Comments
 (0)