If a post is referred to in other posts, then all those posts are creating backlinks to that first post.
As of writing this (# 8077) to track this feature request.
), Hugo doesn’t have a built-in way to generate a list of such backlinks, though there’s an open issue (One way to gather a list of backlinks to a post is to find out that post’s relative or absolute permalink, and search for the occurrences of that link in all the other posts on the published site. The author of seds.nl: Export org-roam backlinks with Gohugo, Ben Mezger, uses this approach in his solution for creating backlinks in that post.
In this post, I am expanding upon that solution and refactoring it bit to fit my needs.
Without further ado, here is my version of the partial:
backlinks.html
partial #Save this partial to your site repo as
layouts/partials/backlinks.html
.
|
|
Add a call to this partial in your “single” layout’s template file,
which is typically layouts/_default/single.html
.
{{ partial "backlinks.html" (dict "page" .) }}
dict
or a dictionary with
keys page
and heading
.
page
key is required to pass the page context from where
the partial is called.heading
key is optional. This can be used by the user to
set the “Backlinks” heading differently. For example,
{{ partial "backlinks.html" (dict "page" . "heading" "<h4>Links to this note</h4>") }}
..File.BaseFileName
would be
just “index” for all the Leaf Bundles
If you follow this link and scroll to the bottom of that page, you
will see a “Backlinks” section auto-generated with the help of this
partial. This post will be linked there because I just referenced
that post here.
, and I use them heavily! Using .File.ContentBaseName
fixes
this problem. See 📖 Hugo File Variables for more
info. [Credit: @sjgknight]$path_base
variable is found
wrapped in characters like "
, /
, (
or )
.
$path_base
is ‘hello’, I don’t want its mere reference like
in this line to create a backlink on that ‘hello’ post!"hello"
(as in {{< relref "hello" >}}
), or /hello"
(as in {{< relref "/posts/hello" >}}
), or /hello)
(as in
[Hello](/hello)
) is found in the raw
Markdown content (.RawContent
).site.RegularPages
. See 📖 About site Pages variables for
more info. site.AllPages
includes all pages.. even the list
pages like section and taxonomy pages which, I believe, won’t
contain backlinks.findRE
in line 6 is slightly optimized
by quitting the search immediately as soon as the first match is
found.This partial works great for this site — adds only a few hundred milliseconds to the build time.
But it’s not an efficient solution. The partial is called in the single template where it searching for backlinks to the current page in all other regular pages, and the single template is evaluated for all the regular pages. So its \(O\) notation will be close to \(O(n^2)\) where \(n\) is the number of regular pages.
I have only about a hundred regular pages at the moment, but I can see
this partial taking a major chunk of the build time
The hugo --templateMetrics --templateMetricsHints
command prints a
table listing all the partials used in the build and how much time
each of them took. See 📖 Hugo Build Performance for more
info.
as the number of pages increase.
A built-in support for backlinks from Hugo (# 8077) would really help in this performance department.
]]>