Leaf Bundle Resources in Templates

Okay, I can’t figure this out.

I can get leaf bundle resources with a markdown render hook, but not with a template file. What am I doing wrong? I can’t seem to figure it out.

Here is the code that I’ve got, this is in layouts/partials/blog/blog-header.html

{{ $feature := .Page.Resources.GetMatch (printf "%s" (index .Params.images 0)) }}
{{ $author := index .Site.Data.authors .Params.author }}

<section class="blog-splash blog-splash-full" style="background-image:linear-gradient(rgba(0, 0, 0, 0.6), rgba(0, 0, 0, 0.6)), url('{{ ($feature.Resize "1200x q65 webp").RelPermalink }}');">

	<div class="post-meta">
		<img src="{{ ((resources.Get $author.avatar).Resize "75x webp").RelPermalink }}">

		<span>{{ $author.name }}</span>

		<span>&nbsp;&middot;&nbsp;</span>

		<span><i class="fa-light fa-calendar-clock"></i>{{ (.Params.Date).Format "January 2, 2006 at 2:00" }}</span>
	</div>

 	<h1>{{ .Title }}</h1>
	{{ with .Params.description }}
		<h2 class="h4">{{ . }}</h2>
	{{ end }}
</section>

Mind you, if I take out the $feature bits, everything works. So I don’t understand why I can pull the images inside the post from the leaf bundle, using the same logic (!!), but can’t pull the “featured image”.

Error

Rebuild failed:

Failed to render pages: render of "page" failed: "D:\Sites\rsdc\layouts\_default\about.html:4:144": execute of template failed: template: _default/about.html:4:4: executing "main" at <partial "blog/post-header.html" .>: error calling partial: "D:\Sites\rsdc\layouts\partials\blog\post-header.html:4:144": execute of template failed: template: partials/blog/post-header.html:4:144: executing "partials/blog/post-header.html" at <$feature.Resize>: nil pointer evaluating resource.Resource.Resize
2
3
4
5
6
	{{ $me := (resources.Get "images/me.jpg").Resize "450x webp 85q" }}

	{{ partial "blog/post-header.html" . }}
	
	<section class="about-me">
hugo v0.91.2-1798BD3F+extended windows/amd64 BuildDate=2021-12-23T15:33:34Z VendorInfo=gohugoio

Reload Page

Here’s my repo: GitHub - bootyocean18/rsdc: My New Website

Here’s the latest working version, where I don’t have things in leaf bundles (the effect I’m trying to acheive): https://www.remysheppard.com

You need to understand where you are at with your dot . - context. With a render hook you are “inside” of the current parsed layout with its content right available to the renderhook. What I am trying to say is that .Page in a render hook will always point to the currently parsed page the renderhook is in.

Your template or layout file however is somewhere in a context (where you load it) and it could be that there is no .Page available or the dot is the page itself. That depends on your layouting.

Untested, but if I remember it right you could just do $.Page, but I don’t know if that would change things in the render hook. As those are typically two separate files keep the .Page there and in the error-layout-file try working with $.Page.

From the limited templates you posted I would say in your layout (not in the renderhook) it should be something like this:

{{ $feature := .Resources.GetMatch (printf "%s" (index .Params.images 0)) }}

PS: I just saw you linked your repo. The code above should work. Remove the .Page from the partial. Look inside of your template, you are already inside of the “page context” (or the .Content would not work some lines later).

The ERROR message is clear, the resources not found <nil>

Rebuild failed: Failed to render pages: render of “page” failed: “D:\Sites\rsdc\layouts_default\about.html:4:144”: execute of template failed: template: _default/about.html:4:4: executing “main” at <partial “blog/post-header.html” .>: error calling partial: “D:\Sites\rsdc\layouts\partials\blog\post-header.html:4:144”: execute of template failed: template: partials/blog/post-header.html:4:144: executing “partials/blog/post-header.html” at <$feature.Resize>: nil pointer evaluating resource.Resource.Resize

{{ $feature := .Page.Resources.GetMatch (printf "%s" "feature") }}
{{ $author := index .Site.Data.authors .Params.author }}

{{ with $feature }}
 IMG_FOUND_DO_THIS
{{ else }}
 IMG_NOT_FOUND_DO_THIS
{{ end }}

In your render-image.html, you check if image exists.

https://github.com/bootyocean18/rsdc/blob/main/layouts/_default/_markup/render-image.html#L4

I tried that and the error message is the exact same. I also tried $.Page to no avail.

I’m beating my head into the wall.

Yeah, I know what the problem is.
Obviously the resources isn’t found.

I’m asking Why isn’t the resource found?

It’s found in the render hook, why isn’t it found in the template when the code is the same?

The code isn’t the same.

I cloned your repository and built your site.

Problem 1

https://github.com/bootyocean18/rsdc/blob/main/layouts/partials/blog/post-header.html#L1

This isn’t going to match anything. Change this:

{{ $feature := .Page.Resources.GetMatch "(printf "%s" "feature")" }}

To this:

{{ $feature := .Page.Resources.GetMatch "feature.*" }}

Problem 2

After fixing Problem 1, the build still throws an error:

failed to render pages: render of “page” failed: “/home/jmooring/temp/rsdc/layouts/_default/about.html:4:144”: execute of template failed: template: _default/about.html:4:4: executing “main” at <partial “blog/post-header.html” .>: error calling partial: “/home/jmooring/temp/rsdc/layouts/partials/blog/post-header.html:4:144”: execute of template failed: template: partials/blog/post-header.html:4:144: executing “partials/blog/post-header.html” at <$feature.Resize>: nil pointer evaluating resource.Resource.Resize

This occurs because content/about.md:

  • Is not a page bundle, and consequently
  • Has no resources, and consequently
  • Does not a have a feature image

You need to code defensively, keeping in mind that one or more content pages rendered by a given template may not have a particular resource. For example:

{{ with $feature := .Page.Resources.GetMatch "feature.*" }}
  ...
{{ end }}

Problem 3

After fixing Problem 1, the build throws this warning:

WARNING: calling IsSet with unsupported type “invalid” () will always return false.

https://github.com/bootyocean18/rsdc/blob/main/layouts/partials/welcomments/comments.html#L15

This warning is thrown because there is not a data file named “welcomments” in the project’s data directory.

1 Like

Excellent, thank you!

I hope one day, truly, to be as good at this.

the third problem is not something I can fix, as it isn’t something I can control. I can only let the Welcomments folks know what is going on.

I’ll make a new topic, if you want, but your fix has created an interesting problem: Everything is now scoped to the featured image.

This results in no post data being displayed, only image data.

EDIT: Never mind, I fixed this quickly. I realized I was scoping the entire partial to the {{ with [...] }}, so now my code works, and looks like this:

{{ $author := index .Site.Data.authors .Params.author }}
{{ $feature := .Page.Resources.GetMatch "feature.*" }}

<section class="blog-splash blog-splash-full" {{ with $feature }}style="background-image:linear-gradient(rgba(0, 0, 0, 0.6), rgba(0, 0, 0, 0.6)), url('{{ (.Resize "1200x q65 webp").RelPermalink }}');"{{ end }}>

	<div class="post-meta">
		<img src="{{ ((resources.Get $author.avatar).Resize "75x webp").RelPermalink }}">

		<span>{{ $author.name }}</span>

		<span>&nbsp;&middot;&nbsp;</span>

		<span><i class="fa-light fa-calendar-clock"></i>{{ (.Params.Date).Format "January 2, 2006 at 2:00" }}</span>
	</div>

 	<h1>{{ .Title }}</h1>
	{{ with .Params.description }}
		<h2 class="h4">{{ . }}</h2>
	{{ end }}
</section>

This was intended to be an example of defensive coding, not code that you copy/paste into your templates.

What you might consider:

  1. Creating a default “feature” image in the assets directory.
  2. Use the resources.Get method to get the default feature image as a resource
  3. Then check to see if the page has a feature image with .Resources.Get and use that instead

Open another topic if you continue to have problems.

1 Like

Absolutely, thank you.

EDIT

Following your advice this morning, @jmooring

The first thing I do in my template is initialize the $feature variable to point to a default value:

{{ $feature := resources.Get "images/feature.jpg" }}

Then, elsewhere as needed, I have this bit to modify $feature:

{{ with .Page.Resources.GetMatch "feature.*" }}
	{{ $feature = . }}
{{ end }}

Works like a dream. Thank you again for the help.

This topic was automatically closed 2 days after the last reply. New replies are no longer allowed.