1 | const { interpolateName, getOptions } = require('loader-utils');
|
2 | const urlSlug = require('url-slug');
|
3 | const SVGCompiler = require('svg-baker');
|
4 |
|
5 | const { NAMESPACE } = require('./config');
|
6 | const configure = require('./configurator');
|
7 | const { getWebpackVersion } = require('./utils');
|
8 | const Exceptions = require('./exceptions');
|
9 |
|
10 | let svgCompiler = new SVGCompiler();
|
11 |
|
12 |
|
13 | module.exports = function loader(content) {
|
14 | if (this.cacheable) {
|
15 | this.cacheable();
|
16 | }
|
17 |
|
18 | const done = this.async();
|
19 | const loaderContext = this;
|
20 | const { resourcePath, rootContext, loaderIndex } = loaderContext;
|
21 |
|
22 | const resourceQuery = loaderContext.resourceQuery || '';
|
23 | const compiler = loaderContext._compiler;
|
24 | const isChildCompiler = compiler.isChild();
|
25 | const parentCompiler = isChildCompiler ? compiler.parentCompilation.compiler : null;
|
26 | const matchedRules = getOptions(loaderContext);
|
27 |
|
28 | if (!content.includes('<svg')) {
|
29 | throw new Exceptions.InvalidSvg(content, matchedRules);
|
30 | }
|
31 |
|
32 | const configObj = { context: loaderContext };
|
33 |
|
34 | if (getWebpackVersion.IS_4) {
|
35 | configObj.config = loaderContext.query;
|
36 | configObj.target = loaderContext.target;
|
37 | } else {
|
38 | configObj.config = matchedRules;
|
39 | configObj.target = loaderContext.options.target || loaderContext.target;
|
40 | }
|
41 |
|
42 | |
43 |
|
44 |
|
45 | const config = configure(configObj);
|
46 |
|
47 | if (config.extract) {
|
48 | const plugin = parentCompiler
|
49 | ? parentCompiler.options.plugins.find(p => p.NAMESPACE && p.NAMESPACE === NAMESPACE)
|
50 | : this[NAMESPACE];
|
51 |
|
52 | if (typeof plugin === 'undefined') {
|
53 | throw new Exceptions.ExtractPluginMissingException();
|
54 | }
|
55 |
|
56 | if (loaderIndex > 0) {
|
57 | this.emitWarning(new Exceptions.RemainingLoadersInExtractModeException());
|
58 | }
|
59 |
|
60 | svgCompiler = plugin.svgCompiler;
|
61 | }
|
62 |
|
63 | let runtimeGenerator;
|
64 | try {
|
65 | runtimeGenerator = require(config.runtimeGenerator);
|
66 | } catch (e) {
|
67 | throw new Exceptions.InvalidRuntimeException(e.message);
|
68 | }
|
69 |
|
70 | let id;
|
71 | if (typeof config.symbolId === 'function') {
|
72 | id = config.symbolId(resourcePath, resourceQuery);
|
73 | } else {
|
74 | const idPattern = config.symbolId + (resourceQuery ? `--${urlSlug(resourceQuery)}` : '');
|
75 | id = interpolateName(loaderContext, idPattern, {
|
76 | content,
|
77 | context: compiler.context,
|
78 | regExp: config.symbolRegExp
|
79 | });
|
80 | }
|
81 | svgCompiler.addSymbol({ id, content, path: resourcePath + resourceQuery })
|
82 | .then((symbol) => {
|
83 | const runtime = runtimeGenerator({ symbol, config, context: rootContext, loaderContext });
|
84 | done(null, runtime);
|
85 | }).catch(done);
|
86 | };
|
87 |
|
88 | module.exports.NAMESPACE = NAMESPACE;
|