Skip to content

Commit 5d21b2f

Browse files
coleturnerkisenka
authored andcommitted
Support issuer filtering when matching rules (fixes #149) (#150)
* fix(loader): add support for issuer when matching rules With Webpack v2 one can use svg-sprite-loader for JavaScript/JSX modules while still using other loaders in other contexts (CSS for example). This is possible by using the "issuer" configuration for loader rules. For use with Webpack v1 an error will still occur. Fixes #149 * test(loader): add coverage for Webpack v1+2 handling of issuer in rules This adds coverage to the loader tests so that the "issuer" attribute on loader rules is honored when evaluating Webpack v2 config. For v1 configuration the issuer attribute is ignored and the previous errors are expected.
1 parent 0640a40 commit 5d21b2f

File tree

3 files changed

+37
-5
lines changed

3 files changed

+37
-5
lines changed

lib/loader.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,8 @@ module.exports = function loader(content) {
5353
throw new Exceptions.InvalidRuntimeException(config.runtimeGenerator);
5454
}
5555

56-
const matchedRules = utils.getMatchedRules(resource, utils.getLoadersRules(compiler));
56+
const issuer = loaderContext._module && loaderContext._module.issuer;
57+
const matchedRules = utils.getMatchedRules(resource, utils.getLoadersRules(compiler), issuer);
5758
if (matchedRules.length > 1 && !compiler.isChild()) {
5859
this.emitWarning(new Exceptions.SeveralRulesAppliedException(resource, matchedRules));
5960
}

lib/utils/get-matched-rules.js

Lines changed: 19 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,29 @@
1-
// eslint-disable-next-line import/no-extraneous-dependencies
1+
/* eslint-disable import/no-extraneous-dependencies */
22
const ruleMatcher = require('webpack/lib/ModuleFilenameHelpers').matchObject;
3+
const isWebpack1 = require('./is-webpack-1');
4+
const RuleSet = !isWebpack1 ? require('webpack/lib/RuleSet') : null;
35

46
/**
57
* @param {string} request
68
* @param {Rule[]} rules Webpack loaders config
79
* @return {Rule[]}
810
*/
9-
function getMatchedRules(request, rules) {
10-
return rules.filter(rule => ruleMatcher(rule, request));
11+
function getMatchedRules(request, rules, issuer) {
12+
const matchedRules = rules.filter(rule => ruleMatcher(rule, request));
13+
14+
if (issuer) {
15+
return matchedRules.filter((rule) => {
16+
// If rule doesn't have an issuer or RuleSet is not available
17+
if (!rule.issuer || !RuleSet) {
18+
return true;
19+
}
20+
21+
const matcher = RuleSet.normalizeCondition(rule.issuer);
22+
return matcher(issuer);
23+
});
24+
}
25+
26+
return matchedRules;
1127
}
1228

1329
module.exports = getMatchedRules;

test/loader.test.js

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ describe('loader and plugin', () => {
3737
errors[0].error.should.be.instanceOf(Exceptions.InvalidRuntimeException);
3838
});
3939

40-
it('should warn if several rules applied to module', async () => {
40+
it('should warn if several rules applied to module without issuer applied', async () => {
4141
const { warnings } = await compile({
4242
entry: './entry',
4343
module: rules(
@@ -64,6 +64,21 @@ describe('loader and plugin', () => {
6464

6565
assets['main.js'].source().should.contain('olala');
6666
});
67+
68+
it('should filter rules against issuer', async () => {
69+
const { warnings } = await compile({
70+
entry: './entry',
71+
module: rules(
72+
svgRule(),
73+
rule({ test: /\.svg$/, loader: loaderPath, issuer: /\.css$/ })
74+
)
75+
});
76+
77+
warnings.should.be.lengthOf(isWebpack1 ? 2 : 0);
78+
if (isWebpack1) {
79+
warnings[0].warning.should.be.instanceOf(Exceptions.SeveralRulesAppliedException);
80+
}
81+
});
6782
});
6883

6984
describe('extract mode', () => {

0 commit comments

Comments
 (0)