Preamble and Background Story
Most of this thread was originally posted here. Another forum member suggested that I cut out my little “ah-ha” moment from my original support request thread and publish it to help others understand Hugo Context a bit better, with special attention to the use of the .
“dot” and $
“dollar” (not to be mistaken for the dollar sign used in variable assignments in templates, {{ $someVar := "some text" }}
.
I had a hard time understanding this subject until:
- I viewed a video called, “A Crash Course on Go Templates” (link follows) - the video is 20-ish minutes but is well explained.
- The presenter has a very good explanation of the difference between the “.” (“dot”) and “$” (“dollar”) symbols as used within Hugo/Go Templates: A Crash Course on Go Templates: time code = 13min/10sec. and
- Took my time to read through the Golang documentation for the
text/template
package that Hugo uses for handling template parsing and variable injection into templates. This documentation is about a 10-30 minute read (depending upon your degree of programming experience and experience with template languages in other languages/frameworks).- PS: A side benefit to reading the
text/template
package documentation I link to above is that it also explains the use of the “-” dash within “{{}}” curly braces like so:{{- /* template action and pipeline are in here */ -}}
. Gist: they tell the Go template parser totrim
whitespace from either/both before/after the template “action/command/pipeline”. - PPS: The terms I mention in the previous point, “action”, “command” and “pipeline” are critical to understanding how Go (and therefore Hugo) templates function. Again, I highly recommend you read the
text/template
documentation page linked to above.
- PS: A side benefit to reading the
Up until now, I simply didn’t understand Hugo templates and the felt a bit like obscure magic to me. I thought that templates are a Hugo construct (yeah - post-facto, I realise that the Hugo documentation is VERY clear about the fact that Hugo uses the html/template
and text/template
packages as stated on the "Templating page in the Templates section in the documentation website). I can’t stress this enough but, just one last time (cause I too kept tripping up on the syntax used within the {{}}
double-curly-braces in templates), I fervently and strongly suggest that anyone new to Hugo (even if you just simply want to get a micro-website up and running in minutes) go over the two resources listed above.
Alright… on to the actual tip/trick post content…
What are the .
(dot) and $
(dollar) symbols used for in Hugo Templates?
BOTH .
and $
(NOTE: just $
, the dollar sign on its own and not $someVar
) refer to the context variable that is passed into a given template. The difference is, the .
can change what it’s pointing/referring to within a template based upon whether it is being used in EITHER a with
or range
“action”. For example, the value that .
is pointing to can change within with
and range
template actions. On the other hand, the $
symbol ALWAYS refers to the ORIGINAL context that was passed into a template and it never changes.
Examples:
file: layouts/_default/baseof.html
has calls a “partial” with the file name, “partials/some-partial.html” like so:
{{- /* file: layouts/_default/baseof.html */ -}}
{{ $myFullName := slice "Abraa" "Cadabra" "Dobrinda" }}
{{ partial "some-partial.html" $myFullName }}
then, within partials/some-partial.html
{{- /* `.` refers to the slice, `$myFullName` that was passed into the partial template. */ -}}
{{ delimit . " " }}<br>{{- /* Outputs "Abraa Cadabra Dobrinda" */ -}}
<!-- `$` ALSO refers to the slice, `$myFullName` that was passed into the partial template. */ -}}
{{ delimit $ " " }}<br>{{- /* Outputs the same as `.` "Abraa Cadabra Dobrinda" */ -}}
{{ range . }}
{{- /*
In here, the `.` is referring to each individual element that the slice $myFullName has in it.
Thus, it will render "Abraa" then "Cadabra" then "Dobrinda" individually. NOTE: here, the `.` "dot"
context IS NO LONGER A SLICE and thus, cannot be used with the "collections.Delimit" function.
*/ -}}
{{ . }}<br>
{{- /*
Conversely, the `$` STILL refers to the original/"root level context" that was passed in, namely:
$myFullName. Thus, it will render "Abraa Cadabra Dobrinda" as a full string for every iteration
of the range's loop.
*/ -}}
{{ delimit $ " " }}<br>
{{ end}}
So the total output of of layouts/some-partial.html
should look something like this:
Abraa Cadabra Dobrinda<br>
Abraa Cadabra Dobrinda<br>
Abraa<br>
Abraa Cadabra Dobrinda<br>
Cadabra<br>
Abraa Cadabra Dobrinda<br>
Dobrinda<br>
Abraa Cadabra Dobrinda<br>
Cheers!