Core Toolbar anti-flicker script adds inline style

Created on 27 August 2024, 9 months ago
Updated 28 August 2024, 8 months ago

Problem/Motivation

Just to re-hash the past here. At one point, Drupal core introduced an inline script to address a flickering issue in the toolbar. This module addressed the CSP issues from that πŸ“Œ Disable toolbar anti-flicker inline JS Fixed . Then, core moved that script to a file Toolbar anti-flicker JavaScript is no longer added inline β†’ , and this module followed suite by removing the unnecessary fix πŸ“Œ Remove code to disable inline anti-flicker js Fixed .

The new script introduced by core however now adds a new CSP issue, by adding an inline style. With a basic CSP installation on a fresh install under the standard profile, I get this error:

Refused to apply inline style because it violates the following Content Security Policy directive:  ... . Note also that 'style-src' was not explicitly set, so 'default-src' is used as a fallback.

(anonymous) @ toolbar.anti-flicker.js?v=10.3.2:62 

The corresponding code in toolbar.anti-flicker.js

    if (activeTray) {
      // These styles are added so the active tab/tray styles are present
      // immediately instead of "flickering" on as the toolbar initializes. In
      // instances where a tray is lazy loaded, these styles facilitate the
      // lazy loaded tray appearing gracefully and without reflow.
      const styleContent = `
      .toolbar-loading #${activeTabId} {
        background-image: linear-gradient(rgba(255, 255, 255, 0.25) 20%, transparent 200%);
      }
      .toolbar-loading #${activeTabId}-tray {
        display: block; box-shadow: -1px 0 5px 2px rgb(0 0 0 / 33%);
        border-right: 1px solid #aaa; background-color: #f5f5f5;
        z-index: 0;
      }
      .toolbar-loading.toolbar-vertical.toolbar-tray-open #${activeTabId}-tray {
        width: 15rem; height: 100vh;
      }
     .toolbar-loading.toolbar-horizontal :not(#${activeTray}) > .toolbar-lining {opacity: 0}`;

      const style = document.createElement('style');
      style.textContent = styleContent;
      style.setAttribute('data-toolbar-anti-flicker-loading', true);
      document.querySelector('head').appendChild(style); // Error happens here.

Steps to reproduce

Under a standard installation on any page while logged in as a user with access to the toolbar. Tested in core 10.3.2, and CSP 2.0.2

Proposed resolution

Site builders would need to add the "unsafe-inline" attribute to their style or default CSP directives. Most of them probably do already, since the need for this seems rather ubiquitous. But we can certainly strive for CSP perfection, right? I'm not really sure what the best practice here for a proposed resolution should be. replace the core script with a version in CSP that uses the nonce?

I assume it would need to add something like this:

      style.setAttribute('nonce', drupalSettings.csp.nonce);

Edit: ... Except we can't access drupalSettings in this anti-flicker script, because it's included before everything else.

🌱 Plan
Status

Active

Version

2.0

Component

Code

Created by

πŸ‡ΊπŸ‡ΈUnited States bburg Washington D.C.

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Comments & Activities

Production build 0.71.5 2024