Skip to content

Commit 1d6e505

Browse files
committed
feat: allow user to choose between resolvers
If a paths property is set in the options, it will effectively disable webpack's resolver. This allows you to use Less' default resolver which is usually faster. However, if you choose to set the paths, you won't be able to use webpack features like resolve.alias or importing other file types. This is not a breaking change because setting the paths hasn't worked properly before this anyway.
1 parent d3022b8 commit 1d6e505

File tree

6 files changed

+38
-11
lines changed

6 files changed

+38
-11
lines changed

src/getOptions.js

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,11 @@ function getOptions(loaderContext) {
1818
// We need to set the filename because otherwise our WebpackFileManager will receive an undefined path for the entry
1919
options.filename = loaderContext.resource;
2020

21-
// It's safe to mutate the array now because it has already been cloned
22-
options.plugins.push(createWebpackLessPlugin(loaderContext));
21+
// When no paths are given, we use the webpack resolver
22+
if ('paths' in options === false) {
23+
// It's safe to mutate the array now because it has already been cloned
24+
options.plugins.push(createWebpackLessPlugin(loaderContext));
25+
}
2326

2427
return options;
2528
}
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
// You can't use include paths and webpack's resolver simulatenously.
2+
@import "some/module.less";
3+
@import "~some/module.less";

test/fixtures/less/imports-paths.less

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
// some/module.less is intended to be loaded from node_modules if the folder is configured as include path.
2+
// webpack would expect this import to be prepended with a ~ character.
3+
@import "some/module.less";

test/helpers/createSpec.js

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,18 @@
1-
2-
31
const { exec } = require('child_process');
42
const fs = require('fs');
53
const path = require('path');
64
const removeSourceMappingUrl = require('../../src/removeSourceMappingUrl');
75

86
const projectPath = path.resolve(__dirname, '..', '..');
9-
const lessFixtures = path.resolve(__dirname, '..', 'fixtures', 'less');
10-
const cssFixtures = path.resolve(__dirname, '..', 'fixtures', 'css');
7+
const fixturesPath = path.resolve(projectPath, 'test', 'fixtures');
8+
const lessFixturesPath = path.resolve(fixturesPath, 'less');
9+
const cssFixturesPath = path.resolve(fixturesPath, 'css');
1110
const matchWebpackImports = /(@import\s+(\([^)]+\))?\s*["'])~/g;
1211
const lessBin = require.resolve('.bin/lessc');
1312
const ignore = [
1413
'non-less-import',
15-
'error',
14+
'error-import-not-existing',
15+
'error-mixed-resolvers',
1616
];
1717
/**
1818
* This object specifies the replacements for the ~-character per test.
@@ -34,8 +34,11 @@ const lessOptions = {
3434
`--source-map-basepath=${projectPath}`,
3535
`--source-map-rootpath=${projectPath}`,
3636
],
37+
'imports-paths': [
38+
`--include-path=${path.resolve(fixturesPath, 'node_modules')}`,
39+
],
3740
};
38-
const testIds = fs.readdirSync(lessFixtures)
41+
const testIds = fs.readdirSync(lessFixturesPath)
3942
.filter(name =>
4043
path.extname(name) === '.less' && ignore.indexOf(path.basename(name, '.less')) === -1,
4144
)
@@ -45,8 +48,8 @@ const testIds = fs.readdirSync(lessFixtures)
4548

4649
testIds
4750
.forEach((testId) => {
48-
const lessFile = path.resolve(lessFixtures, `${testId}.less`);
49-
const cssFile = path.resolve(cssFixtures, `${testId}.css`);
51+
const lessFile = path.resolve(lessFixturesPath, `${testId}.less`);
52+
const cssFile = path.resolve(cssFixturesPath, `${testId}.css`);
5053
const tildeReplacement = tildeReplacements[testId];
5154
const originalLessContent = fs.readFileSync(lessFile, 'utf8');
5255

test/index.test.js

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,10 @@
1+
const path = require('path');
12
const compile = require('./helpers/compile');
23
const moduleRules = require('./helpers/moduleRules');
34
const { readCssFixture, readSourceMap } = require('./helpers/readFixture');
45

6+
const nodeModulesPath = path.resolve(__dirname, 'fixtures', 'node_modules');
7+
58
async function compileAndCompare(fixture, lessLoaderOptions, lessLoaderContext) {
69
let inspect;
710
const rules = moduleRules.basic(lessLoaderOptions, lessLoaderContext, (i) => {
@@ -28,6 +31,10 @@ test('should resolve all imports from node_modules', async () => {
2831
await compileAndCompare('imports-node');
2932
});
3033

34+
test('should resolve imports from given paths', async () => {
35+
await compileAndCompare('imports-paths', { paths: [__dirname, nodeModulesPath] });
36+
});
37+
3138
test('should not try to resolve import urls', async () => {
3239
await compileAndCompare('imports-url');
3340
});
@@ -90,9 +97,17 @@ test('should not alter the original options object', async () => {
9097
});
9198

9299
test('should report error correctly', async () => {
93-
const err = await compile('error')
100+
const err = await compile('error-import-not-existing')
94101
.catch(e => e);
95102

96103
expect(err).toBeInstanceOf(Error);
97104
expect(err.message).toMatch(/not-existing/);
98105
});
106+
107+
test('should fail if a file is tried to be loaded from include paths and with webpack\'s resolver simultaneously', async () => {
108+
const err = await compile('error-mixed-resolvers', moduleRules.basic({ paths: [nodeModulesPath] }))
109+
.catch(e => e);
110+
111+
expect(err).toBeInstanceOf(Error);
112+
expect(err.message).toMatch(/'~some\/module\.less' wasn't found/);
113+
});

0 commit comments

Comments
 (0)