什么时候应该使用内联与外部Javascript?

我想知道什么时候应该包含外部脚本,或者在内部使用html代码进行编写,以便提高性能和维护的便利性。

这是什么一般的做法?

真实世界的情况 – 我有几个需要客户端表单validation的html页面。 为此,我使用了包含在所有这些页面上的jQuery插件。 但问题是,我是否:

  • 写内联configuration这个脚本的代码位?
  • 包括所有这些html页面之间共享的一个文件中的所有位?
  • 包括每个位在一个单独的外部文件,每个HTML页面?

谢谢。

当时这个答案最初发布(2008年),规则很简单:所有的脚本应该是外部的。 维护和性能。

(为什么性能?因为如果代码是分开的,浏览器可以更容易地caching)。

JavaScript不属于HTML代码,如果它包含特殊字符(如<> )甚至会产生问题。

如今,networking可扩展性已经发生了变化。 由于发出多个HTTP请求的延迟,减less请求数已成为一个有效的考虑因素。 这使得答案更加复杂:在大多数情况下, 仍然build议使用JavaScript。 但是对于某些情况,特别是非常小的代码,将它们embedded到网站的HTML中是很有意义的。

可维护性绝对是将它们保持在外部的原因,但是如果configuration是单行(或者通常比将这些文件外部化的HTTP开销更短),那么保持内联性能更好。 请记住,每个HTTP请求都会在执行时间和stream量方面产生一些开销。

当然,当你的代码长于几行时,这一切就变得毫无意义了,而且对于单个页面来说并不是特定的。 当你想要重用这个代码的时候,把它放到外部。 如果你不这样做,看看它的大小,然后决定。

外化JavaScript是雅虎性能规则之一: http : //developer.yahoo.com/performance/rules.html#external

虽然你应该始终将脚本外化的硬性规定通常是一个很好的select,在某些情况下,你可能想要内联一些脚本和样式。 但是,只有内联你所知道的内容才能提高性能(因为你已经testing过了)。

如果你只关心性能,那么这个线程中的大部分build议都是错误的,而且在SPA时代变得越来越错误,我们可以假设页面没有JS代码是没有用的。 我花了无数小时来优化SPA页面加载时间,并用不同的浏览器validation这些结果。 通过重新编排你的html来提高性能可能会相当戏剧性。

为了获得最好的performance,你必须把页面看成是两级火箭。 这两个阶段大致对应于<head><body>阶段,但将它们视为<static><dynamic> 。 静态部分基本上是一个string常量,您可以尽可能快地按下响应pipe道。 如果你使用了很多设置cookie的中间件(这些需要在发送http内容之前设置),这可能有点棘手,但是原则上它只是刷新响应缓冲区,希望在跳转到一些模板代码(razor,PHP,等等)在服务器上。 这听起来很难,但是我只是解释错误,因为这几乎是微不足道的。 正如你可能已经猜到的,这个静态部分应该包含所有内联和缩小的javascript。 它看起来像

 <!DOCTYPE html> <html> <head> <script>/*...inlined jquery, angular, your code*/</script> <style>/* ditto css */</style> </head> <body> <!-- inline all your templates, if applicable --> <script type='template-mime' id='1'></script> <script type='template-mime' id='2'></script> <script type='template-mime' id='3'></script> 

由于接下来没有什么东西要发送这个部分,所以你可以期望在连接到你的服务器之后,客户端会开始接收大约5ms +的延迟。 假设服务器相当接近,这个延迟可能在20ms到60ms之间。 浏览器一旦得到它就会开始处理这部分内容,而处理时间通常将传输时间控制在20或更多,这是您的<dynamic>部分的服务器端处理的摊销窗口。

浏览器(铬,其余的可能慢20%)需要大约50ms来处理内联的jquery + signalr + angular + nganimation+ ng touch + ng路由+ lodash。 这本身就相当惊人。 大多数Web应用程序的代码比所有stream行库的代码less,但是假设您拥有同样多的代码,所以我们将赢得客户端延迟+100毫秒的处理时间(这个延迟胜出来自第二个传输块)。 当第二块到达时,我们已经处理了所有的js代码和模板,我们可以开始执行dom转换。

你可能反对这个方法是正交的内联概念,但事实并非如此。 如果你不用内联,而是链接到cdns或你自己的服务器,浏览器将不得不打开另一个连接并延迟执行。 由于这个执行基本上是免费的(因为服务器端正在与数据库交谈),所以必须清楚的是,所有这些跳转将花费更多而不是完全跳转。 如果有一个浏览器的怪癖,说外部js执行速度更快,我们可以衡量哪个因素占主导地位。 我的测量结果表明,额外的请求会在这个阶段杀死性能

我在SPA应用程序的优化方面做了很多工作。 人们常常认为数据量是一个大问题,而事实上,延迟和执行往往占主导地位。 我列出的缩小的库增加了300kb的数据,这只是68KB的gzip,或者在一个2mbit 3G / 4G手机上下载了200ms,这正是在同一个手机上检查IF是否具有相同数据的延迟在其caching中,即使它是代理caching,因为移动延迟税(电话到塔延迟)仍然适用。 同时,具有较低首跳延迟的桌面连接通常具有较高的带宽。

总之,现在(2014),最好是内联所有脚本,样式和模板。

编辑(五月2016)

随着JS应用程序的不断增长,现在我的一些有效载荷可以叠加到3+兆字节的缩小代码上,显而易见,至less通用库不应该被内联。

我认为具体到一页,短脚本案例是(唯一)内联脚本的辩护情况

实际上,使用内联JavaScript有一个非常可靠的例子。 如果js足够小 (单行),我倾向于更喜欢javascript内联,因为有两个因素:

  • 地点 。 没有必要浏览一个外部文件来validation一些JavaScript的行为
  • AJAX 。 如果您通过AJAX刷新页面的某个部分,则可能会丢失该部分的所有DOM处理程序(onclick等),具体取决于您如何绑定它们。 例如,使用jQuery你可以使用live或者delegate方法来绕过这个,但是我发现如果js足够小,最好把它放在内联中。

为什么总是使用外部脚本的另一个原因是为了更容易地转换到内容安全策略(CSP) 。 CSP默认禁止所有内联脚本,使您的网站更能抵御XSS攻击。

我会看看所需的代码,并根据需要将它分成许多单独的文件。 每个js文件只能保存一个函数的“逻辑集合”等。 一个文件的所有login相关的function。

然后在每个html页面的网站开发过程中,您只包括那些需要的。 当你和你的网站一起生活的时候,你可以通过把每个页面需要的js文件合并成一个文件来进行优化。

我可以为内联javascipt提供的唯一防御是,当使用.net MVC的强types视图时,您可以引用c#variables中间JavaScript,我发现有用。

三点考虑:

  • 你需要多less代码(有时候库是一stream的消费者)?
  • 特定性:这个代码只在这个特定文档或元素的上下文中起作用吗?
  • 文档中的每个代码往往会使其更长,从而变慢。 除了SEO的考虑使其明显,你最小化内部脚本…

外部脚本也更容易使用Firebug进行debugging。 我喜欢unit testing我的JavaScript,并拥有一切外部帮助。 我讨厌在PHP代码和HTML中看到JavaScript,看起来对我来说是一个很大的混乱。

为了保持JavaScript的外部:

ASP.NET 3.5SP1最近引入了创buildComposite脚本资源的function(将一堆js文件合并为一个)。 另一个好处是打开Web服务器压缩时,下载一个稍大的文件将有更好的压缩比,然后很多较小的文件(也更less的HTTP开销,往返等)。 我想这节省了初始页面加载,然后浏览器caching踢如上所述。

除了ASP.NET之外,这个截屏video更详细地解释了这些好处: http : //www.asp.net/learn/3.5-SP1/video-296.aspx

外部脚本的另一个隐藏的好处是,你可以很容易地通过像jslint这样的语法检查器来运行它们。 这可以让你免受很多令人心碎的,难以发现的IE6的bug。

在你的情况下,听起来像写外部的东西在一个文件共享的文件将是对你有好处。 我同意上面所说的一切。

在早期的原型开发过程中,为了获得快速迭代,请保持代码内联,但一定要在达到生产时将其全部置于外部。

我甚至敢说,如果你不能在外部放置所有的Javascript,那么你的devise就不好,你应该重构你的数据和脚本

Google已经将加载时间join到页面排名测量中,如果您进行了大量的内嵌,蜘蛛抓取您的页面所花费的时间也会更长,但是如果您需要大量的内容,这可能会影响您的页面排名。 无论如何,不​​同的策略可能会影响你的排名。

以及我认为你应该使用内联制作单页网站,因为脚本不需要在多个页面上共享