diff --git a/src/wp-includes/functions.php b/src/wp-includes/functions.php
index 537425d8981ab..164fae9bc1c00 100644
--- a/src/wp-includes/functions.php
+++ b/src/wp-includes/functions.php
@@ -7773,3 +7773,123 @@ function is_php_version_compatible( $required ) {
function wp_fuzzy_number_match( $expected, $actual, $precision = 1 ) {
return abs( (float) $expected - (float) $actual ) <= $precision;
}
+
+/**
+ * Sanitizes an attributes array into an attributes string to be placed inside a `\n", wp_sanitize_script_attributes( $attributes ) );
+}
+
+/**
+ * Prints formatted `\n", wp_sanitize_script_attributes( $attributes ), $javascript );
+}
+
+/**
+ * Prints inline JavaScript wrapped in `\n",
+ wp_get_inline_script_tag(
+ $this->event_handler,
+ array(
+ 'type' => 'application/javascript',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+
+ $this->assertSame(
+ '\n",
+ wp_get_inline_script_tag(
+ $this->event_handler,
+ array(
+ 'type' => 'application/javascript',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+ }
+
+ function test_get_inline_script_tag_type_not_set() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ "\n",
+ wp_get_inline_script_tag(
+ $this->event_handler,
+ array(
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+ function test_get_inline_script_tag_unescaped_src() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ "\n",
+ wp_get_inline_script_tag( $this->event_handler )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+ function test_print_script_tag_prints_get_inline_script_tag() {
+ add_filter(
+ 'wp_script_attributes',
+ function ( $attributes ) {
+ if ( isset( $attributes['id'] ) && 'utils-js-extra' === $attributes['id'] ) {
+ $attributes['async'] = true;
+ }
+ return $attributes;
+ }
+ );
+
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $attributes = array(
+ 'id' => 'utils-js-before',
+ 'nomodule' => true,
+ );
+
+ $this->assertSame(
+ wp_get_inline_script_tag( $this->event_handler, $attributes ),
+ get_echo(
+ 'wp_print_inline_script_tag',
+ array(
+ $this->event_handler,
+ $attributes,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+
+ $this->assertSame(
+ wp_get_inline_script_tag( $this->event_handler, $attributes ),
+ get_echo(
+ 'wp_print_inline_script_tag',
+ array(
+ $this->event_handler,
+ $attributes,
+ )
+ )
+ );
+ }
+}
diff --git a/tests/phpunit/tests/functions/wpSanitizeScriptAttributes.php b/tests/phpunit/tests/functions/wpSanitizeScriptAttributes.php
new file mode 100644
index 0000000000000..dd060ebd5daf4
--- /dev/null
+++ b/tests/phpunit/tests/functions/wpSanitizeScriptAttributes.php
@@ -0,0 +1,130 @@
+assertSame(
+ ' type="application/javascript" src="https://DOMAIN.TLD/PATH/FILE.js" nomodule',
+ wp_sanitize_script_attributes(
+ array(
+ 'type' => 'application/javascript',
+ 'src' => 'https://DOMAIN.TLD/PATH/FILE.js',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+
+ $this->assertSame(
+ ' src="https://DOMAIN.TLD/PATH/FILE.js" type="application/javascript" nomodule="nomodule"',
+ wp_sanitize_script_attributes(
+ array(
+ 'src' => 'https://DOMAIN.TLD/PATH/FILE.js',
+ 'type' => 'application/javascript',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+ }
+
+ function test_sanitize_script_attributes_type_not_set() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ ' src="https://DOMAIN.TLD/PATH/FILE.js" nomodule',
+ wp_sanitize_script_attributes(
+ array(
+ 'src' => 'https://DOMAIN.TLD/PATH/FILE.js',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+
+ $this->assertSame(
+ ' src="https://DOMAIN.TLD/PATH/FILE.js" nomodule="nomodule"',
+ wp_sanitize_script_attributes(
+ array(
+ 'src' => 'https://DOMAIN.TLD/PATH/FILE.js',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+ }
+
+
+ function test_sanitize_script_attributes_no_attributes() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ '',
+ wp_sanitize_script_attributes( array() )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+ function test_sanitize_script_attributes_relative_src() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ ' src="PATH/FILE.js" nomodule',
+ wp_sanitize_script_attributes(
+ array(
+ 'src' => 'PATH/FILE.js',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+
+ function test_sanitize_script_attributes_only_false_boolean_attributes() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ '',
+ wp_sanitize_script_attributes(
+ array(
+ 'async' => false,
+ 'nomodule' => false,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+ function test_sanitize_script_attributes_only_true_boolean_attributes() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ ' async nomodule',
+ wp_sanitize_script_attributes(
+ array(
+ 'async' => true,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+}
diff --git a/tests/phpunit/tests/functions/wpScriptTag.php b/tests/phpunit/tests/functions/wpScriptTag.php
new file mode 100644
index 0000000000000..3c451f5359cad
--- /dev/null
+++ b/tests/phpunit/tests/functions/wpScriptTag.php
@@ -0,0 +1,94 @@
+assertSame(
+ '' . "\n",
+ wp_get_script_tag(
+ array(
+ 'type' => 'application/javascript',
+ 'src' => 'https://localhost/PATH/FILE.js',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+
+ $this->assertSame(
+ '' . "\n",
+ wp_get_script_tag(
+ array(
+ 'src' => 'https://localhost/PATH/FILE.js',
+ 'type' => 'application/javascript',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+ }
+
+ function test_get_script_tag_type_not_set() {
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $this->assertSame(
+ '' . "\n",
+ wp_get_script_tag(
+ array(
+ 'src' => 'https://localhost/PATH/FILE.js',
+ 'async' => false,
+ 'nomodule' => true,
+ )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+ }
+
+ function test_print_script_tag_prints_get_script_tag() {
+ add_filter(
+ 'wp_script_attributes',
+ function ( $attributes ) {
+ if ( isset( $attributes['id'] ) && 'utils-js-extra' === $attributes['id'] ) {
+ $attributes['async'] = true;
+ }
+ return $attributes;
+ }
+ );
+
+ add_theme_support( 'html5', array( 'script' ) );
+
+ $attributes = array(
+ 'src' => 'https://localhost/PATH/FILE.js',
+ 'id' => 'utils-js-extra',
+ 'nomodule' => true,
+ );
+
+ $this->assertSame(
+ wp_get_script_tag( $attributes ),
+ get_echo(
+ 'wp_print_script_tag',
+ array( $attributes )
+ )
+ );
+
+ remove_theme_support( 'html5' );
+
+ $this->assertSame(
+ wp_get_script_tag( $attributes ),
+ get_echo(
+ 'wp_print_script_tag',
+ array( $attributes )
+ )
+ );
+ }
+}