Relative Links within Template Data

How can I compute a “relative” link from a page to a resource? (rather than having links be site-relative)?

I have an odd use case: I am using Hugo to build “workbooks” that students download to their computers and run using a local web server. Sometimes, they don’t start the web server in the site root (for example, they might start it in the directory above - if they have a collection of workbooks).

For links, I can use relativeURLs - this works fine. I understand that this happens in a way specific to the links in the generated pages.

However: I have references to files that aren’t HTML links. For example, I pass parameters to scripts. If I just use “.RelPermalink”, I get a link relative to the domain route (which may not be the site root).

Is there a way to compute a relative link (using “..”) to a .RelPermalink within a template?

Here is an example (from a big messy page template)

        {{- $jsonfile := resources.Get "wb_localstore_save.json" -}}
        const WORKBOOK_CONFIG = {
            jsonFile: "{{ $jsonfile.RelPermalink }}",
        };

As expected, this puts a site relative link in jsonfile. I’d like it to be “../../file.json” rather than /json (as an example).

Thank you!

Mike

There’s nothing built-in. You might be able to cobble together a partial template that handles it. That would be relatively simple if the site-relative link were in the same branch as the current page, but going sideways would be a hassle.

Although I think this is a terrible idea in 99.9% of sites, you might look at the relativeURLs setting.

This might be a good candidate for a template function, though the use case is uncommon.

Function signature: urls.Relativize BASE TARGET where the parameters could be strings or (potentially) page references and resources.

{{ urls.Relativize "/a/b/c/" "/d/e/f.pdf" }} → ../../../d/e/f.pdf
{{ urls.Relativize . "/d/e/f.pdf" }}         → ../../../d/e/f.pdf

We’d probably use Go’s filepath.Rel function. If using strings you could pass in whatever you want, but when passing page references we’d limit it to pages within the same site (role + version + language).

Thank you!

This is a weird use case. I wouldn’t expect something like this to be built in.

The site does use relativeURL - which works well for the links in the HTML. But, it doesn’t fill in the strings in the data parts.

I think you are the one who explained it to me years ago, but as I understand it, relativeURLs is implemented as a post-process on the generated HTML.

<a href="{{resources.Get "wb_localstore_save.json"}}">json</a>

does correctly make a relative link.

My fallback is to make a link in the HTML and then have javascript read the URL from the page at viewing time. Ugly.

Or decide that this isn’t a problem worth fixing for my students. (just tell them they have to start the server in the workbook directory).

Yup… described here: https://gohugo.io/content-management/urls/#relative-urls

That sounds about right to me.

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