Define one page param based on other params

I host all my images on Cloudflare Images. While this has huge advantages for serving responsive content, it also means URLs quickly become a bit complicated to handle, and in particular makes any sort of dynamic content generation awkward to achieve: I’ve got stuck trying to dynamically generate URLs within front matter, and would need some help for the following.

1. In my site front matter, I have the following:

[params]
 [...]
  # Sets the URL for images
  cloudflare_images = "https://[CLIENT_URL]/cdn-cgi/imagedelivery/[CLIENT_ID]/"

2. Then in each post, I have the following:

---
title: "Curabitur viverra, neque nec porttitor semper, sapien massa euismod erat, eget rutrum eros ligula sed nibh."
[...]
featured_image: "969a796-2fbc-451f-ba14-8f6e0276b000"
---

In posts, images are referenced (via shortcodes) by concatenating those two parameters, like so:

{{ .Site.Params.cloudflare_images }}{{ .Params.featured_image }}

What I would like to do is add the images parameter to each post’s front matter, and have it dynamically generated by combining the two above variables, in such a way that I can then use the images parameter in the Hugo Open Graph internal template.

So the post’s front matter would look like something similar to this (except this code doesn’t work!, obviously:

---
title: "Curabitur viverra, neque nec porttitor semper, sapien massa euismod erat, eget rutrum eros ligula sed nibh."
[...]
featured_image: "969a796-2fbc-451f-ba14-8f6e0276b000"
images : {{ .Site.Params.cloudflare_images }}{{ .Params.featured_image }}
---

Is it actually possible to define a front matter parameter dynamically in this way? I did try to see if I could do it with Pages Resources, but couldn’t find a way to make that work.

I don’t think you can no.

But what about adding it as a string in your featured_image key:

---
title: "Curabitur viverra, neque nec porttitor semper, sapien massa euismod erat, eget rutrum eros ligula sed nibh."
[...]
featured_image: " {cloudflare_domain}/969a796-2fbc-451f-ba14-8f6e0276b000"
---

Then when retrieving the featured_image

{{ with .Params.featured_image }}
  {{ $image := . }}
  {{ if in $image "{cloudflare_domain}" }}
     {{ $image = replace $image "{cloudflare_domain}" site.Params.cloudflare_images }}
  {{ end }}
  <img src="{{ $image }}" />
{{ end }}

Thank you for the suggestion.

Yes, obviously, you’re right: that would solve it, but was what I was keen to avoid, since that portion of the Cloudflare images is always the same.

So I was hoping there would be some way of having my cake and eating it: (1) only having to store Cloudflare Image ID in the featured_image param; and (2) being able to have the images param automatically generated. Adding any extra code wouldn’t be possible for my intended use which is to provide an images variable for the Hugo Open Graph template, since that is baked into Hugo—but a perfectly adequate solution is to use a shortcode with the code you suggested to generate the images parameter (which is used by Open Graph) for each page. Thank you!

You don’t need to use the built-in template. You can create a partial instead, using the built-in template as a starting point.

Yes, totally right: thank you for pointing me to that repository. I still think it’s a pity parameters can’t be manipulated in this way, but I can see why Hugo was deliberately designed for them to be ‘set in stone’ once and for all.

Alternate method

I like @regis’s answer. But I have an alternate approach where your frontmatter need not be dynamic. It is based on string substitution:

{{ if isset .Params "featured_image" }}
  {{ $icon := .Params.featured_image }}
  {{ $icon_url := printf "%s%s" .Site.Params.cloudflare_images $icon }}
  <img src="{{ $icon_url }}" />
{{end}}

Advantage

This approach allows you to get rid of {cloudflare_domain} in the frontmatter as well as in the template (head partial). Thus your frontmatter is more or less static where you have to define the name of image file only.

1 Like

Very neat indeed. Thank you very much.

1 Like

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