diff --git a/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css.ts b/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css.ts index df51b2e082af..457ae3994d8b 100644 --- a/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css.ts +++ b/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css.ts @@ -146,7 +146,15 @@ class CrittersExtended extends Critters { this.conditionallyInsertCspLoadingScript(document, cspNonce); } - link.prev?.setAttribute('nonce', cspNonce); + // Ideally we would hook in at the time Critters inserts the `style` tags, but there isn't + // a way of doing that at the moment so we fall back to doing it any time a `link` tag is + // inserted. We mitigate it by only iterating the direct children of the `` which + // should be pretty shallow. + document.head.children.forEach((child) => { + if (child.tagName === 'style' && !child.hasAttribute('nonce')) { + child.setAttribute('nonce', cspNonce); + } + }); } return returnValue; diff --git a/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css_spec.ts b/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css_spec.ts index d0df2b3a2de6..240ad91c3572 100644 --- a/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css_spec.ts +++ b/packages/angular_devkit/build_angular/src/utils/index-file/inline-critical-css_spec.ts @@ -133,4 +133,34 @@ describe('InlineCriticalCssProcessor', () => { html { color: white; } `); }); + + it('should not modify the document for external stylesheets', async () => { + const inlineCssProcessor = new InlineCriticalCssProcessor({ + readAsset, + }); + + const initialContent = ` + + + + + + + + + + + `; + + const { content } = await inlineCssProcessor.process(initialContent, { + outputPath: '/dist/', + }); + + expect(tags.stripIndents`${content}`).toContain(tags.stripIndents` + + + + + `); + }); });