Skip to content

breaks when used in webpack <=3, with svelte v3 #89

Closed
@0gust1

Description

@0gust1

Sorry for the annoying issue :-/

TLDR :

It's a cross bug between :

  • the changes between svelte v2 and svelte v3 compiler strategy in options handling
  • a mocha test written the old way.
  • the usage of both this.options and loader-utils.getOptions(this) to handle options.
    ** this.options was deprecated in webpack3 and removed in webpack4.
    ** loader-utils.getOptions(this) is the right way to do. It appeared in version 1.0.0 (21 Feb 2017) of loader-utils and seems supported since webpack v1

edit: proposed pull request : #90
edit: related issue : #88
edit: possibly related issue/pr : #87

Below, all the analysis I did investigating the issue. Sorry, it's a bit verbose.


Context :
Our big project is stuck to webpack 3 at the moment (due to a bug in webpack 4 that will be resolved in webpack 5).

This loader seems to break in webpack3. We have been able to reconstruct a minimal case (using the svelte-app template and making a dichotomy with webpack3 vs webpack4)

  • with webpack3, the loader breaks at the same line as our big project :
    let { js, css, warnings } = normalize(compile(processed.toString(), compileOptions));
  • with webpack4 everything compile fine.

The kind of errors we have :

ERROR in ./src/App.svelte
Module build failed: Error: Error: Error: Unrecognized option 'entry'
    at preprocess.then.catch.err (/ABSOLUTE_PATH/test_svelte3_webpack3/node_modules/svelte-loader/index.js:182:12)
 @ ./src/main.js 1:0-31

On our other project, it's not entry but context.


After further analysis, it seems that the svelte V3 compiler doesn't like the configuration feeded to it when it comes from webpack 3. The validate_options() function of the compiler reject it.

Config is inited here :

const options = Object.assign({}, this.options, getOptions(this));
where this.options is :

  • with webpack 3 : the webpack big config object
  • with webpack 4 : undefined (because it was finally deprecated)

Config is transformed along the way (into a compileOptions object) and, after that, it's used here :

let { js, css, warnings } = normalize(compile(processed.toString(), compileOptions));

In the minimal test case we have :

compileOptions with webpack 3 and svelte 3

{
  "filename": "/workspace_absolute_path/test_svelte3_webpack3/src/App.svelte",
  "format": "esm",
  "entry": "./src/main.js",
  "module": {
    "rules": [
      { "test": {}, "use": [{ "loader": "svelte-loader", "options": {} }] }
    ],
    "unknownContextRequest": ".",
    "unknownContextRegExp": false,
    "unknownContextRecursive": true,
    "unknownContextCritical": true,
    "exprContextRequest": ".",
    "exprContextRegExp": false,
    "exprContextRecursive": true,
    "exprContextCritical": true,
    "wrappedContextRegExp": {},
    "wrappedContextRecursive": true,
    "wrappedContextCritical": false,
    "strictExportPresence": false,
    "strictThisContextOnImports": false,
    "unsafeCache": true
  },
  "output": {
    "path": "/workspace_absolute_path/test_svelte3_webpack3/public",
    "filename": "bundle.js",
    "chunkFilename": "[id].bundle.js",
    "library": "",
    "hotUpdateFunction": "webpackHotUpdate",
    "jsonpFunction": "webpackJsonp",
    "libraryTarget": "var",
    "sourceMapFilename": "[file].map[query]",
    "hotUpdateChunkFilename": "[id].[hash].hot-update.js",
    "hotUpdateMainFilename": "[hash].hot-update.json",
    "crossOriginLoading": false,
    "jsonpScriptType": "text/javascript",
    "chunkLoadTimeout": 120000,
    "hashFunction": "md5",
    "hashDigest": "hex",
    "hashDigestLength": 20,
    "devtoolLineToLine": false,
    "strictModuleExceptionHandling": false
  },
  "context": "/workspace_absolute_path/test_svelte3_webpack3",
  "devtool": false,
  "cache": true,
  "target": "web",
  "node": {
    "console": false,
    "process": true,
    "global": true,
    "Buffer": true,
    "setImmediate": true,
    "__filename": "mock",
    "__dirname": "mock"
  },
  "performance": {
    "maxAssetSize": 250000,
    "maxEntrypointSize": 250000,
    "hints": false
  },
  "resolve": {
    "unsafeCache": true,
    "modules": ["node_modules"],
    "extensions": [".js", ".json"],
    "mainFiles": ["index"],
    "aliasFields": ["browser"],
    "mainFields": ["browser", "module", "main"],
    "cacheWithContext": false
  },
  "resolveLoader": {
    "unsafeCache": true,
    "mainFields": ["loader", "main"],
    "extensions": [".js", ".json"],
    "mainFiles": ["index"],
    "cacheWithContext": false
  }
}

compileOptions with webpack 4 and svelte 3

{"filename":"/workspace_absolute_path/test_svelte3_webpack3/src/App.svelte","format":"esm"}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions