Skip to content

Commit 897e7dd

Browse files
refactor: future build @import (#1390)
1 parent 8946be4 commit 897e7dd

16 files changed

+259
-78
lines changed

src/index.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,8 @@ export default async function loader(content, map, meta) {
7171
if (shouldUseImportPlugin(options)) {
7272
plugins.push(
7373
importParser({
74-
isSupportAbsoluteURL,
74+
isSupportAbsoluteURL: false,
75+
isSupportDataURL: false,
7576
isCSSStyleSheet: options.exportType === "css-style-sheet",
7677
loaderContext: this,
7778
imports: importPluginImports,
@@ -100,7 +101,6 @@ export default async function loader(content, map, meta) {
100101
context: this.context,
101102
rootContext: this.rootContext,
102103
filter: getFilter(options.url.filter, this.resourcePath),
103-
needToResolveURL,
104104
resolver: needToResolveURL
105105
? this.getResolve({ mainFiles: [], extensions: [] })
106106
: // eslint-disable-next-line no-undefined

src/plugins/postcss-import-parser.js

+28-13
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,12 @@ import valueParser from "postcss-value-parser";
33
import {
44
normalizeUrl,
55
resolveRequests,
6-
isUrlRequestable,
6+
isURLRequestable,
77
requestify,
88
WEBPACK_IGNORE_COMMENT_REGEXP,
99
} from "../utils";
1010

11-
function parseNode(atRule, key) {
11+
function parseNode(atRule, key, options) {
1212
// Convert only top-level @import
1313
if (atRule.parent.type !== "root") {
1414
return;
@@ -97,10 +97,11 @@ function parseNode(atRule, key) {
9797

9898
url = normalizeUrl(url, isStringValue);
9999

100-
const isRequestable = isUrlRequestable(url);
100+
const { requestable, needResolve } = isURLRequestable(url, options);
101+
101102
let prefix;
102103

103-
if (isRequestable) {
104+
if (requestable && needResolve) {
104105
const queryParts = url.split("!");
105106

106107
if (queryParts.length > 1) {
@@ -165,7 +166,16 @@ function parseNode(atRule, key) {
165166
}
166167

167168
// eslint-disable-next-line consistent-return
168-
return { atRule, prefix, url, layer, supports, media, isRequestable };
169+
return {
170+
atRule,
171+
prefix,
172+
url,
173+
layer,
174+
supports,
175+
media,
176+
requestable,
177+
needResolve,
178+
};
169179
}
170180

171181
const plugin = (options = {}) => {
@@ -189,10 +199,15 @@ const plugin = (options = {}) => {
189199
return;
190200
}
191201

202+
const { isSupportDataURL, isSupportAbsoluteURL } = options;
203+
192204
let parsedAtRule;
193205

194206
try {
195-
parsedAtRule = parseNode(atRule, "params", result);
207+
parsedAtRule = parseNode(atRule, "params", {
208+
isSupportAbsoluteURL,
209+
isSupportDataURL,
210+
});
196211
} catch (error) {
197212
result.warn(error.message, { node: error.node });
198213
}
@@ -223,7 +238,8 @@ const plugin = (options = {}) => {
223238
parsedAtRules.map(async (parsedAtRule) => {
224239
const {
225240
atRule,
226-
isRequestable,
241+
requestable,
242+
needResolve,
227243
prefix,
228244
url,
229245
layer,
@@ -245,7 +261,7 @@ const plugin = (options = {}) => {
245261
}
246262
}
247263

248-
if (isRequestable) {
264+
if (needResolve) {
249265
const request = requestify(url, loaderContext.rootContext);
250266
const resolvedUrl = await resolveRequests(
251267
resolver,
@@ -272,14 +288,14 @@ const plugin = (options = {}) => {
272288
supports,
273289
media,
274290
prefix,
275-
isRequestable,
291+
requestable,
276292
};
277293
}
278294

279295
atRule.remove();
280296

281297
// eslint-disable-next-line consistent-return
282-
return { url, layer, supports, media, prefix, isRequestable };
298+
return { url, layer, supports, media, prefix, requestable };
283299
})
284300
);
285301

@@ -293,10 +309,9 @@ const plugin = (options = {}) => {
293309
continue;
294310
}
295311

296-
const { url, isRequestable, layer, supports, media } =
297-
resolvedAtRule;
312+
const { url, requestable, layer, supports, media } = resolvedAtRule;
298313

299-
if (!isRequestable) {
314+
if (!requestable) {
300315
options.api.push({ url, layer, supports, media, index });
301316

302317
// eslint-disable-next-line no-continue

src/plugins/postcss-url-parser.js

+49-34
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,7 @@ import {
44
resolveRequests,
55
normalizeUrl,
66
requestify,
7-
isUrlRequestable,
8-
isDataUrl,
7+
isURLRequestable,
98
WEBPACK_IGNORE_COMMENT_REGEXP,
109
} from "../utils";
1110

@@ -48,30 +47,16 @@ function getWebpackIgnoreCommentValue(index, nodes, inBetween) {
4847
return matched && matched[2] === "true";
4948
}
5049

51-
function shouldHandleURL(url, declaration, result, options = {}) {
50+
function shouldHandleURL(url, declaration, result, options) {
5251
if (url.length === 0) {
5352
result.warn(`Unable to find uri in '${declaration.toString()}'`, {
5453
node: declaration,
5554
});
5655

57-
return false;
56+
return { requestable: false, needResolve: false };
5857
}
5958

60-
if (isDataUrl(url) && options.isSupportDataURL) {
61-
try {
62-
decodeURIComponent(url);
63-
} catch (ignoreError) {
64-
return false;
65-
}
66-
67-
return true;
68-
}
69-
70-
if (!isUrlRequestable(url, options.isSupportAbsoluteURL)) {
71-
return false;
72-
}
73-
74-
return true;
59+
return isURLRequestable(url, options);
7560
}
7661

7762
function parseDeclaration(declaration, key, result, options) {
@@ -138,15 +123,24 @@ function parseDeclaration(declaration, key, result, options) {
138123
const { nodes } = valueNode;
139124
const isStringValue = nodes.length !== 0 && nodes[0].type === "string";
140125
let url = isStringValue ? nodes[0].value : valueParser.stringify(nodes);
126+
141127
url = normalizeUrl(url, isStringValue);
142128

129+
const { requestable, needResolve } = shouldHandleURL(
130+
url,
131+
declaration,
132+
result,
133+
options
134+
);
135+
143136
// Do not traverse inside `url`
144-
if (!shouldHandleURL(url, declaration, result, options)) {
137+
if (!requestable) {
145138
// eslint-disable-next-line consistent-return
146139
return false;
147140
}
148141

149142
const queryParts = url.split("!");
143+
150144
let prefix;
151145

152146
if (queryParts.length > 1) {
@@ -161,6 +155,7 @@ function parseDeclaration(declaration, key, result, options) {
161155
prefix,
162156
url,
163157
needQuotes: false,
158+
needResolve,
164159
});
165160

166161
// eslint-disable-next-line consistent-return
@@ -194,15 +189,24 @@ function parseDeclaration(declaration, key, result, options) {
194189
let url = isStringValue
195190
? nodes[0].value
196191
: valueParser.stringify(nodes);
192+
197193
url = normalizeUrl(url, isStringValue);
198194

195+
const { requestable, needResolve } = shouldHandleURL(
196+
url,
197+
declaration,
198+
result,
199+
options
200+
);
201+
199202
// Do not traverse inside `url`
200-
if (!shouldHandleURL(url, declaration, result, options)) {
203+
if (!requestable) {
201204
// eslint-disable-next-line consistent-return
202205
return false;
203206
}
204207

205208
const queryParts = url.split("!");
209+
206210
let prefix;
207211

208212
if (queryParts.length > 1) {
@@ -217,6 +221,7 @@ function parseDeclaration(declaration, key, result, options) {
217221
prefix,
218222
url,
219223
needQuotes: false,
224+
needResolve,
220225
});
221226
} else if (type === "string") {
222227
needIgnore = getWebpackIgnoreCommentValue(
@@ -239,13 +244,21 @@ function parseDeclaration(declaration, key, result, options) {
239244

240245
let url = normalizeUrl(value, true);
241246

247+
const { requestable, needResolve } = shouldHandleURL(
248+
url,
249+
declaration,
250+
result,
251+
options
252+
);
253+
242254
// Do not traverse inside `url`
243-
if (!shouldHandleURL(url, declaration, result, options)) {
255+
if (!requestable) {
244256
// eslint-disable-next-line consistent-return
245257
return false;
246258
}
247259

248260
const queryParts = url.split("!");
261+
249262
let prefix;
250263

251264
if (queryParts.length > 1) {
@@ -260,6 +273,7 @@ function parseDeclaration(declaration, key, result, options) {
260273
prefix,
261274
url,
262275
needQuotes: true,
276+
needResolve,
263277
});
264278
}
265279
}
@@ -301,7 +315,7 @@ const plugin = (options = {}) => {
301315

302316
const resolvedDeclarations = await Promise.all(
303317
parsedDeclarations.map(async (parsedDeclaration) => {
304-
const { url } = parsedDeclaration;
318+
const { url, needResolve } = parsedDeclaration;
305319

306320
if (options.filter) {
307321
const needKeep = await options.filter(url);
@@ -312,7 +326,7 @@ const plugin = (options = {}) => {
312326
}
313327
}
314328

315-
if (isDataUrl(url)) {
329+
if (!needResolve) {
316330
// eslint-disable-next-line consistent-return
317331
return parsedDeclaration;
318332
}
@@ -323,30 +337,31 @@ const plugin = (options = {}) => {
323337
let hash = query ? "?" : "";
324338
hash += hashOrQuery ? `#${hashOrQuery}` : "";
325339

326-
const { needToResolveURL, rootContext } = options;
340+
const { resolver, rootContext } = options;
327341
const request = requestify(
328342
pathname,
329343
rootContext,
330-
needToResolveURL
344+
Boolean(resolver)
331345
);
332346

333-
if (!needToResolveURL) {
347+
if (!resolver) {
334348
// eslint-disable-next-line consistent-return
335349
return { ...parsedDeclaration, url: request, hash };
336350
}
337351

338-
const { resolver, context } = options;
339-
const resolvedUrl = await resolveRequests(resolver, context, [
340-
...new Set([request, url]),
341-
]);
352+
const resolvedURL = await resolveRequests(
353+
resolver,
354+
options.context,
355+
[...new Set([request, url])]
356+
);
342357

343-
if (!resolvedUrl) {
358+
if (!resolvedURL) {
344359
// eslint-disable-next-line consistent-return
345360
return;
346361
}
347362

348363
// eslint-disable-next-line consistent-return
349-
return { ...parsedDeclaration, url: resolvedUrl, hash };
364+
return { ...parsedDeclaration, url: resolvedURL, hash };
350365
})
351366
);
352367

@@ -391,7 +406,7 @@ const plugin = (options = {}) => {
391406
options.imports.push({
392407
type: "url",
393408
importName,
394-
url: options.needToResolveURL
409+
url: options.resolver
395410
? options.urlHandler(newUrl)
396411
: JSON.stringify(newUrl),
397412
index,

0 commit comments

Comments
 (0)