Hugo: ToCSS includePaths ignores paths from parent directory (../node_modules)

Created on 27 Aug 2019  ยท  8Comments  ยท  Source: gohugoio/hugo

Error

When running hugo, it fails with the following error:

hugo -D -s site server     
Building sites โ€ฆ ERROR 2019/08/27 16:56:32 error: failed to transform resource: SCSS processing failed: file "stdin", line 3, col 1: File to import not found or unreadable: bulma/bulma. 
Total in 13 ms
Error: Error building site: logged 1 error(s)

Project Structure (abridged)

project
โ”œโ”€โ”€ node_modules
โ”‚ย ย  โ””โ”€โ”€ bulma
โ”‚ย ย   ย ย  โ”œโ”€โ”€ bulma.sass
โ”‚ย ย   ย ย  โ””โ”€โ”€ sass
โ”‚    ย ย   ย ย  โ””โ”€โ”€ ...
โ”œโ”€โ”€ package.json
โ”œโ”€โ”€ package-lock.json
โ”œโ”€โ”€ README.md
โ””โ”€โ”€ site
    โ””โ”€โ”€ themes
        โ””โ”€โ”€ custom-theme
            โ”œโ”€โ”€ assets
            โ”‚ย ย  โ””โ”€โ”€ scss
            โ”‚ย ย      โ”œโ”€โ”€ main.scss
            โ”‚ย ย      โ””โ”€โ”€ variables.scss
            โ””โ”€โ”€ layouts
             ย ย  โ””โ”€โ”€ _default
             ย ย   ย ย  โ””โ”€โ”€ baseof.html

project/site/themes/custom-theme/assets/scss/main.scss

@charset "utf-8";
@import "variables.scss";
@import "bulma/bulma";

// custom style ...

head

<head>
    {{ $scssOptions := (dict "targetPath" "css/styles.css" "enableSourceMap" false "includePaths" (slice "../node_modules")) }}
    {{ $scssFile:= default "scss/main.scss" .Params.ScssFile}}
    {{ $scss := resources.Get $scssFile }}
    {{ $style := $scss | resources.ToCSS $scssOptions | minify | fingerprint }}
    <link rel="stylesheet" href="{{ $style.Permalink }}">
    <!-- ... -->
</head>

Hugo Versions

  • Hugo Static Site Generator v0.55.6-A5D4C82D2/extended linux/amd64 BuildDate: 2019-05-18T08:08:34Z
    
  • Hugo Static Site Generator v0.56.3/extended linux/amd64 BuildDate: unknown
    

    OS

cat /etc/lsb-release 
DISTRIB_ID=ManjaroLinux
DISTRIB_RELEASE=18.0.4
DISTRIB_CODENAME=Illyria
DISTRIB_DESCRIPTION="Manjaro Linux"

Notes

I tried playing with various variations of paths in the head (such as node_modules, ./node_modules, absolute path, ...) and in main.scss (such as ./bulma/bulma, ../bulma/bulma, ...) and nothing works. The only way around is to not use incluePaths and instead to hard-code node_modules in the scss file, as in: @import './node_modules/bulma/bulma';.

Note that using includePaths as described in this setup works fine with the following hugo version:

Hugo Static Site Generator v0.55.6-A5D4C82D2/extended linux/amd64 BuildDate: 2019-05-18T08:08:34Z
NeedsInvestigation

Most helpful comment

@bep Thanks I was looking into it and it does indeed look like the introduction of modules might have interfered with this feature. You suggestions to use modules (which is a really cool new feature btw) works!

Specfically (and for anyone stumbling upon this) the corrrect configuration is:

[module]

  [[module.mounts]]
    source = "static"
    target = "static"

  [[module.mounts]]
    source = "../node_modules/bulma"
    target = "assets/scss/bulma"

I had to mount the static folder explicitly (not sure if that's intentional or not, but it may be because I have a target of static/webfonts as well in my project) and the source path for the node modules has to start with ../ since the folder is located in the parent of the site in my setup.
You can check the working setup here.

For me this is a perfectly acceptable solution. I find it much cleaner and explicit than passing the node_modules folder in the head template. That being said, it may be nice to update the SASS/SCSS documentation to let people know of the changes.

All 8 comments

This is possibly a bug introduced by my 0.57 changes. That said, I think you would get a simpler setup/easier to reason about if you use the new module mounts setup.

E.g. (from memory):

[module]

  [[module.mounts]]
    source = "node_modules/bulma"
    target = "assets/scss/bulma"

If you get those paths in line you should not need to add any includePaths.

@bep Thanks I was looking into it and it does indeed look like the introduction of modules might have interfered with this feature. You suggestions to use modules (which is a really cool new feature btw) works!

Specfically (and for anyone stumbling upon this) the corrrect configuration is:

[module]

  [[module.mounts]]
    source = "static"
    target = "static"

  [[module.mounts]]
    source = "../node_modules/bulma"
    target = "assets/scss/bulma"

I had to mount the static folder explicitly (not sure if that's intentional or not, but it may be because I have a target of static/webfonts as well in my project) and the source path for the node modules has to start with ../ since the folder is located in the parent of the site in my setup.
You can check the working setup here.

For me this is a perfectly acceptable solution. I find it much cleaner and explicit than passing the node_modules folder in the head template. That being said, it may be nice to update the SASS/SCSS documentation to let people know of the changes.

That being said, it may be nice to update the SASS/SCSS documentation to let people know of the changes.

I agree. It would be cool if you could lend us a hand, now that you know how it works... But I will fix this particular issue, as this was an unintended side effect. But I do agree that using the file mounts is a cleaner and easier to reason about solution. And it gets even cooler when you mount folders inside other GitHub projects ...

I tried to create a failing test similar to your setup, but I failed (or succeeded ...). Which means that there is something I'm not seeing in your setup ...

Hi sorry for the late reply. I can do a simple set up for testing. I am also happy to lend an hand.

Which approach do you prefer:

  1. Prevent adding paths past the root, display an error message and update the doc?
  2. Fix the logic to restore the old behavior?

Hi @bep. I think I reproduced this case. The quickest way would be to modify Netlify's Victor Hugo's template:

  1. Clone it.
  2. Make Hugo generate the SCSS instead of Webpack.
  3. Include some SCSS import in node_modules.

As a side note, with Hugo 0.67.1, specifying the modules with @0xjac's configuration results in the following error on my build:

execute of template failed: template: partials/head.html:57:52: executing "partials/head.html" at <resources.ToCSS>: error calling ToCSS: no Resource provided in transformation

Hi @bep,

For information, I made minimal cases of this bug at this repo:
https://github.com/cyChop/minimal-cases-hugo

About the branches:

  • master is a dirty but working case (the path to the node_module is hardcoded).
  • bug/tocss-includepaths demonstrates the problem with includePaths.
  • bug/tocss-modules uses a configuration such as @0xjac's, but it fails with a different error.
  • bug/postcss demonstrates yet another problem when piping toCSS | postCSS, though I'm unsure if it's a bug or a configuration problem.

The most important code parts and error log are all summarized in the README.

Please let me know if I can help further (maybe the last problem is a support question for the discourse?).

And thank you for Hugo. :)

I am also experiencing this issue. My hugo site is stored under the root site/ directory. So I'm trying to use
"includePaths" (slice "../node_modules")

and importing the bootstrap sass partial like: @import "bootstrap/scss/functions";

but keep getting the error:

File to import not found or unreadable: bootstrap/scss/functions.

So now I'm relegated to doing @import '../../../../../node_modules/bootstrap/scss/functions';

Was this page helpful?
0 / 5 - 0 ratings

Related issues

digitalcraftsman picture digitalcraftsman  ยท  3Comments

antifuchs picture antifuchs  ยท  3Comments

VoidingWarranties picture VoidingWarranties  ยท  3Comments

geddski picture geddski  ยท  3Comments

bep picture bep  ยท  3Comments