如何将此WordPress javascript片段推迟或异步加载,以加快页面加载速度?

Jas*_*ber 49 javascript php wordpress asynchronous

我有各种javascripts,这是我的一个WordPress域中必需的插件,我知道它在php文件中的位置.

我正在采取一切措施来加快页面加载时间,网上的每个速度测试员都会说如果可能的话推迟javascripts.

我已经阅读了关于defer ='defer'和javascript中的异步函数,我认为其中一个将完成我想要完成的任务.但是我不明白我是如何在php文件中这样做的.

例如,这是一个特定插件的php文件的片段,其中调用了javascript文件:

function add_dcsnt_scripts() {

    wp_enqueue_script( 'jquery' );
    wp_enqueue_script( 'dcsnt', dc_jqsocialtabs::get_plugin_directory() . '/js/jquery.social.media.tabs.1.7.1.min.js' );

}
Run Code Online (Sandbox Code Playgroud)

我已经读过,最好这样做,以加快页面加载时间:

<script defer async src="..."></script>
Run Code Online (Sandbox Code Playgroud)

但我不知道如何在php文件中完成它.我想用我的所有javascript文件来做这件事.

我如何完成推迟或推断这个javascript片段是最后加载并加快页面加载时间?在所有浏览器中增加页面加载时间的理想方法是什么?感谢任何人提供的任何指导!

小智 48

或更普遍的方式:

function add_async_forscript($url)
{
    if (strpos($url, '#asyncload')===false)
        return $url;
    else if (is_admin())
        return str_replace('#asyncload', '', $url);
    else
        return str_replace('#asyncload', '', $url)."' async='async"; 
}
add_filter('clean_url', 'add_async_forscript', 11, 1);
Run Code Online (Sandbox Code Playgroud)

因此,您可以在不更改代码的情况下将async添加到任何脚本,只需将#asyncload添加到脚本URL,如下所示:

wp_enqueue_script('dcsnt', '/js/jquery.social.media.tabs.1.7.1.min.js#asyncload' )
Run Code Online (Sandbox Code Playgroud)

  • 感谢用户...这是假设插件作者使用enqueue方法正确编码其插件.越来越多,我正在删除编码不正确的插件,并坚持使用编码更好的插件,即使它们不像更流行的插件那么老和受信任. (2认同)

bra*_*ilo 28

这篇博客文章链接到两个感兴趣的插件:

异步Javascript
通过使用head.js异步加载javascript来提高页面加载性能

WP Deferred Javascripts
使用LABJS(异步javascript库)推迟使用wp_enqueue_scripts添加的所有javascripts的加载.

没有测试过它们但是检查了代码,他们用WordPress脚本排队进程做了很多花哨的东西.

但随后WPSE来救援:

// Adapted from https://gist.github.com/toscho/1584783
add_filter( 'clean_url', function( $url )
{
    if ( FALSE === strpos( $url, '.js' ) )
    { // not our file
        return $url;
    }
    // Must be a ', not "!
    return "$url' defer='defer";
}, 11, 1 );
Run Code Online (Sandbox Code Playgroud)

  • 它已经被弃用了,而不是'esc_url'我现在使用WP 4.1中的'script_loader_tag' (3认同)
  • @brasofolo 'clean_url' 现在已被弃用,支持或 'esc_url' https://codex.wordpress.org/Function_Reference/clean_url (2认同)
  • 回过头来看这个。Async 插件已经失去支持,并且在旧版 Internet Explorer 之外,`defer` 可能不是很有帮助。只是把它扔在那里以防有人在做研究。 (2认同)

Mik*_*ndy 25

为了保持模块化和包含所有内容,以下方法通过在$ handle名称后附加一个小标识符来动态选择如何使用async或defer属性嵌入标记:

/**
* Add async or defer attributes to script enqueues
* @author Mike Kormendy
* @param  String  $tag     The original enqueued <script src="...> tag
* @param  String  $handle  The registered unique name of the script
* @return String  $tag     The modified <script async|defer src="...> tag
*/
// only on the front-end
if(!is_admin()) {
    function add_asyncdefer_attribute($tag, $handle) {
        // if the unique handle/name of the registered script has 'async' in it
        if (strpos($handle, 'async') !== false) {
            // return the tag with the async attribute
            return str_replace( '<script ', '<script async ', $tag );
        }
        // if the unique handle/name of the registered script has 'defer' in it
        else if (strpos($handle, 'defer') !== false) {
            // return the tag with the defer attribute
            return str_replace( '<script ', '<script defer ', $tag );
        }
        // otherwise skip
        else {
            return $tag;
        }
    }
    add_filter('script_loader_tag', 'add_asyncdefer_attribute', 10, 2);
}
Run Code Online (Sandbox Code Playgroud)

用法示例:

function enqueue_my_scripts() {

    // script to load asynchronously
    wp_register_script('firstscript-async', '//www.domain.com/somescript.js', '', 2, false);
    wp_enqueue_script('firstscript-async');

    // script to be deferred
    wp_register_script('secondscript-defer', '//www.domain.com/otherscript.js', '', 2, false);
    wp_enqueue_script('secondscript-defer');


    // standard script embed
    wp_register_script('thirdscript', '//www.domain.com/anotherscript.js', '', 2, false);
    wp_enqueue_script('thirdscript');
}
add_action('wp_enqueue_scripts', 'enqueue_my_scripts', 9999);
Run Code Online (Sandbox Code Playgroud)

输出:

<script async type='text/javascript' src='//www.domain.com/somescript.js'></script>
<script defer type='text/javascript' src='//www.domain.com/otherscript.js'></script>
<script type='text/javascript' src='//www.domain.com/anothercript.js'></script>
Run Code Online (Sandbox Code Playgroud)

感谢@MattKeys @crissoca在这里激发了我的答案.

  • 简单太棒了. (4认同)

Mat*_*eys 15

使用不同过滤器的另一种解决方案,可用于定位特定脚本句柄:

function frontend_scripts()
{
    wp_enqueue_script( 'my-unique-script-handle', 'path/to/my/script.js' );
}
add_action( 'wp_enqueue_scripts', 'frontend_script' );

function make_script_async( $tag, $handle, $src )
{
    if ( 'my-unique-script-handle' != $handle ) {
        return $tag;
    }

    return str_replace( '<script', '<script async', $tag );
}
add_filter( 'script_loader_tag', 'make_script_async', 10, 3 );
Run Code Online (Sandbox Code Playgroud)


The*_*JAG 11

一种简化的方法.添加到您的functions.php文件,使Word在JavaScript中异步

// Make JavaScript Asynchronous in Wordpress
add_filter( 'script_loader_tag', function ( $tag, $handle ) {    
    if( is_admin() ) {
        return $tag;
    }
    return str_replace( ' src', ' async src', $tag );
}, 10, 2 );
Run Code Online (Sandbox Code Playgroud)


Nat*_*end 5

要控制哪些js文件延迟并避免冲突,您可以将变量附加到wp_register_script函数中的url,如下所示.

wp_register_script( 'menu', get_template_directory_uri() . '/js/script.js?defer', array('jquery'), '1.0', true );
Run Code Online (Sandbox Code Playgroud)

然后换行:

if ( FALSE === strpos( $url, '.js' ))
Run Code Online (Sandbox Code Playgroud)

至:

if ( FALSE === strpos( $url, '.js?defer' ))
Run Code Online (Sandbox Code Playgroud)

新过滤器看起来像这样.

add_filter( 'clean_url', function( $url )
{
    if ( FALSE === strpos( $url, '.js?defer' ) )
    { // not our file
    return $url;
    }
    // Must be a ', not "!
    return "$url' defer='defer";
}, 11, 1 );
Run Code Online (Sandbox Code Playgroud)


小智 5

很少的修改代码Mike Kormendy,它允许您一次添加2个属性:

// Async load
function add_asyncdefer_attribute($tag, $handle)
{
    $param = '';
    if ( strpos($handle, 'async') !== false ) $param = 'async ';
    if ( strpos($handle, 'defer') !== false ) $param .= 'defer ';
    if ( $param )
        return str_replace('<script ', '<script ' . $param, $tag);
    else
        return $tag;
}
Run Code Online (Sandbox Code Playgroud)

结果:

<script async defer type='text/javascript' src='#URL'></script>
Run Code Online (Sandbox Code Playgroud)

  • 我赞成!;-) (2认同)