我想知道以下哪一项会为加载大量javascript(jQuery + jQuery UI +各种其他javascript文件)的页面带来更好的性能。我已经浏览了大部分YSlow和Google Page Speed的内容,但我对某个特定细节感到疑惑。
对我来说,关键是我正在处理的网站不在公共网络上;它是一个企业对企业平台,几乎所有用户都是重复访问者(因此有数据缓存,这是YSlow认为对于大量访问者来说不是这种情况)。
首先,YSlow等工具推荐的标准方法是连接它,压缩它,并在页面末尾加载的单个文件中提供它。这种方法听起来相当有效,但我认为这里推理的一个关键部分是提高没有缓存数据的用户的性能。
我目前拥有的系统是这样的
现在,我的理解是,如果尚未达到javascript文件的缓存过期日期,则立即使用缓存版本;根本没有向服务器发送HTTP请求。如果这是正确的,我会假设有多个标签不会导致任何性能损失,因为我仍然没有在大多数页面上有任何额外的请求(从上面回忆几乎所有用户都有填充的缓存)。
除此之外,不加载JS意味着浏览器不必解释或执行它不需要的所有额外代码;作为一个B2B应用程序,我们的大多数用户不幸遇到了IE6及其缓慢的JS引擎。
另一个好处是,当代码更改时,只需要再次获取受影响的文件,而不是整个集(被授予,只需要获取一次,因此这不是一个好处)。
我也在考虑使用LabJS来允许在没有缓存的情况下并行加载JS。
具体问题
答案 0 :(得分:11)
我想说最重要的是对速度的感知。
首先要考虑的是,没有双赢公式,但是javascript文件增长到可以(并且应该)拆分的大小的阈值。
GWT uses this他们称之为 DFN(现在为死)代码。这里没什么魔力。您只需手动定义何时需要新代码,如果用户需要,只需调用该文件即可。
您需要的方式,时间,地点? 基准。 Chrome有一个很棒的基准测试工具。广泛使用它。看看是否只有一个小的javascript文件将大大改善该特定页面的加载。如果确实如此,请开始DFNing您的代码。
除此之外,一切都与感知有关。
不要让内容跳跃!
如果您的页面有图像,请预先设置其宽度和高度。由于页面将加载位于它们应该位于的位置的元素,因此不会有内容拟合,并且调整用户对速度的感知会增加。
推迟javascript!
在执行javascript之前,所有主要库都可以等待页面加载。用它。 jQuery就像这样$(document).ready(function(){ ... })
。它不会等待解析代码,但会使解析后的代码准确触发。页面加载后,在图像加载之前。
需要考虑的重要事项:
Apache缓存示例:
// Set up caching on media files for 1 month
<FilesMatch "\.(gif|jpg|jpeg|png|swf|js|css)$">
ExpiresDefault A2629744
Header append Cache-Control "public, proxy-revalidate"
Header append Vary "Accept-Encoding: *"
</FilesMatch>
Apache缩小的例子:
// compresses all files for faster transfer
LoadModule deflate_module modules/mod_deflate.so
AddOutputFilterByType DEFLATE text/html text/plain text/xml font/opentype font/truetype font/woff
<FilesMatch "\.(js|css|html|htm|php|xml)$">
SetOutputFilter DEFLATE
</FilesMatch>
最后,也许最不重要的是,从无cookie的域中提供您的Javascript。
为了让你的问题成为焦点,请记住,当你有DFN代码时,你会有几个较小的javascript文件,正好被拆分,没有压缩级别Closure可以给你一个单独的。在这种情况下,各部分的总和不等于整体。
希望它有所帮助!
答案 1 :(得分:3)
我真的认为你需要做一些测量来确定一个解决方案是否比另一个更好。您可以使用JavaScript和日志数据来清楚了解用户所看到的内容。
首先,分析您的日志,看看您的缓存率是否真的与您对用户群的期望一样好。例如,如果每个html页面都包含jquery.js,请查看日志一天 - html页面有多少请求? jquery.js有多少?如果缓存率良好,您应该看到jquery.js的请求远远少于html页面的请求。您可能希望在更新后立即执行此操作,并在更新后的几周内执行此操作,以查看它如何影响缓存速率。
接下来,在JavaScript中为您的页面添加一些简单的度量。你说脚本标签在底部,所以我认为它看起来像这样吗?
<html>
<!-- all your HTML content... -->
<script src="jquery.js"></script>
<script src="jquery-ui.js"></script>
<script src="mycode.js"></script>
在这种情况下,您需要花费多长时间来加载JS,并像这样ping服务器:
<html>
<!-- all your HTML content... -->
<script>var startTime = new Date().getTime();</script>
<script src="jquery.js"></script>
<script src="jquery-ui.js"></script>
<script src="mycode.js"></script>
<script>
var endTime = new Date().getTime();
var totalTime = endTime - startTime; // In milliseconds
new Image().src = "/time_tracker?script_load=" + totalTime;
</script>
然后你可以查看/ time_tracker的日志(或者你想要调用它的任何内容),看看它花了多长时间加载脚本。
如果你的缓存率不好,和/或你对加载脚本需要多长时间不满意,那么尝试将所有脚本移动到你的一个页面上的连接/缩小文件中,并测量如何需要以相同的方式加载。如果结果看起来很有希望,请完成网站的其余部分。
答案 2 :(得分:2)
我肯定会选择非单片方法。不仅在您的情况下,而且通常在您需要更改或重新配置时提供更大的灵活性。
如果您对其中一个文件进行了更改,则必须进行合并 - 压缩和传递。如果您以自动方式执行此操作,那么您就可以了。
就浏览器问题“如果尚未达到javascript文件的缓存过期日期,则立即使用缓存版本;根本没有向服务器发送HTTP请求”,我认为那里是一个HTTP请求,但响应“NOT MODIFIED”。确保您应该检查对Web服务器的所有请求(使用其中一个可用工具)。在给出响应之后,浏览器使用未修改的资源 - js文件或图像或其他。
祝你的B2B好运。
答案 3 :(得分:1)
您是否尝试过Google Closure?从我读到的内容来看,这似乎很有希望。
答案 4 :(得分:1)
即使您正在处理重复访问者,也有很多原因可能导致他们的缓存被清除,包括删除临时缓存文件以“加速计算机”的隐私和性能工具。
合并和迷你编写脚本不一定是繁重的过程。我将我的JavaScript写在单独的文件中,很好地分隔开来以便我可读,因此更容易维护。但是,我通过一个脚本页面提供服务,该脚本页面将所有脚本组合到一个脚本中并将其全部缩小 - 所以我的所有脚本都会将一个脚本发送到浏览器。这是我工作的两个世界中最好的在一组可读的JavaScript文件上,访问者获得一个压缩的JavaScript文件,这是减少HTTP请求(以及队列时间)的建议。
答案 5 :(得分:0)
通常,拥有更少,更大的请求比拥有许多小请求更好,因为浏览器只会对特定域并行执行两个(?)请求。
因此,虽然您说大多数用户都是重复访问者,但是当缓存过期时,许多文件会有许多往返,而不是单个文件。
如果你把这个带到一个极端,并且可能有成千上万个带有单独功能的文件,那么很明显,这会在缓存过期时导致大量请求。
拥有单片文件的另一个原因是,当网站的各个部分具有与其关联的不同javascript块时,当您点击第一页时再次将其保存在缓存中,从而节省了后续请求和往返。
如果您担心初始点击加载“大”javascript文件,您可以尝试使用此处描述的方法异步加载它:http://www.webmaster-source.com/2010/06/07/loading-javascript-asynchronously/
无论你最终采用哪种方式,都要记住,因为你设置了一个远期修改日期,所以当你对它们进行更改时,你需要更改javascript(和CSS)文件的名称。 ,否则客户端无论如何都会在缓存过期之前接收更改。
PS:使用不同的方法在不同的浏览器上对其进行配置并编写它,因为它对于那些也被卡在像IE6这样的慢速JS引擎上的人来说非常有用:)
答案 6 :(得分:0)
我在CSS和Javascript中使用了以下内容 - 我在Google Speed报告中的大部分页面都是94-96 / 100,并且加载速度非常快(即使有100kb的Javascript,也会在一秒钟内加载)。
1。我有一个PHP函数来调用文件 - 这是一个类,它存储了所有要求的唯一文件。我的电话看起来像是:
javascript( 'jquery', 'jquery.ui', 'home-page' );
2. 我吐出这些字符串的url编码版本,组合在一起调用动态PHP页面:
<script type="text/javascript" src="/js/?files=eNptkFsSgjAMRffCP4zlTVmDi4iQkVwibbEUHzju3UYEHMffc5r05gJnEX8IvisHnnHPQN9cMHZeKThzJOVeex7R3AmEDhQLCEZBLHLMLVhgpaXUikRMXCJbhdTjgNcG59UJyWSVPSh_0lqSSp0KN6XNEZSYwAqt_KoBY-lRRvNblBZrYeHQYdAOpHPS-VeoTpteVFwnNGSLX6ss3uwe1fi-mopg8aqt7P0LzIWwz-T_UCycC2sQavrp-QIsrnKh"></script>
3. 动态PHP页面会对字符串进行解码并创建需要调用的文件数组。创建cache_file路径:
$compressed_js_file_path = $_SERVER['DOCUMENT_ROOT'] . '/cache/js/' . md5( implode( '|', $js_files ) ) . '.js';
4. 它检查缓存中是否已存在该文件路径,如果是,则只读取文件:
if( file_exists( $compressed_js_file_path ) ) {
echo file_get_contents( $compressed_js_file_path );
} else {
5. 如果它不存在,它会将所有javascript压缩成一个“monolith”文件,但是意识到它只包含该页面所需的javascript,而不是整个网站。< / p>
if( $fh = @fopen( $compressed_js_file_path, 'w' ) ) {
fwrite( $fh, $js );
fclose( $fh );
}
// Echo the compressed Javascript
echo $js;
我已经为您提供了代码摘录。用于压缩javascript的程序完全取决于您。我将它与CSS和Javascript一起使用,以便所有这些文件都需要1个HTTP请求,结果缓存在服务器上(如果你改变了某些内容,只需删除该文件),它只有必要的Javascript&amp;该页面的CSS。