Wp-rocket: Delay JS/Preload links - inline scripts not added in WordPress prior to 5.0

Created on 16 Sep 2020  Â·  7Comments  Â·  Source: wp-media/wp-rocket

Before submitting an issue please check that you’ve completed the following steps:

  • Made sure you’re on the latest version ✅
  • Used the search feature to ensure that the bug hasn’t been reported before ✅

Describe the bug

The Delay JavaScript execution and Preload links features rely on the inline JavaScript WP Rocket adds on the page.

We are using wp_add_inline_script() to enqueue the scripts:
https://github.com/wp-media/wp-rocket/blob/8f7f67b621e5085ccf6424a08a15ce636e4fbf2f/inc/Engine/Optimization/DelayJS/Subscriber.php#L91

That isn't working as expected in WordPress < 5.0 when there isn't any source. The scripts are properly in $wp_scripts but are not printed to the page, and this results in the features not working and/or breaking the page or features. For example, Google Ads are not displayed.

Related WordPress ticket where the fix is mentioned.

To Reproduce
Steps to reproduce the behavior:

  1. Use WordPress 4.9.15.
  2. Enable Dealy JavaScript Execution.
  3. Pick a script to delay.
  4. Load the page. The script will not be loaded after interacting with the page.

Expected behavior
The features should work with WordPress 4.9.

Screencasts

Additional context
Related ticket: https://secure.helpscout.net/conversation/1278600269/193807?folderId=2135277
Slack discussion: https://wp-media.slack.com/archives/C43T1AYMQ/p1600257143184300

Backlog Grooming (for WP Media dev team use only)

  • [ ] Reproduce the problem
  • [ ] Identify the root cause
  • [ ] Scope a solution
  • [ ] Estimate the effort
delay JS preload low bug wontfix

Most helpful comment

Just had to do a workaround for this in WP 4.9

if ( version_compare( $GLOBALS['wp_version'], '5.0.0', '<' ) ) {
  add_action('wp_print_footer_scripts', function() {
    $wp_scripts = wp_scripts();
    $done_scripts = wp_scripts()->done;

    foreach ($done_scripts as $handle) {
      $obj = $wp_scripts->registered[$handle];

      // not interested in those as they have src
      if ($obj->src) {
        continue;
      }

      $cond_before = '';
      $cond_after  = '';
      $conditional = isset( $obj->extra['conditional'] ) ? $obj->extra['conditional'] : '';

      if ( $conditional ) {
        $cond_before = "<!--[if {$conditional}]>\n";
        $cond_after  = "<![endif]-->\n";
      }

      $before_handle = $wp_scripts->print_inline_script( $handle, 'before', false );
      $after_handle  = $wp_scripts->print_inline_script( $handle, 'after', false );

      if ( $before_handle ) {
        $before_handle = sprintf( "<script%s>\n%s\n</script>\n", $wp_scripts->type_attr, $before_handle );
      }

      if ( $after_handle ) {
        $after_handle = sprintf( "<script%s>\n%s\n</script>\n", $wp_scripts->type_attr, $after_handle );
      }

      if ( $before_handle || $after_handle ) {
        $inline_script_tag = $cond_before . $before_handle . $after_handle . $cond_after;
      } else {
        $inline_script_tag = '';
      }

      if ( $inline_script_tag ) {
        echo $inline_script_tag;
      }
    }

  }, PHP_INT_MAX );
}

All 7 comments

If fixing this is complicated and since we plan to drop support for pre WordPress 5.0 anyway, we could instead grey out the options that need WordPress 5.0 to function with a UI note.

We can have a variant of the code that would be directly outputting the scripts using the wp_footer action hook.

Thanks for the input Remy.

As per our Mixpanel data, we have less than 1.5% of our users using pre 5.0 versions of WordPress. Given that we need 100% of our dev efforts on more important tasks right now, I think it's best to not work on this (just as you suggested).

Going to remove the needs: grooming label so that we do not have to work on this now and can come back to it later if needed.

Just had to do a workaround for this in WP 4.9

if ( version_compare( $GLOBALS['wp_version'], '5.0.0', '<' ) ) {
  add_action('wp_print_footer_scripts', function() {
    $wp_scripts = wp_scripts();
    $done_scripts = wp_scripts()->done;

    foreach ($done_scripts as $handle) {
      $obj = $wp_scripts->registered[$handle];

      // not interested in those as they have src
      if ($obj->src) {
        continue;
      }

      $cond_before = '';
      $cond_after  = '';
      $conditional = isset( $obj->extra['conditional'] ) ? $obj->extra['conditional'] : '';

      if ( $conditional ) {
        $cond_before = "<!--[if {$conditional}]>\n";
        $cond_after  = "<![endif]-->\n";
      }

      $before_handle = $wp_scripts->print_inline_script( $handle, 'before', false );
      $after_handle  = $wp_scripts->print_inline_script( $handle, 'after', false );

      if ( $before_handle ) {
        $before_handle = sprintf( "<script%s>\n%s\n</script>\n", $wp_scripts->type_attr, $before_handle );
      }

      if ( $after_handle ) {
        $after_handle = sprintf( "<script%s>\n%s\n</script>\n", $wp_scripts->type_attr, $after_handle );
      }

      if ( $before_handle || $after_handle ) {
        $inline_script_tag = $cond_before . $before_handle . $after_handle . $cond_after;
      } else {
        $inline_script_tag = '';
      }

      if ( $inline_script_tag ) {
        echo $inline_script_tag;
      }
    }

  }, PHP_INT_MAX );
}

I only found this now, after coming up with this code to fix the issue:

add_action( 'wp_footer', function() {
  global $wp_scripts;
  $wp_scripts->print_inline_script('rocket-browser-checker');
  $wp_scripts->print_inline_script('rocket-delay-js');

}, PHP_INT_MAX );

It prints the inline JS for these specific scripts - the delayed JS execution and it's dependency.

It's too bad you do not care about WordPress 4.9 anymore.

I added the wontfix label as since 3.8, the minimum WordPress version required is 5.2.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

jbma picture jbma  Â·  5Comments

webtrainingwheels picture webtrainingwheels  Â·  5Comments

webtrainingwheels picture webtrainingwheels  Â·  5Comments

aniatanasova picture aniatanasova  Â·  5Comments

Tabrisrp picture Tabrisrp  Â·  4Comments