get_all_settings();
if ( empty( $s['dns_prefetch'] ) && empty( $s['dns_prefetch_auto'] ) && empty( $s['modulepreload_enabled'] ) ) {
return;
}
add_action( 'wp_head', array( $this, 'emit' ), 1 );
}
public function emit() {
// The queried post is unavailable during plugins_loaded.
if ( ! \QWSpeedCache\Plugin::should_optimize() ) {
return;
}
$s = \QWSpeedCache\Plugin::instance()->get_all_settings();
$seen = array();
// Manual lines: "https://cdn.example.com" or "preconnect https://..."
$manual = isset( $s['dns_prefetch'] ) ? (string) $s['dns_prefetch'] : '';
foreach ( preg_split( '/\r\n|\r|\n/', $manual ) as $line ) {
$line = trim( $line );
if ( '' === $line || 0 === strpos( $line, '#' ) ) {
continue;
}
$preconnect = false;
if ( 0 === stripos( $line, 'preconnect ' ) ) {
$preconnect = true;
$line = trim( substr( $line, 11 ) );
}
$host = self::origin_from( $line );
if ( ! $host || isset( $seen[ $host ] ) ) {
continue;
}
$seen[ $host ] = true;
if ( $preconnect || ! empty( $s['dns_preconnect'] ) ) {
echo '' . "\n";
} else {
echo '' . "\n";
}
}
if ( ! empty( $s['dns_prefetch_auto'] ) ) {
$limit = isset( $s['dns_prefetch_auto_limit'] ) ? max( 1, min( 20, (int) $s['dns_prefetch_auto_limit'] ) ) : 8;
foreach ( self::auto_origins( $limit ) as $origin ) {
if ( isset( $seen[ $origin ] ) ) {
continue;
}
$seen[ $origin ] = true;
if ( ! empty( $s['dns_preconnect'] ) ) {
echo '' . "\n";
} else {
echo '' . "\n";
}
}
}
if ( ! empty( $s['modulepreload_enabled'] ) ) {
foreach ( self::modulepreload_urls( 5 ) as $url ) {
echo '' . "\n";
}
}
}
/**
* @param string $url URL or host.
* @return string Origin https://host or empty.
*/
public static function origin_from( $url ) {
$url = trim( (string) $url );
if ( '' === $url ) {
return '';
}
if ( 0 === strpos( $url, '//' ) ) {
$url = 'https:' . $url;
}
if ( ! preg_match( '#^https?://#i', $url ) ) {
$url = 'https://' . ltrim( $url, '/' );
}
$url = esc_url_raw( $url, array( 'http', 'https' ) );
$parts = wp_parse_url( $url );
if ( ! is_array( $parts ) || empty( $parts['host'] ) || ! is_string( $parts['host'] ) ) {
return '';
}
// Do not emit preconnect origins containing credentials or malformed hosts.
if ( isset( $parts['user'] ) || isset( $parts['pass'] ) || ! preg_match( '/^[a-z0-9.-]+$/i', $parts['host'] ) ) {
return '';
}
$scheme = isset( $parts['scheme'] ) ? $parts['scheme'] : 'https';
if ( ! in_array( $scheme, array( 'http', 'https' ), true ) ) {
$scheme = 'https';
}
return $scheme . '://' . strtolower( $parts['host'] );
}
/**
* Third-party origins from enqueued assets.
*
* @param int $limit Max origins.
* @return string[]
*/
public static function auto_origins( $limit = 8 ) {
$home = function_exists( 'home_url' ) ? wp_parse_url( home_url(), PHP_URL_HOST ) : '';
$home = $home ? strtolower( (string) $home ) : '';
$out = array();
global $wp_scripts, $wp_styles;
foreach ( array( $wp_scripts, $wp_styles ) as $reg ) {
if ( ! is_object( $reg ) || empty( $reg->queue ) || empty( $reg->registered ) ) {
continue;
}
foreach ( (array) $reg->queue as $handle ) {
if ( empty( $reg->registered[ $handle ]->src ) ) {
continue;
}
$src = (string) $reg->registered[ $handle ]->src;
$origin = self::origin_from( $src );
if ( ! $origin ) {
continue;
}
$host = wp_parse_url( $origin, PHP_URL_HOST );
if ( $home && strtolower( (string) $host ) === $home ) {
continue;
}
$out[ $origin ] = true;
if ( count( $out ) >= $limit ) {
return array_keys( $out );
}
}
}
return array_keys( $out );
}
/**
* First N type=module script srcs.
*
* @param int $limit Max.
* @return string[]
*/
public static function modulepreload_urls( $limit = 5 ) {
$out = array();
global $wp_scripts;
if ( ! is_object( $wp_scripts ) || empty( $wp_scripts->queue ) ) {
return $out;
}
foreach ( (array) $wp_scripts->queue as $handle ) {
if ( empty( $wp_scripts->registered[ $handle ] ) ) {
continue;
}
$obj = $wp_scripts->registered[ $handle ];
$src = isset( $obj->src ) ? (string) $obj->src : '';
if ( ! $src ) {
continue;
}
// Heuristic: handle or extra data marks module.
$extra = isset( $obj->extra['strategy'] ) ? $obj->extra['strategy'] : '';
$type = isset( $obj->extra['type'] ) ? $obj->extra['type'] : '';
if ( 'module' !== $type && 'module' !== $extra && false === strpos( $handle, 'module' ) ) {
continue;
}
if ( 0 === strpos( $src, '/' ) && function_exists( 'home_url' ) ) {
$src = home_url( $src );
}
$out[] = $src;
if ( count( $out ) >= $limit ) {
break;
}
}
return $out;
}
}