FredKSchott / snowpack

ESM-powered frontend build tool. Instant, lightweight, unbundled development. ✌️
https://www.snowpack.dev
MIT License
19.48k stars 923 forks source link

Error snowpack thinks SCSS partial imports are modules #2695

Closed Danzo7 closed 3 years ago

Danzo7 commented 3 years ago

Error when import SASS partials : only when using snowpack dev

snowpack think partial.scss is a module for some reason when read an .SCSS file that contain @import 'partial.scss'; full stack:

[snowpack] run command: dev
[snowpack] loaded plugin: /home/codespace/workspace/doctorIO/node_modules/@snowpack/plugin-react-refresh/plugin.js
[snowpack] loaded plugin: /home/codespace/workspace/doctorIO/node_modules/@snowpack/plugin-dotenv/plugin.js
[snowpack] loaded plugin: /home/codespace/workspace/doctorIO/node_modules/@snowpack/plugin-typescript/plugin.js
[snowpack] loaded plugin: /home/codespace/workspace/doctorIO/node_modules/snowpack-svgr-plugin/index.js
[snowpack] loaded plugin: /home/codespace/workspace/doctorIO/node_modules/snowpack-sass-compiler/plugin.js
[snowpack] config loaded: {
  root: '/home/codespace/workspace/doctorIO',
  plugins: [
    {
      name: '@snowpack/plugin-react-refresh',
      transform: [Function: transform],
      markChanged: [Function (anonymous)]
    },
    {
      name: '@snowpack/plugin-dotenv',
      markChanged: [Function (anonymous)]
    },
    {
      name: '@snowpack/plugin-typescript',
      run: [AsyncFunction: run],
      markChanged: [Function (anonymous)]
    },
    {
      name: 'snowpack-svgr',
      resolve: [Object],
      load: [AsyncFunction: load],
      markChanged: [Function (anonymous)]
    },
    {
      name: 'snowpack-sass-compiler',
      resolve: [Object],
      _markImportersAsChanged: [Function: _markImportersAsChanged],
      onChange: [Function: onChange],
      load: [AsyncFunction: load],
      markChanged: [Function (anonymous)]
    },
    {
      name: '@snowpack/plugin-esbuild',
      resolve: [Object],
      load: [AsyncFunction: load],
      cleanup: [Function: cleanup]
    }
  ],
  alias: {
    '@data': '/home/codespace/workspace/doctorIO/src/data',
    '@components': '/home/codespace/workspace/doctorIO/src/components/components',
    '@containers': '/home/codespace/workspace/doctorIO/src/components/containers',
    toSvg: '/home/codespace/workspace/doctorIO/src/assets/svg',
    '@assets': '/home/codespace/workspace/doctorIO/src/assets',
    '@styles': '/home/codespace/workspace/doctorIO/src/assets/styles'
  },
  exclude: [
    '**/node_modules/**/*',
    '/home/codespace/workspace/doctorIO/build/**/*'
  ],
  routes: [],
  devOptions: {
    secure: false,
    hostname: 'localhost',
    port: 8080,
    open: 'default',
    output: 'dashboard',
    hmrDelay: 0,
    hmrPort: undefined,
    hmrErrorOverlay: true
  },
  buildOptions: {
    out: '/home/codespace/workspace/doctorIO/build',
    baseUrl: '/',
    metaUrlPath: '/_snowpack',
    clean: true,
    sourcemap: false,
    watch: false,
    htmlFragments: false,
    ssr: false
  },
  testOptions: { files: [ '__tests__/**/*', '**/*.@(spec|test).*' ] },
  packageOptions: {
    source: 'local',
    external: [],
    packageLookupFields: [],
    knownEntrypoints: [],
    rollup: { plugins: [] }
  },
  mount: {
    '/home/codespace/workspace/doctorIO/public': { url: '/', static: true, resolve: true },
    '/home/codespace/workspace/doctorIO/src': { url: '/dist', static: false, resolve: true }
  },
  optimize: undefined,
  experiments: {},
  _extensionMap: {
    '.svgr.svg': [ '.js' ],
    '.scss': [ '.css' ],
    '.sass': [ '.css' ],
    '.mjs': [ '.js' ],
    '.jsx': [ '.js' ],
    '.ts': [ '.js' ],
    '.tsx': [ '.js' ]
  }
}
[snowpack] lockfile not loaded
[snowpack] attaching console.log listeners
[snowpack] dashboard started
[snowpack] Using in-memory cache.
[snowpack] Mounting directories:
[snowpack]  -> '/home/codespace/workspace/doctorIO/public' as URL '/'
[snowpack]  -> '/home/codespace/workspace/doctorIO/src' as URL '/dist'
[snowpack] Using cache folder: node_modules/.cache/snowpack/development
[snowpack] Cache out of date or missing. Updating...
[snowpack] Scanning public/index.html for imports as HTML
[snowpack] Skip scanning public/robots.txt for imports (unknown file extension .txt)
[snowpack] Scanning src/App.scss for imports as CSS
[snowpack] Scanning src/App.tsx for imports as JS
[snowpack] Scanning src/assets/styles/_appColors.scss for imports as CSS
[snowpack] Scanning src/assets/styles/color.ts for imports as JS
[snowpack] Skip scanning src/assets/svg/clinic.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/database.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/history.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/home.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/logo.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/messages.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/clinic.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/database.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/history.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/home.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/logo.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/messages.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/settings.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/render/stats.svgr.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/settings.svg for imports (unknown file extension .svg)
[snowpack] Skip scanning src/assets/svg/stats.svg for imports (unknown file extension .svg)
[snowpack] Scanning src/components/components/LinkyIcon/index.scss for imports as CSS
[snowpack] Scanning src/components/components/LinkyIcon/index.ts for imports as JS
[snowpack] Scanning src/components/components/LinkyIcon/LinkyIcon.tsx for imports as JS
[snowpack] Scanning src/components/components/QueueItem/index.ts for imports as JS
[snowpack] Scanning src/components/components/QueueItem/QueueItem.tsx for imports as JS
[snowpack] Scanning src/components/components/QueueItem/style/index.scss for imports as CSS
[snowpack] Scanning src/components/containers/AppContent/AppContent.tsx for imports as JS
[snowpack] Scanning src/components/containers/AppContent/index.scss for imports as CSS
[snowpack] Scanning src/components/containers/AppContent/index.ts for imports as JS
[snowpack] Scanning src/components/containers/AppMenu/AppMenu.tsx for imports as JS
[snowpack] Scanning src/components/containers/AppMenu/index.ts for imports as JS
[snowpack] Scanning src/components/containers/AppMenu/MenuOption/index.ts for imports as JS
[snowpack] Scanning src/components/containers/AppMenu/MenuOption/MenuOption.tsx for imports as JS
[snowpack] Scanning src/components/containers/AppMenu/MenuOption/style/index.scss for imports as CSS
[snowpack] Scanning src/components/containers/AppMenu/style/index.scss for imports as CSS
[snowpack] Scanning src/components/containers/AppSidebar/AppSidebar.tsx for imports as JS
[snowpack] Scanning src/components/containers/AppSidebar/index.scss for imports as CSS
[snowpack] Scanning src/components/containers/AppSidebar/index.ts for imports as JS
[snowpack] Scanning src/data/iconfig.ts for imports as JS
[snowpack] Scanning src/data/menuSvgs.ts for imports as JS
[snowpack] Scanning src/index.scss for imports as CSS
[snowpack] Scanning src/index.tsx for imports as JS
[snowpack] Skip scanning src/logo.svg for imports (unknown file extension .svg)
[snowpack] ! building dependencies...
[snowpack] Cannot find module 'appColors.scss'
Require stack:
- /home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js
- /home/codespace/workspace/doctorIO/node_modules/snowpack/index.bin.js
[snowpack] Error: Cannot find module 'appColors.scss'
Require stack:
- /home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js
- /home/codespace/workspace/doctorIO/node_modules/snowpack/index.bin.js
    at Function.Module._resolveFilename (internal/modules/cjs/loader.js:880:15)
    at Function.resolve (internal/modules/cjs/helpers.js:94:19)
    at Object.resolveEntrypoint (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:47222:49)
    at resolveWebDependency (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:47545:29)
    at Object.install (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:47656:36)
    at Object.run (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:47867:37)
    at installDependencies (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:49378:46)
    at async Object.prepare (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:49433:35)
    at async startServer (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:131149:27)
    at async Object.command (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:132039:9)
    at async cli (/home/codespace/workspace/doctorIO/node_modules/snowpack/lib/index.js:132333:9)

npm ERR! code ELIFECYCLE
npm ERR! errno 1
npm ERR! @ start: `snowpack dev --verbose`
npm ERR! Exit status 1
npm ERR! 
BPScott commented 3 years ago

I'm running into this too.

Some cursory investigation suggests this only occurs when the import path looks absolute. e.g. @import 'partial' fails but @import './partial' works. This is reasonable for CSS-style imports which are URLs, however Sass overloads the @import method for local imports and @import 'partial' can refer to a relative file i.e. it is functionally equal to @import './partial'.

I think the fix might involve editing scan-imports.ts' parseFileForInstallTargets to add a special-case for handling imports in sass/scss files instead of treating them the same as css files.

As a work around, I think consumers can use dart-sass's @use notation instead of @import notation which will not trigger this import discovery process. (This isn't helpful for me right now as I'm working on a legacy codebase that is still using libsass).

An alternative workaround is to ensure you always include a ./ when targeting relative files when using an @import. i.e. replace @import 'partial' with @import './partial' and to avoid usage of custom import paths (i.e. importing anything that doesn't start a relative path)

Danzo7 commented 3 years ago

I'm running into this too.

Some cursory investigation suggests this only occurs when the import path looks absolute. e.g. @import 'partial' fails but @import './partial' works. This is reasonable for CSS-style imports which are URLs, however Sass overloads the @import method for local imports and @import 'partial' can refer to a relative file i.e. it is functionally equal to @import './partial'.

I think the fix might involve editing scan-imports.ts' parseFileForInstallTargets to add a special-case for handling imports in sass/scss files instead of treating them the same as css files.

As a work around, I think consumers can use dart-sass's @use notation instead of @import notation which will not trigger this import discovery process. (This isn't helpful for me right now as I'm working on a legacy codebase that is still using libsass).

An alternative workaround is to ensure you always include a ./ when targeting relative files when using an @import. i.e. replace @import 'partial' with @import './partial' and to avoid usage of custom import paths (i.e. importing anything that doesn't start a relative path)

I didn't know that using @import is not even recommended anymore by the sass team

The Sass team discourages the continued use of the @import rule. Sass will gradually phase it out over the next few years, and eventually remove it from the language entirely. Prefer the @use rule instead. (Note that only Dart Sass currently supports @use. Users of other implementations must use the @import rule instead.) I will considered that in the future project thank you.

just to explain why using relative path may not solve this issue in my case: using a relative path @import './partial' instead of @import 'partial' will work but only when your partial.scss is within the same path as your importer.sass but if your project is a three-architecture with a great depth you will struggle using relative paths, that why dart-sass introduce --load-path for CLI and includePaths for JS API which add the ability of importing from any path that is included in this property without having to use the relative path which means for a file in ./src/someOtherPath/../_partial.scss its can only be imported in this way @import 'partial'.

I still think its a bug in the snowpack that can accrue anytime in the future and has to be fix

fgblomqvist commented 3 years ago

I just hit this as well, but in a slightly different scenario. I'm using the loadPath config for sass, which results in you being able to write absolute imports that consequently seem to be picked up incorrectly as explained by @BPScott.

E.g.:

    [
      '@snowpack/plugin-sass',
      {
        compilerOptions: {
          loadPath: ['node_modules'],
        },
      },
    ],

and then I have imports in my scss files like:

@import "somepackage/styles/theme";

which trigger this when I run snowpack in dev mode:

[snowpack] ! building dependencies...
[snowpack] Package "somepackage/styles/theme" not found. Have you installed it? 

However, it works as intended when running build. Switching to a @use does indeed also solve the problem, and is preferred in basically all (?) of the cases anyway.

Danzo7 commented 3 years ago

I just hit this as well, but in a slightly different scenario. I'm using the loadPath config for sass, which results in you being able to write absolute imports that consequently seem to be picked up incorrectly as explained by @BPScott.

E.g.:

    [
      '@snowpack/plugin-sass',
      {
        compilerOptions: {
          loadPath: ['node_modules'],
        },
      },
    ],

and then I have imports in my scss files like:

@import "somepackage/styles/theme";

which trigger this when I run snowpack in dev mode:

[snowpack] ! building dependencies...
[snowpack] Package "somepackage/styles/theme" not found. Have you installed it? 

However, it works as intended when running build. Switching to a @use does indeed also solve the problem, and is preferred in basically all (?) of the cases anyway.

it was a wrong written regular expression and this PR will fix hopefully: https://github.com/snowpackjs/snowpack/pull/2817

drwpow commented 3 years ago

OK did some investigation, and I did find that in instances where extension was omitted, we were falling back to .js when a better guess at the extension could be inferred (for example, if we’re in a .scss file, let’s assume that @import "component" refers to ./component.scss rather than ./component.js).

I think #2817 can help in some ways—it improves import RegExs—but perhaps we can prevent Sass from even being parsed as JS in the first place.

simonwiles commented 3 years ago

Should this be fixed in 3.4.0? I'm still seeing the same issue with Snowpack attempting to find JS modules for, e.g.

@import "overlay-buttons";

in my .scss files. ([snowpack] Package "overlay-buttons" not found. Have you installed it?).

Using relative paths:

@import "./overlay-buttons";

works just fine.

puka-tchou commented 2 years ago

I'm using v3.8.8 and I'm still experiencing this issue with snowpack build --watch. I had to change all my imports to use a relative path because Snowpack kept asking me to install the missing packages.

Am I the only one experiencing this issue or is it still active?

Here's my config:

// Snowpack Configuration File
// See all supported options: https://www.snowpack.dev/reference/configuration

/** @type {import("snowpack").SnowpackUserConfig } */
module.exports = {
    root: 'resources/cth/',
    plugins: [
        [
            '@snowpack/plugin-sass',
            {
                compilerOptions: {
                    // Temporary fix
                    quiet: true,
                },
            },
        ],
        '@snowpack/plugin-postcss',
    ],
    devOptions: {},
    packageOptions: {
        polyfillNode: true,
    },
    buildOptions: {
        out: 'public/application/themes/cth/snowpack/',
    },
    optimize: {
        // bundle: true,
        minify: true,
        target: 'es2017',
        treeshake: true,
        // entrypoints: ['public/application/single_pages/**/*.php', 'public/application/themes/**/*.php'],
    },
};