Is it possible to programatically include resources in a slice?

I don’t need to include all scripts in every page, to save resources I am trying to do something like this, is this possible?:

{{ if and .IsPage .Params.toc }}
    {{ $toc := resources.Get "js/toc.js" -}}
    {{ $allScripts = $allScripts | append $toc }}
{{ end }}

{{ if and .IsPage .Params.copy }}
    {{ $codeCopy := resources.Get "js/code-copy.js" -}}
    {{ $allScripts = $allScripts | append $codeCopy }}
{{ end }}

{{ $script := slice $allScripts | resources.Concat "js/bundle.js" | minify | fingerprint -}}
<script async media="screen" src="{{ $script.Permalink }}" integrity="{{ $script.Data.Integrity }}" crossorigin="anonymous"></script>
1 Like

First of all welcome to forum, and congrats on your first post!

The code you have written looks good, though you will need to define $allScripts as an empty slice firsthand. Also, no need to use slice when concatenating the resources. So your code would become:

{{ $allScripts := slice }}
{{ if and .IsPage .Params.toc }}
    {{ $toc := resources.Get "js/toc.js" -}}
    {{ $allScripts = $allScripts | append $toc }}
{{ end }}

{{ if and .IsPage .Params.copy }}
    {{ $codeCopy := resources.Get "js/code-copy.js" -}}
    {{ $allScripts = $allScripts | append $codeCopy }}
{{ end }}

{{ $script := $allScripts | resources.Concat "js/bundle.js" | minify | fingerprint -}}
<script async media="screen" src="{{ $script.Permalink }}" integrity="{{ $script.Data.Integrity }}" crossorigin="anonymous"></script>

I haven’t tested it, but should work in theory.

Quick tip:
The code you have written can be stored in partial under say layouts/partials/resources.html. And, can be included in the layouts you want with {{ partial "resources.html" . }}

3 Likes

Google and other page load speed sites will suggest you to merge multiple js into one. The performance of a bigger js file will be better than several smaller js connection. Just enable HTTP compression and file caching.

@SanmayJoshi I tried that, but I get the following error:

execute of template failed: template: _default/single.html:63:51: executing "_default/single.html" at <resources.Concat>: error calling Concat: slice []resource.Resources not supported in concat

I have used it in my project, here. Feel free to have a look. Will update this answer with details tomorrow, gotta sleep :sweat_smile:.

Strange, with your snippet I get the same error :confused:.

May you share what version of Hugo you are using? You can check it with hugo version.

hugo 0.75.1-1

Is it extended version? If it is, not sure what the problem is :slightly_frowning_face:

Edit:
You may further see,

  1. [SOLVED] Hugo v0.55.6 error calling ressources.Concat
  2. resources.Concat with js - slice interface not supported in concat

I thought the extended version was just for sass support. The links you linked didn’t seem to help either.

I would recommend using extended version of Hugo whenever you can (i.e. if you have 64 bit OS). If you aren’t currently using extended version of Hugo, I would suggest to give it a try.

Also, what OS are you using?

5.8.13-arch1-1, Arch linux. Comes with extended in the pacman repos.

I have ran out of ideas :no_mouth:

Some really experienced folks like @davidsneighbour @alexandros @pointyfar may be able to help!

@NullSense, it will be easier to help you if we could see your code in a repo somewhere we can clone. @SanmayJoshi has provided good resources. We cannot help if we cannot replicate what you are doing.

2 Likes

@pointyfar @SanmayJoshi please find the code here, it’s a baseof.html file:

Please provide your whole site code. We cannot run just the baseof.html file on its own.

Given this setup:

assets/
├── one.js   // console.log('one')
├── three.js // console.log('three')
└── two.js   // console.log('two')
{{ $one := resources.Get "one.js"}}
{{ $two := resources.Get "two.js"}}
{{ $three := resources.Get "three.js"}}
{{ $concat := slice $one $two $three | resources.Concat "js/scripts.js" | minify | fingerprint }}
<script src="{{ $concat.Permalink }}"></script>

This works, and produces:

/js/scripts.min.[hash].js
console.log('one');console.log('two');console.log('three')

You are getting an error, so clearly something is wrong somewhere. But we cannot help you if we cannot reproduce it ourselves.

Please read Requesting Help to see how to make it easier for us to help you.

1 Like

@pointyfar sorry, here is the full repository https://github.com/NullSense/pub_blog/

You need to npm install, then hugo server -D --watch --gc should work.

It works without errors for me.

Tested with:

Hugo Static Site Generator v0.75.1-A4A7BAB7 linux/amd64 BuildDate: 2020-09-15T06:46:04Z
Hugo Static Site Generator v0.75.1-A4A7BAB7/extended linux/amd64 BuildDate: 2020-09-15T06:57:20Z
Hugo Static Site Generator v0.76.2-207913F3 linux/amd64 BuildDate: 2020-10-07T08:59:22Z
Hugo Static Site Generator v0.76.2-207913F3/extended linux/amd64 BuildDate: 2020-10-07T09:09:05Z

Can you try and clone a fresh copy of your repo, and run Hugo there?

Ah sorry @pointyfar I didn’t commit the changes, can you pull and try now?

This line should be:

{{ $script := $allScripts | resources.Concat "js/main-bundle.js" | minify | fingerprint -}}