In countless places online I have seen the recommendation to include CSS prior to JavaScript.(在网上无数的地方,我已经看到了在JavaScript之前包含CSS的建议。)
The reasoning is generally, of this form :(一般来说,推理的形式如下:)
When it comes to ordering your CSS and JavaScript, you want your CSS to come first.(在订购CSS和JavaScript时,您希望首先使用CSS。) The reason is that the rendering thread has all the style information it needs to render the page.(原因是渲染线程具有渲染页面所需的所有样式信息。) If the JavaScript includes come first, the JavaScript engine has to parse it all before continuing on to the next set of resources.(如果首先包含JavaScript,则JavaScript引擎必须先解析它,然后再继续使用下一组资源。) This means the rendering thread can't completely show the page, since it doesn't have all the styles it needs.(这意味着渲染线程无法完全显示页面,因为它没有所需的所有样式。)
My actual testing reveals something quite different:(我的实际测试揭示了一些截然不同)
My test harness(我的测试工具)
I use the following Ruby script to generate specific delays for various resources:(我使用以下Ruby脚本为各种资源生成特定的延迟:)
require 'rubygems'
require 'eventmachine'
require 'evma_httpserver'
require 'date'
class Handler < EventMachine::Connection
include EventMachine::HttpServer
def process_http_request
resp = EventMachine::DelegatedHttpResponse.new( self )
return unless @http_query_string
path = @http_path_info
array = @http_query_string.split("&").map{|s| s.split("=")}.flatten
parsed = Hash[*array]
delay = parsed["delay"].to_i / 1000.0
jsdelay = parsed["jsdelay"].to_i
delay = 5 if (delay > 5)
jsdelay = 5000 if (jsdelay > 5000)
delay = 0 if (delay < 0)
jsdelay = 0 if (jsdelay < 0)
# Block which fulfills the request
operation = proc do
sleep delay
if path.match(/.js$/)
resp.status = 200
resp.headers["Content-Type"] = "text/javascript"
resp.content = "(function(){
var start = new Date();
while(new Date() - start < #{jsdelay}){}
})();"
end
if path.match(/.css$/)
resp.status = 200
resp.headers["Content-Type"] = "text/css"
resp.content = "body {font-size: 50px;}"
end
end
# Callback block to execute once the request is fulfilled
callback = proc do |res|
resp.send_response
end
# Let the thread pool (20 Ruby threads) handle request
EM.defer(operation, callback)
end
end
EventMachine::run {
EventMachine::start_server("0.0.0.0", 8081, Handler)
puts "Listening..."
}
The above mini server allows me to set arbitrary delays for JavaScript files (both server and client) and arbitrary CSS delays.(上面的迷你服务器允许我为JavaScript文件(服务器和客户端)和任意CSS延迟设置任意延迟。) For example, http://10.0.0.50:8081/test.css?delay=500
gives me a 500 ms delay transferring the CSS.(例如, http://10.0.0.50:8081/test.css?delay=500
delay = 500给我一个500毫秒的延迟传输CSS。)
I use the following page to test.(我使用以下页面进行测试。)
<!DOCTYPE html>
<html>
<head>
<title>test</title>
<script type='text/javascript'>
var startTime = new Date();
</script>
<link href="http://10.0.0.50:8081/test.css?delay=500" type="text/css" rel="stylesheet">
<script type="text/javascript" src="http://10.0.0.50:8081/test2.js?delay=400&jsdelay=1000"></script>
</head>
<body>
<p>
Elapsed time is:
<script type='text/javascript'>
document.write(new Date() - startTime);
</script>
</p>
</body>
</html>
When I include the CSS first, the page takes 1.5 seconds to render:(当我首先包含CSS时,页面需要1.5秒才能呈现:)
When I include the JavaScript first, the page takes 1.4 seconds to render:(当我首先包含JavaScript时,该页面需要1.4秒才能呈现:)
I get similar results in Chrome, Firefox and Internet Explorer.(我在Chrome,Firefox和Internet Explorer中获得了类似的结果。) In Opera however, the ordering simply does not matter.(然而,在Opera中,排序无关紧要。)
What appears to be happening is that the JavaScript interpreter refuses to start until all the CSS is downloaded.(似乎正在发生的事情是JavaScript解释器在下载所有CSS之前拒绝启动。) So, it seems that having JavaScript includes first is more efficient as the JavaScript thread gets more run time.(因此,似乎首先使用JavaScript包含更高效,因为JavaScript线程会获得更多的运行时间。)
Am I missing something, is the recommendation to place CSS includes prior to JavaScript includes not correct?(我错过了什么,建议将CSS包含在JavaScript之前包括不正确吗?)
It is clear that we could add async or use setTimeout to free up the render thread or put the JavaScript code in the footer, or use a JavaScript loader.(很明显,我们可以添加async或使用setTimeout来释放渲染线程或将JavaScript代码放在页脚中,或者使用JavaScript加载器。) The point here is about ordering of essential JavaScript bits and CSS bits in the head.(这里的要点是关于头部中基本JavaScript位和CSS位的排序。)
ask by Sam Saffron translate from so
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…