mirror of
https://github.com/WordPress/WordPress.git
synced 2025-01-18 14:21:25 +01:00
Script Loader: Use wp_get_script_tag()
and wp_get_inline_script_tag()
/wp_print_inline_script_tag()
helper functions to output scripts on the frontend and login screen.
Using script tag helper functions allows plugins to employ the `wp_script_attributes` and `wp_inline_script_attributes` filters to inject the `nonce` attribute to apply Content Security Policy (e.g. Strict CSP). Use of helper functions also simplifies logic in `WP_Scripts`. * Update `wp_get_inline_script_tag()` to wrap inline script in CDATA blocks for XHTML-compatibility when not using HTML5. * Ensure the `type` attribute is printed first in `wp_get_inline_script_tag()` for back-compat. * Wrap existing `<script>` tags in output buffering to retain IDE supports. * In `wp_get_inline_script_tag()`, append the newline to `$javascript` before it is passed into the `wp_inline_script_attributes` filter so that the CSP hash can be computed properly. * In `the_block_template_skip_link()`, opt to enqueue the inline script rather than print it. * Add `ext-php` to `composer.json` under `suggest` as previously it was an undeclared dependency for running PHPUnit tests. * Update tests to rely on `DOMDocument` to compare script markup, normalizing unsemantic differences. Props westonruter, spacedmonkey, flixos90, 10upsimon, dmsnell, mukesh27, joemcgill, swissspidy, azaozz. Fixes #58664. See #39941. Built from https://develop.svn.wordpress.org/trunk@56687 git-svn-id: http://core.svn.wordpress.org/trunk@56199 1a063a9b-81f0-0310-95a4-ce76da25c4cd
This commit is contained in:
parent
98a0a6b5e5
commit
e7747ce23e
@ -464,6 +464,8 @@ final class WP_Customize_Manager {
|
||||
),
|
||||
'error' => $ajax_message,
|
||||
);
|
||||
$message .= ob_get_clean();
|
||||
ob_start();
|
||||
?>
|
||||
<script>
|
||||
( function( api, settings ) {
|
||||
@ -472,7 +474,7 @@ final class WP_Customize_Manager {
|
||||
} )( wp.customize, <?php echo wp_json_encode( $settings ); ?> );
|
||||
</script>
|
||||
<?php
|
||||
$message .= ob_get_clean();
|
||||
$message .= wp_get_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
wp_die( $message );
|
||||
@ -2083,6 +2085,7 @@ final class WP_Customize_Manager {
|
||||
if ( ! $this->messenger_channel ) {
|
||||
return;
|
||||
}
|
||||
ob_start();
|
||||
?>
|
||||
<script>
|
||||
( function() {
|
||||
@ -2106,6 +2109,7 @@ final class WP_Customize_Manager {
|
||||
} )();
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
@ -2201,8 +2205,9 @@ final class WP_Customize_Manager {
|
||||
}
|
||||
}
|
||||
|
||||
ob_start();
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
<script>
|
||||
var _wpCustomizeSettings = <?php echo wp_json_encode( $settings ); ?>;
|
||||
_wpCustomizeSettings.values = {};
|
||||
(function( v ) {
|
||||
@ -2225,6 +2230,7 @@ final class WP_Customize_Manager {
|
||||
})( _wpCustomizeSettings.values );
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
@ -4976,8 +4982,9 @@ final class WP_Customize_Manager {
|
||||
}
|
||||
}
|
||||
|
||||
ob_start();
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
<script>
|
||||
var _wpCustomizeSettings = <?php echo wp_json_encode( $settings ); ?>;
|
||||
_wpCustomizeSettings.initialClientTimestamp = _.now();
|
||||
_wpCustomizeSettings.controls = {};
|
||||
@ -5012,6 +5019,7 @@ final class WP_Customize_Manager {
|
||||
?>
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1559,7 +1559,7 @@ final class WP_Customize_Nav_Menus {
|
||||
$exports = array(
|
||||
'navMenuInstanceArgs' => $this->preview_nav_menu_instance_args,
|
||||
);
|
||||
printf( '<script>var _wpCustomizePreviewNavMenusExports = %s;</script>', wp_json_encode( $exports ) );
|
||||
wp_print_inline_script_tag( sprintf( 'var _wpCustomizePreviewNavMenusExports = %s;', wp_json_encode( $exports ) ) );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1310,12 +1310,9 @@ final class WP_Customize_Widgets {
|
||||
foreach ( $settings['registeredWidgets'] as &$registered_widget ) {
|
||||
unset( $registered_widget['callback'] ); // May not be JSON-serializeable.
|
||||
}
|
||||
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
var _wpWidgetCustomizerPreviewSettings = <?php echo wp_json_encode( $settings ); ?>;
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag(
|
||||
sprintf( 'var _wpWidgetCustomizerPreviewSettings = %s;', wp_json_encode( $settings ) )
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -122,17 +122,6 @@ class WP_Scripts extends WP_Dependencies {
|
||||
*/
|
||||
public $default_dirs;
|
||||
|
||||
/**
|
||||
* Holds a string which contains the type attribute for script tag.
|
||||
*
|
||||
* If the active theme does not declare HTML5 support for 'script',
|
||||
* then it initializes as `type='text/javascript'`.
|
||||
*
|
||||
* @since 5.3.0
|
||||
* @var string
|
||||
*/
|
||||
private $type_attr = '';
|
||||
|
||||
/**
|
||||
* Holds a mapping of dependents (as handles) for a given script handle.
|
||||
* Used to optimize recursive dependency tree checks.
|
||||
@ -167,14 +156,6 @@ class WP_Scripts extends WP_Dependencies {
|
||||
* @since 3.4.0
|
||||
*/
|
||||
public function init() {
|
||||
if (
|
||||
function_exists( 'is_admin' ) && ! is_admin()
|
||||
&&
|
||||
function_exists( 'current_theme_supports' ) && ! current_theme_supports( 'html5', 'script' )
|
||||
) {
|
||||
$this->type_attr = " type='text/javascript'";
|
||||
}
|
||||
|
||||
/**
|
||||
* Fires when the WP_Scripts instance is initialized.
|
||||
*
|
||||
@ -245,20 +226,7 @@ class WP_Scripts extends WP_Dependencies {
|
||||
return $output;
|
||||
}
|
||||
|
||||
printf( "<script%s id='%s-js-extra'>\n", $this->type_attr, esc_attr( $handle ) );
|
||||
|
||||
// CDATA is not needed for HTML 5.
|
||||
if ( $this->type_attr ) {
|
||||
echo "/* <![CDATA[ */\n";
|
||||
}
|
||||
|
||||
echo "$output\n";
|
||||
|
||||
if ( $this->type_attr ) {
|
||||
echo "/* ]]> */\n";
|
||||
}
|
||||
|
||||
echo "</script>\n";
|
||||
wp_print_inline_script_tag( $output, array( 'id' => "{$handle}-js-extra" ) );
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -335,7 +303,7 @@ class WP_Scripts extends WP_Dependencies {
|
||||
|
||||
$translations = $this->print_translations( $handle, false );
|
||||
if ( $translations ) {
|
||||
$translations = sprintf( "<script%s id='%s-js-translations'>\n%s\n</script>\n", $this->type_attr, esc_attr( $handle ), $translations );
|
||||
$translations = wp_get_inline_script_tag( $translations, array( 'id' => "{$handle}-js-translations" ) );
|
||||
}
|
||||
|
||||
if ( $this->do_concat ) {
|
||||
@ -403,21 +371,24 @@ class WP_Scripts extends WP_Dependencies {
|
||||
}
|
||||
|
||||
/** This filter is documented in wp-includes/class-wp-scripts.php */
|
||||
$src = esc_url( apply_filters( 'script_loader_src', $src, $handle ) );
|
||||
$src = esc_url_raw( apply_filters( 'script_loader_src', $src, $handle ) );
|
||||
|
||||
if ( ! $src ) {
|
||||
return true;
|
||||
}
|
||||
|
||||
$tag = $translations . $cond_before . $before_script;
|
||||
$tag .= sprintf(
|
||||
"<script%s src='%s' id='%s-js'%s%s></script>\n",
|
||||
$this->type_attr,
|
||||
$src, // Value is escaped above.
|
||||
esc_attr( $handle ),
|
||||
$strategy ? " {$strategy}" : '',
|
||||
$intended_strategy ? " data-wp-strategy='{$intended_strategy}'" : ''
|
||||
$attr = array(
|
||||
'src' => $src,
|
||||
'id' => "{$handle}-js",
|
||||
);
|
||||
if ( $strategy ) {
|
||||
$attr[ $strategy ] = true;
|
||||
}
|
||||
if ( $intended_strategy ) {
|
||||
$attr['data-wp-strategy'] = $intended_strategy;
|
||||
}
|
||||
$tag = $translations . $cond_before . $before_script;
|
||||
$tag .= wp_get_script_tag( $attr );
|
||||
$tag .= $after_script . $cond_after;
|
||||
|
||||
/**
|
||||
@ -720,7 +691,7 @@ class WP_Scripts extends WP_Dependencies {
|
||||
JS;
|
||||
|
||||
if ( $display ) {
|
||||
printf( "<script%s id='%s-js-translations'>\n%s\n</script>\n", $this->type_attr, esc_attr( $handle ), $output );
|
||||
wp_print_inline_script_tag( $output, array( 'id' => "{$handle}-js-translations" ) );
|
||||
}
|
||||
|
||||
return $output;
|
||||
|
@ -1366,7 +1366,7 @@ function wp_comment_form_unfiltered_html_nonce() {
|
||||
|
||||
if ( current_user_can( 'unfiltered_html' ) ) {
|
||||
wp_nonce_field( 'unfiltered-html-comment_' . $post_id, '_wp_unfiltered_html_comment_disabled', false );
|
||||
echo "<script>(function(){if(window===window.parent){document.getElementById('_wp_unfiltered_html_comment_disabled').name='_wp_unfiltered_html_comment';}})();</script>\n";
|
||||
wp_print_inline_script_tag( "(function(){if(window===window.parent){document.getElementById('_wp_unfiltered_html_comment_disabled').name='_wp_unfiltered_html_comment';}})();" );
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -193,7 +193,7 @@ final class WP_Customize_Selective_Refresh {
|
||||
);
|
||||
|
||||
// Export data to JS.
|
||||
printf( '<script>var _customizePartialRefreshExports = %s;</script>', wp_json_encode( $exports ) );
|
||||
wp_print_inline_script_tag( sprintf( 'var _customizePartialRefreshExports = %s;', wp_json_encode( $exports ) ) );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -7655,6 +7655,7 @@ function wp_post_preview_js() {
|
||||
// Has to match the window name used in post_submit_meta_box().
|
||||
$name = 'wp-preview-' . (int) $post->ID;
|
||||
|
||||
ob_start();
|
||||
?>
|
||||
<script>
|
||||
( function() {
|
||||
@ -7670,6 +7671,7 @@ function wp_post_preview_js() {
|
||||
}());
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -2787,7 +2787,11 @@ function wp_sanitize_script_attributes( $attributes ) {
|
||||
*/
|
||||
function wp_get_script_tag( $attributes ) {
|
||||
if ( ! isset( $attributes['type'] ) && ! is_admin() && ! current_theme_supports( 'html5', 'script' ) ) {
|
||||
$attributes['type'] = 'text/javascript';
|
||||
// Keep the type attribute as the first for legacy reasons (it has always been this way in core).
|
||||
$attributes = array_merge(
|
||||
array( 'type' => 'text/javascript' ),
|
||||
$attributes
|
||||
);
|
||||
}
|
||||
/**
|
||||
* Filters attributes to be added to a script tag.
|
||||
@ -2830,9 +2834,23 @@ function wp_print_script_tag( $attributes ) {
|
||||
* @return string String containing inline JavaScript code wrapped around `<script>` tag.
|
||||
*/
|
||||
function wp_get_inline_script_tag( $javascript, $attributes = array() ) {
|
||||
if ( ! isset( $attributes['type'] ) && ! is_admin() && ! current_theme_supports( 'html5', 'script' ) ) {
|
||||
$attributes['type'] = 'text/javascript';
|
||||
$is_html5 = current_theme_supports( 'html5', 'script' ) || is_admin();
|
||||
if ( ! isset( $attributes['type'] ) && ! $is_html5 ) {
|
||||
// Keep the type attribute as the first for legacy reasons (it has always been this way in core).
|
||||
$attributes = array_merge(
|
||||
array( 'type' => 'text/javascript' ),
|
||||
$attributes
|
||||
);
|
||||
}
|
||||
|
||||
// Ensure markup is XHTML compatible if not HTML5.
|
||||
if ( ! $is_html5 ) {
|
||||
$javascript = str_replace( ']]>', ']]]]><![CDATA[>', $javascript ); // Escape any existing CDATA section.
|
||||
$javascript = sprintf( "/* <![CDATA[ */\n%s\n/* ]]> */", $javascript );
|
||||
}
|
||||
|
||||
$javascript = "\n" . trim( $javascript, "\n\r " ) . "\n";
|
||||
|
||||
/**
|
||||
* Filters attributes to be added to a script tag.
|
||||
*
|
||||
@ -2845,8 +2863,6 @@ function wp_get_inline_script_tag( $javascript, $attributes = array() ) {
|
||||
*/
|
||||
$attributes = apply_filters( 'wp_inline_script_attributes', $attributes, $javascript );
|
||||
|
||||
$javascript = "\n" . trim( $javascript, "\n\r " ) . "\n";
|
||||
|
||||
return sprintf( "<script%s>%s</script>\n", wp_sanitize_script_attributes( $attributes ), $javascript );
|
||||
}
|
||||
|
||||
|
@ -160,8 +160,9 @@ function the_block_template_skip_link() {
|
||||
wp_enqueue_style( $handle );
|
||||
|
||||
/**
|
||||
* Print the skip-link script.
|
||||
* Enqueue the skip-link script.
|
||||
*/
|
||||
ob_start();
|
||||
?>
|
||||
<script>
|
||||
( function() {
|
||||
@ -204,6 +205,11 @@ function the_block_template_skip_link() {
|
||||
}() );
|
||||
</script>
|
||||
<?php
|
||||
$skip_link_script = str_replace( array( '<script>', '</script>' ), '', ob_get_clean() );
|
||||
$script_handle = 'wp-block-template-skip-link';
|
||||
wp_register_script( $script_handle, false );
|
||||
wp_add_inline_script( $script_handle, $skip_link_script );
|
||||
wp_enqueue_script( $script_handle );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -3783,9 +3783,9 @@ function wp_customize_support_script() {
|
||||
$admin_origin = parse_url( admin_url() );
|
||||
$home_origin = parse_url( home_url() );
|
||||
$cross_domain = ( strtolower( $admin_origin['host'] ) !== strtolower( $home_origin['host'] ) );
|
||||
$type_attr = current_theme_supports( 'html5', 'script' ) ? '' : ' type="text/javascript"';
|
||||
ob_start();
|
||||
?>
|
||||
<script<?php echo $type_attr; ?>>
|
||||
<script>
|
||||
(function() {
|
||||
var request, b = document.body, c = 'className', cs = 'customize-support', rcs = new RegExp('(^|\\s+)(no-)?'+cs+'(\\s+|$)');
|
||||
|
||||
@ -3801,6 +3801,7 @@ function wp_customize_support_script() {
|
||||
}());
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -16,7 +16,7 @@
|
||||
*
|
||||
* @global string $wp_version
|
||||
*/
|
||||
$wp_version = '6.4-alpha-56686';
|
||||
$wp_version = '6.4-alpha-56687';
|
||||
|
||||
/**
|
||||
* Holds the WordPress DB revision, increments when changes are made to the WordPress DB schema.
|
||||
|
@ -100,8 +100,6 @@ class WP_Widget_Archives extends WP_Widget {
|
||||
$label = __( 'Select Post' );
|
||||
break;
|
||||
}
|
||||
|
||||
$type_attr = current_theme_supports( 'html5', 'script' ) ? '' : ' type="text/javascript"';
|
||||
?>
|
||||
|
||||
<option value=""><?php echo esc_html( $label ); ?></option>
|
||||
@ -109,8 +107,8 @@ class WP_Widget_Archives extends WP_Widget {
|
||||
|
||||
</select>
|
||||
|
||||
<script<?php echo $type_attr; ?>>
|
||||
/* <![CDATA[ */
|
||||
<?php ob_start(); ?>
|
||||
<script>
|
||||
(function() {
|
||||
var dropdown = document.getElementById( "<?php echo esc_js( $dropdown_id ); ?>" );
|
||||
function onSelectChange() {
|
||||
@ -120,9 +118,9 @@ class WP_Widget_Archives extends WP_Widget {
|
||||
}
|
||||
dropdown.onchange = onSelectChange;
|
||||
})();
|
||||
/* ]]> */
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
} else {
|
||||
$format = current_theme_supports( 'html5', 'navigation-widgets' ) ? 'html5' : 'xhtml';
|
||||
|
||||
|
@ -92,11 +92,10 @@ class WP_Widget_Categories extends WP_Widget {
|
||||
|
||||
echo '</form>';
|
||||
|
||||
$type_attr = current_theme_supports( 'html5', 'script' ) ? '' : ' type="text/javascript"';
|
||||
ob_start();
|
||||
?>
|
||||
|
||||
<script<?php echo $type_attr; ?>>
|
||||
/* <![CDATA[ */
|
||||
<script>
|
||||
(function() {
|
||||
var dropdown = document.getElementById( "<?php echo esc_js( $dropdown_id ); ?>" );
|
||||
function onCatChange() {
|
||||
@ -106,10 +105,10 @@ class WP_Widget_Categories extends WP_Widget {
|
||||
}
|
||||
dropdown.onchange = onCatChange;
|
||||
})();
|
||||
/* ]]> */
|
||||
</script>
|
||||
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
} else {
|
||||
$format = current_theme_supports( 'html5', 'navigation-widgets' ) ? 'html5' : 'xhtml';
|
||||
|
||||
|
33
wp-login.php
33
wp-login.php
@ -101,9 +101,11 @@ function login_header( $title = 'Log In', $message = '', $wp_error = null ) {
|
||||
* but maybe better if it's not removable by plugins.
|
||||
*/
|
||||
if ( 'loggedout' === $wp_error->get_error_code() ) {
|
||||
ob_start();
|
||||
?>
|
||||
<script>if("sessionStorage" in window){try{for(var key in sessionStorage){if(key.indexOf("wp-autosave-")!=-1){sessionStorage.removeItem(key)}}}catch(e){}};</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
@ -193,9 +195,10 @@ function login_header( $title = 'Log In', $message = '', $wp_error = null ) {
|
||||
?>
|
||||
</head>
|
||||
<body class="login no-js <?php echo esc_attr( implode( ' ', $classes ) ); ?>">
|
||||
<script type="text/javascript">
|
||||
document.body.className = document.body.className.replace('no-js','js');
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( "document.body.className = document.body.className.replace('no-js','js');" );
|
||||
?>
|
||||
|
||||
<?php
|
||||
/**
|
||||
* Fires in the login page header after the body tag is opened.
|
||||
@ -414,12 +417,14 @@ function login_footer( $input_id = '' ) {
|
||||
<?php
|
||||
|
||||
if ( ! empty( $input_id ) ) {
|
||||
ob_start();
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
<script>
|
||||
try{document.getElementById('<?php echo $input_id; ?>').focus();}catch(e){}
|
||||
if(typeof wpOnload==='function')wpOnload();
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
/**
|
||||
@ -441,11 +446,7 @@ function login_footer( $input_id = '' ) {
|
||||
* @since 3.0.0
|
||||
*/
|
||||
function wp_shake_js() {
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
document.querySelector('form').classList.add('shake');
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( "document.querySelector('form').classList.add('shake');" );
|
||||
}
|
||||
|
||||
/**
|
||||
@ -1357,9 +1358,11 @@ switch ( $action ) {
|
||||
do_action( 'login_footer' );
|
||||
|
||||
if ( $customize_login ) {
|
||||
ob_start();
|
||||
?>
|
||||
<script type="text/javascript">setTimeout( function(){ new wp.customize.Messenger({ url: '<?php echo wp_customize_url(); ?>', channel: 'login' }).send('login') }, 1000 );</script>
|
||||
<script>setTimeout( function(){ new wp.customize.Messenger({ url: '<?php echo wp_customize_url(); ?>', channel: 'login' }).send('login') }, 1000 );</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
?>
|
||||
@ -1605,15 +1608,12 @@ switch ( $action ) {
|
||||
// Run `wpOnload()` if defined.
|
||||
$login_script .= "if ( typeof wpOnload === 'function' ) { wpOnload() }";
|
||||
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
<?php echo $login_script; ?>
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( $login_script );
|
||||
|
||||
if ( $interim_login ) {
|
||||
ob_start();
|
||||
?>
|
||||
<script type="text/javascript">
|
||||
<script>
|
||||
( function() {
|
||||
try {
|
||||
var i, links = document.getElementsByTagName( 'a' );
|
||||
@ -1627,6 +1627,7 @@ switch ( $action ) {
|
||||
}());
|
||||
</script>
|
||||
<?php
|
||||
wp_print_inline_script_tag( str_replace( array( '<script>', '</script>' ), '', ob_get_clean() ) );
|
||||
}
|
||||
|
||||
login_footer();
|
||||
|
Loading…
Reference in New Issue
Block a user