-
Notifications
You must be signed in to change notification settings - Fork 11.9k
Description
🐞 Bug report
Command (mark with an x)
- new
- build
- serve
- test
- e2e
- generate
- add
- update
- lint
- extract-i18n
- run
- config
- help
- version
- doc
Is this a regression?
Yes, the previous version in which this bug was not present was: @angular-devkit/build-angular 14.1.1Description
When loading a CSS file containing a url that contains a closing parenthesis ) the regular expression fails to capture the full value in the url. In addition if the value contains another url expression (inside the svg markup) then the parser will try to resolve that url as well.
🔬 Minimal Reproduction
- Clone https://github.com/snocorp/angular-url-issue (Base angular app with mapbox-gl installed for CSS)
- Run
npm install - Run
ng build(orng build --verboseto see a trace of the error)
🔥 Exception or Error
./node_modules/mapbox-gl/dist/mapbox-gl.css - Error: Module Error (from ./node_modules/postcss-loader/dist/cjs.js):
/Users/dave/dev/snocorp/angular-url-issue/url-issue/node_modules/mapbox-gl/dist/mapbox-gl.css:1:28378: Can't resolve '%23clip' in '/Users/dave/dev/snocorp/angular-url-issue/url-issue/node_modules/mapbox-gl/dist'
🌍 Your Environment
_ _ ____ _ ___
/ \ _ __ __ _ _ _| | __ _ _ __ / ___| | |_ _|
/ △ \ | '_ \ / _` | | | | |/ _` | '__| | | | | | |
/ ___ \| | | | (_| | |_| | | (_| | | | |___| |___ | |
/_/ \_\_| |_|\__, |\__,_|_|\__,_|_| \____|_____|___|
|___/
Angular CLI: 14.1.3
Node: 16.15.1
Package Manager: npm 6.14.15
OS: darwin arm64
Angular: 14.1.3
... animations, cli, common, compiler, compiler-cli, core, forms
... platform-browser, platform-browser-dynamic, router
Package Version
---------------------------------------------------------
@angular-devkit/architect 0.1401.3
@angular-devkit/build-angular 14.1.3
@angular-devkit/core 14.1.3
@angular-devkit/schematics 14.1.3
@schematics/angular 14.1.3
rxjs 7.5.6
typescript 4.7.4
Anything else relevant?
This is a regression caused by #23691
The current regular expression is /url(?:\(\s*['"]?)(.*?)(?:['"]?\s*\))/g which is problematic because it can find a closing parenthesis without finding a closing quote, since the closing quote is optional.
A regular expression that solves the problem and still fixes #23680 is something like /url(?:\(\s*(['"]?))(.*?)(?:\1\s*\))/. This uses a back reference to ensure that the quotes are the same. This does mean there is an extra capturing group and so const originalUrl = match[1]; would need to be const originalUrl = match[2]; instead.
A small-ish test case:
background-image:url("data:image/svg+xml;charset=utf-8,<svg><mask id='clip'><rect x='0' y='0' width='100%' height='100%' fill='white'/></mask> <g> <circle mask='url(%23clip)' cx='11.5' cy='11.5' r='9.25'/> <use xlink:href='#text' mask='url(#clip)'/> </g></svg>")