Skip to content

Commit

Permalink
fix: resolve absolute and root relative imports
Browse files Browse the repository at this point in the history
  • Loading branch information
cap-Bernardito committed Jun 22, 2020
1 parent d95e037 commit 3d01b82
Show file tree
Hide file tree
Showing 7 changed files with 179 additions and 3 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,8 @@ yarn-debug.log*
/local
/reports
/test/fixtures/css
/test/fixtures/generated-1.less
/test/fixtures/generated-2.less
/test/output
.DS_Store
Thumbs.db
Expand Down
12 changes: 9 additions & 3 deletions src/utils.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import path from 'path';

import less from 'less';
import clone from 'clone';

Expand Down Expand Up @@ -26,6 +28,10 @@ function createWebpackLessPlugin(loaderContext) {

class WebpackFileManager extends less.FileManager {
supports(filename) {
if (filename[0] === '/' || path.win32.isAbsolute(filename)) {
return true;
}

if (this.isPathAbsolute(filename)) {
return false;
}
Expand Down Expand Up @@ -53,15 +59,15 @@ function createWebpackLessPlugin(loaderContext) {
async resolveFilename(filename, currentDirectory, options) {
const url = this.getUrl(filename, options);

const moduleRequest = urlToRequest(
const request = urlToRequest(
url,
url.charAt(0) === '/' ? '' : null
url.charAt(0) === '/' ? loaderContext.rootContext : null
);

// Less is giving us trailing slashes, but the context should have no trailing slash
const context = currentDirectory.replace(trailingSlash, '');

return this.resolveRequests(context, [moduleRequest, url]);
return this.resolveRequests(context, [request, url]);
}

resolveRequests(context, possibleRequests) {
Expand Down
68 changes: 68 additions & 0 deletions test/__snapshots__/loader.test.js.snap
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,23 @@ exports[`loader should delegate resolving (LESS) imports with URLs to "less" pac
exports[`loader should delegate resolving (LESS) imports with URLs to "less" package: warnings 1`] = `Array []`;
exports[`loader should get absolute path relative rootContext: css 1`] = `
".box {
color: #fe33ac;
border-color: #fdcdea;
background: url(box.png);
}
.box div {
-webkit-box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
}
"
`;
exports[`loader should get absolute path relative rootContext: errors 1`] = `Array []`;
exports[`loader should get absolute path relative rootContext: warnings 1`] = `Array []`;
exports[`loader should import from plugins: css 1`] = `
".imported-class {
color: coral;
Expand Down Expand Up @@ -180,6 +197,40 @@ Array [
exports[`loader should provide a useful error message if there was a syntax error: warnings 1`] = `Array []`;
exports[`loader should resolve absolute path with alias: css 1`] = `
".box {
color: #fe33ac;
border-color: #fdcdea;
background: url(box.png);
}
.box div {
-webkit-box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
}
"
`;
exports[`loader should resolve absolute path with alias: errors 1`] = `Array []`;
exports[`loader should resolve absolute path with alias: warnings 1`] = `Array []`;
exports[`loader should resolve absolute path: css 1`] = `
".box {
color: #fe33ac;
border-color: #fdcdea;
background: url(box.png);
}
.box div {
-webkit-box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
}
"
`;
exports[`loader should resolve absolute path: errors 1`] = `Array []`;
exports[`loader should resolve absolute path: warnings 1`] = `Array []`;
exports[`loader should resolve aliases in diffrent variants: css 1`] = `
".img {
background: url(some/img.jpg);
Expand Down Expand Up @@ -297,6 +348,23 @@ exports[`loader should resolve nested imports: errors 1`] = `Array []`;
exports[`loader should resolve nested imports: warnings 1`] = `Array []`;
exports[`loader should resolve unresolved url with alias: css 1`] = `
".box {
color: #fe33ac;
border-color: #fdcdea;
background: url(box.png);
}
.box div {
-webkit-box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
box-shadow: 0 0 5px rgba(0, 0, 0, 0.3);
}
"
`;
exports[`loader should resolve unresolved url with alias: errors 1`] = `Array []`;
exports[`loader should resolve unresolved url with alias: warnings 1`] = `Array []`;
exports[`loader should transform urls: css 1`] = `
".img4 {
background: url(folder/img.jpg);
Expand Down
1 change: 1 addition & 0 deletions test/fixtures/import-absolute-2.less
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
@import "/fixtures/basic.less";
1 change: 1 addition & 0 deletions test/fixtures/import-absolute-3.less
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
@import "/styles/style.less";
5 changes: 5 additions & 0 deletions test/helpers/getCodeFromLess.js
Original file line number Diff line number Diff line change
Expand Up @@ -70,10 +70,15 @@ const pathMap = {
'package',
'style.less'
),
'/styles/style.less': path.resolve(__dirname, '..', 'fixtures', 'basic.less'),
};

class ResolvePlugin extends less.FileManager {
supports(filename) {
if (filename[0] === '/' || path.win32.isAbsolute(filename)) {
return true;
}

if (this.isPathAbsolute(filename)) {
return false;
}
Expand Down
93 changes: 93 additions & 0 deletions test/loader.test.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import path from 'path';

import fs from 'fs';

import CustomImportPlugin from './fixtures/folder/customImportPlugin';
import CustomFileLoaderPlugin from './fixtures/folder/customFileLoaderPlugin';

Expand Down Expand Up @@ -503,4 +505,95 @@ describe('loader', () => {
expect(getWarnings(stats)).toMatchSnapshot('warnings');
expect(getErrors(stats)).toMatchSnapshot('errors');
});

it('should get absolute path relative rootContext', async () => {
const testId = './import-absolute-2.less';
const compiler = getCompiler(
testId,
{},
{
context: path.resolve(__dirname),
entry: path.resolve(__dirname, './fixtures', testId),
}
);
const stats = await compile(compiler);

const codeFromBundle = getCodeFromBundle(stats, compiler);

expect(codeFromBundle.css).toMatchSnapshot('css');
expect(getWarnings(stats)).toMatchSnapshot('warnings');
expect(getErrors(stats)).toMatchSnapshot('errors');
});

it('should resolve unresolved url with alias', async () => {
const testId = './import-absolute-3.less';
const compiler = getCompiler(
testId,
{},
{
resolve: {
alias: {
'/styles/style.less': path.resolve(
__dirname,
'fixtures',
'basic.less'
),
},
},
}
);
const stats = await compile(compiler);
const codeFromBundle = getCodeFromBundle(stats, compiler);
const codeFromLess = await getCodeFromLess(testId);

expect(codeFromBundle.css).toBe(codeFromLess.css);
expect(codeFromBundle.css).toMatchSnapshot('css');
expect(getWarnings(stats)).toMatchSnapshot('warnings');
expect(getErrors(stats)).toMatchSnapshot('errors');
});

it('should resolve absolute path', async () => {
// Create the file with absolute path
const file = path.resolve(__dirname, 'fixtures', 'generated-1.less');
const absolutePath = path.resolve(__dirname, 'fixtures', 'basic.less');

fs.writeFileSync(file, `@import "${absolutePath}";`);

const testId = './generated-1.less';
const compiler = getCompiler(testId);
const stats = await compile(compiler);
const codeFromBundle = getCodeFromBundle(stats, compiler);
const codeFromLess = await getCodeFromLess(testId);

expect(codeFromBundle.css).toBe(codeFromLess.css);
expect(codeFromBundle.css).toMatchSnapshot('css');
expect(getWarnings(stats)).toMatchSnapshot('warnings');
expect(getErrors(stats)).toMatchSnapshot('errors');
});

it('should resolve absolute path with alias', async () => {
// Create the file with absolute path
const file = path.resolve(__dirname, 'fixtures', 'generated-2.less');
const absolutePath = path.resolve(__dirname, 'fixtures', 'unresolved.less');

fs.writeFileSync(file, `@import "${absolutePath}";`);

const config = {};
config.resolve = {};
config.resolve.alias = {};
config.resolve.alias[absolutePath] = path.resolve(
__dirname,
'fixtures',
'basic.less'
);

const testId = './generated-2.less';
const compiler = getCompiler(testId, {}, config);
const stats = await compile(compiler);
const codeFromBundle = getCodeFromBundle(stats, compiler);

expect(codeFromBundle.css).toMatchSnapshot('css');
expect(getWarnings(stats)).toMatchSnapshot('warnings');
expect(getErrors(stats)).toMatchSnapshot('errors');
});
});

0 comments on commit 3d01b82

Please sign in to comment.