Skip to content

Commit

Permalink
fix: ignore watch for remove URLs
Browse files Browse the repository at this point in the history
  • Loading branch information
cap-Bernardito authored Jun 22, 2020
1 parent 1eeec73 commit 3946937
Show file tree
Hide file tree
Showing 6 changed files with 127 additions and 3 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ yarn-debug.log*
/test/fixtures/css
/test/fixtures/generated-1.less
/test/fixtures/generated-2.less
/test/fixtures/generated-3.less
/test/output
.DS_Store
Thumbs.db
Expand Down
10 changes: 9 additions & 1 deletion src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,11 @@ import { getOptions } from 'loader-utils';
import validateOptions from 'schema-utils';

import schema from './options.json';
import { getLessOptions, getLessImplementation } from './utils';
import {
getLessOptions,
getLessImplementation,
isUnsupportedUrl,
} from './utils';
import LessError from './LessError';

function lessLoader(source) {
Expand Down Expand Up @@ -38,6 +42,10 @@ function lessLoader(source) {
.render(data, lessOptions)
.then(({ css, map, imports }) => {
imports.forEach((item) => {
if (isUnsupportedUrl(item)) {
return;
}

// `less` return forward slashes on windows when `webpack` resolver return an absolute windows path in `WebpackFileManager`
// Ref: https://github.com/webpack-contrib/less-loader/issues/357
this.addDependency(path.normalize(item));
Expand Down
17 changes: 15 additions & 2 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 @@ -126,7 +128,7 @@ function createWebpackLessPlugin(loaderContext) {
return super.loadFile(result, ...args);
}

loaderContext.addDependency(result.filename);
loaderContext.addDependency(path.normalize(result.filename));

return result;
}
Expand Down Expand Up @@ -188,4 +190,15 @@ function getLessImplementation(implementation) {
return less;
}

export { getLessImplementation, getLessOptions };
function isUnsupportedUrl(url) {
// Is Windows paths `c:\`
if (/^[a-zA-Z]:\\/.test(url)) {
return false;
}

// Scheme: https://tools.ietf.org/html/rfc3986#section-3.1
// Absolute URL: https://tools.ietf.org/html/rfc3986#section-4.3
return /^[a-zA-Z][a-zA-Z\d+\-.]*:/.test(url);
}

export { getLessImplementation, getLessOptions, isUnsupportedUrl };
49 changes: 49 additions & 0 deletions test/__snapshots__/loader.test.js.snap
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,23 @@ exports[`loader should add all resolved imports as dependencies: errors 1`] = `A

exports[`loader should add all resolved imports as dependencies: warnings 1`] = `Array []`;

exports[`loader should add path to dependencies: 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 add path to dependencies: errors 1`] = `Array []`;

exports[`loader should add path to dependencies: warnings 1`] = `Array []`;

exports[`loader should allow to import non-less files: css 1`] = `
".some-file {
background: hotpink;
Expand Down Expand Up @@ -135,6 +152,38 @@ exports[`loader should install plugins: errors 1`] = `Array []`;
exports[`loader should install plugins: warnings 1`] = `Array []`;
exports[`loader should not add to dependencies imports with URLs: css 1`] = `
"@font-face {
font-family: 'Roboto';
font-style: normal;
font-weight: 300;
src: local('Roboto Light'), local('Roboto-Light'), url(http://fonts.gstatic.com/s/roboto/v20/KFOlCnqEu92Fr1MmSU5fBBc9.ttf) format('truetype');
}
@font-face {
font-family: 'Roboto';
font-style: normal;
font-weight: 300;
src: local('Roboto Light'), local('Roboto-Light'), url(https://fonts.gstatic.com/s/roboto/v20/KFOlCnqEu92Fr1MmSU5fBBc9.ttf) format('truetype');
}
@font-face {
font-family: 'Roboto';
font-style: normal;
font-weight: 400;
src: local('Roboto'), local('Roboto-Regular'), url(https://fonts.gstatic.com/s/roboto/v20/KFOmCnqEu92Fr1Mu4mxP.ttf) format('truetype');
}
@font-face {
font-family: 'Roboto';
font-style: normal;
font-weight: 500;
src: local('Roboto Medium'), local('Roboto-Medium'), url(https://fonts.gstatic.com/s/roboto/v20/KFOlCnqEu92Fr1MmEU9fBBc9.ttf) format('truetype');
}
"
`;
exports[`loader should not add to dependencies imports with URLs: errors 1`] = `Array []`;
exports[`loader should not add to dependencies imports with URLs: warnings 1`] = `Array []`;
exports[`loader should not alter the original options object: errors 1`] = `Array []`;
exports[`loader should not alter the original options object: warnings 1`] = `Array []`;
Expand Down
2 changes: 2 additions & 0 deletions test/fixtures/import-url-deps.less
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
@import url("http://fonts.googleapis.com/css?family=Roboto:300");
@import url("https://fonts.googleapis.com/css?family=Roboto:300,400,500");
51 changes: 51 additions & 0 deletions test/loader.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -616,4 +616,55 @@ describe('loader', () => {
expect(getWarnings(stats)).toMatchSnapshot('warnings');
expect(getErrors(stats)).toMatchSnapshot('errors');
});

it('should not add to dependencies imports with URLs', async () => {
const testId = './import-url-deps.less';
const compiler = getCompiler(testId);
const stats = await compile(compiler);
const codeFromBundle = getCodeFromBundle(stats, compiler);
const codeFromLess = await getCodeFromLess(testId);
const { fileDependencies } = stats.compilation;

validateDependencies(fileDependencies);

Array.from(fileDependencies).forEach((item) => {
['http', 'https'].forEach((protocol) => {
expect(item.includes(protocol)).toBe(false);
});
});

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

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

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

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

validateDependencies(fileDependencies);

let isAddedToDependensies = false;

Array.from(fileDependencies).forEach((item) => {
if (item === absolutePath) {
isAddedToDependensies = true;
}
});

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

0 comments on commit 3946937

Please sign in to comment.