settings = \QWSpeedCache\Plugin::instance()->get_all_settings();
// Heartbeat control applies in admin regardless of front-end optimize gate.
if ( ! empty( $this->settings['heartbeat_control'] ) ) {
add_filter( 'heartbeat_settings', array( $this, 'heartbeat' ) );
add_action( 'init', array( $this, 'maybe_disable_heartbeat' ), 1 );
}
if ( ! empty( $this->settings['dns_prefetch'] ) || ! empty( $this->settings['dns_prefetch_auto'] ) ) {
add_action( 'wp_head', array( $this, 'maybe_dns_prefetch' ), 1 );
}
}
/**
* Evaluate post-specific optimization exclusions after the main query.
*/
public function maybe_dns_prefetch() {
if ( ! \QWSpeedCache\Plugin::should_optimize() ) {
return;
}
$this->dns_prefetch();
}
/**
* Emit dns-prefetch and optional preconnect tags.
* Lines may be host URLs, or "preconnect https://example.com".
*/
public function dns_prefetch() {
$seen = array();
$hosts = array_filter( array_map( 'trim', explode( "\n", (string) ( $this->settings['dns_prefetch'] ?? '' ) ) ) );
foreach ( $hosts as $line ) {
if ( '' === $line || 0 === strpos( $line, '#' ) ) {
continue;
}
$preconnect = false;
if ( 0 === stripos( $line, 'preconnect ' ) ) {
$preconnect = true;
$line = trim( substr( $line, 10 ) );
}
$host = esc_url( $line );
if ( ! $host ) {
continue;
}
$key = strtolower( $host );
if ( isset( $seen[ $key ] ) ) {
continue;
}
$seen[ $key ] = true;
echo '' . "\n";
if ( $preconnect || ! empty( $this->settings['dns_preconnect'] ) ) {
echo '' . "\n";
}
}
if ( ! empty( $this->settings['dns_prefetch_auto'] ) ) {
foreach ( self::collect_external_hosts() as $origin ) {
$key = strtolower( $origin );
if ( isset( $seen[ $key ] ) ) {
continue;
}
$seen[ $key ] = true;
echo '' . "\n";
if ( ! empty( $this->settings['dns_preconnect'] ) ) {
echo '' . "\n";
}
}
}
}
/**
* External origins from registered front-end scripts and styles.
*
* @return string[]
*/
public static function collect_external_hosts() {
$out = array();
$site_host = function_exists( 'home_url' ) ? wp_parse_url( home_url(), PHP_URL_HOST ) : '';
$site_host = $site_host ? strtolower( (string) $site_host ) : '';
$limit = 8;
if ( class_exists( '\QWSpeedCache\Plugin' ) ) {
$s = \QWSpeedCache\Plugin::instance()->get_all_settings();
$limit = isset( $s['dns_prefetch_auto_limit'] ) ? (int) $s['dns_prefetch_auto_limit'] : 8;
$limit = max( 1, min( 20, $limit ) );
}
global $wp_scripts, $wp_styles;
$queues = array();
if ( isset( $wp_scripts ) && is_object( $wp_scripts ) && ! empty( $wp_scripts->queue ) && is_array( $wp_scripts->queue ) ) {
$queues[] = array( $wp_scripts, $wp_scripts->queue );
}
if ( isset( $wp_styles ) && is_object( $wp_styles ) && ! empty( $wp_styles->queue ) && is_array( $wp_styles->queue ) ) {
$queues[] = array( $wp_styles, $wp_styles->queue );
}
foreach ( $queues as $pair ) {
list( $reg, $queue ) = $pair;
foreach ( $queue as $handle ) {
if ( empty( $reg->registered[ $handle ]->src ) ) {
continue;
}
$src = (string) $reg->registered[ $handle ]->src;
if ( 0 === strpos( $src, '//' ) ) {
$src = 'https:' . $src;
}
if ( ! preg_match( '#^https?://#i', $src ) ) {
continue;
}
$host = wp_parse_url( $src, PHP_URL_HOST );
$scheme = wp_parse_url( $src, PHP_URL_SCHEME );
if ( ! $host || ! $scheme ) {
continue;
}
if ( $site_host && strtolower( (string) $host ) === $site_host ) {
continue;
}
$origin = strtolower( $scheme ) . '://' . strtolower( (string) $host );
$out[ $origin ] = $origin;
if ( count( $out ) >= $limit ) {
return array_values( $out );
}
}
}
return array_values( $out );
}
/**
* Disable Heartbeat on front when configured.
*/
public function maybe_disable_heartbeat() {
if ( empty( $this->settings['heartbeat_disable_front'] ) ) {
return;
}
if ( is_admin() ) {
return;
}
wp_deregister_script( 'heartbeat' );
}
/**
* @param array $settings Heartbeat settings.
* @return array
*/
public function heartbeat( $settings ) {
$freq = (int) ( $this->settings['heartbeat_frequency'] ?? 60 );
if ( $freq < 15 ) {
$freq = 15;
}
if ( $freq > 300 ) {
$freq = 300;
}
// Post editor can use a different interval.
if ( is_admin() && ! empty( $this->settings['heartbeat_editor_frequency'] ) ) {
$editor = (int) $this->settings['heartbeat_editor_frequency'];
$editor = max( 15, min( 300, $editor ) );
$screen = function_exists( 'get_current_screen' ) ? get_current_screen() : null;
if ( $screen && isset( $screen->base ) && in_array( $screen->base, array( 'post', 'site-editor' ), true ) ) {
$settings['interval'] = $editor;
return $settings;
}
}
$settings['interval'] = $freq;
return $settings;
}
}