在同一页面中组合特定页面样式和全局样式时的性能

时间:2014-02-12 20:13:18

标签: php html css performance load-time

我的主要目标是允许加载多个页面尽可能快。为此,我想利用缓存和一种“特殊技术”,作为后备,依赖于标准缓存。

结构

在后端,我有以下结构。 public_html中有一个主页面和几个子页面,每个子页面都有不同的特定css规则。 所有最小化文件的创建都是通过脚本完成的,因此没有额外的复杂性。为简单起见,我们假设这是结构,虽然它更复杂:

/public_html
  /index.php
  /style.css    ~50kb
  /min.css      ~100kb
  /subjects
    /index.php
    /style.css      ~20kb
    /min.css        ~10kb
  /books
    /index.php  
    /style.css      ~20kb
    /min.css        ~10kb
  ...

第一次请求

因此,当用户第一次在子页面上输入时,他们将收到此HTML代码:

<!DOCTYPE html>
<html>
  <head>
    <link href="/subjects/min.css" rel="stylesheet" type="text/css">
  </head>
  <body>
    All the body here
    <link href="/min.css" rel="stylesheet" type="text/css">
  </body>

如您所见,用户在一个小文件中加载标题中该页面所需的所有css代码。请注意,/subjects/min.css/min.css小很多,这会使第一次请求加载更快。然后,在正确加载完整的html和css之后,/min.css将开始加载。此文件包含子页面样式的所有

请注意it's appropriate to put the <link> within the <body> tag,即使它不起作用,也没有问题,因为已经加载了特定于页面的样式。我为什么要在这里加载?继续阅读:

以下请求

对于该会话的第二个及后续请求,用户将收到此html代码:

<!DOCTYPE html>
<html>
  <head>
    <link href="/min.css" rel="stylesheet" type="text/css">
  </head>
  <body>
    All the body here
  </body>

/min.css应该已经从第一个请求缓存了。但是,如果由于任何原因不是,它将立即加载完全最小化的样式,就像在任何普通网站中一样。这将是后备案例。

这是一个有效的计划吗? 为什么我以前没见过这样的东西?它是否包含任何逻辑错误?

这些是我能看到的主要问题,与收益相比还不够强大:

  • 它为代码增加了一些额外的复杂性。
  • 需要在已经加载所有内容后发出额外请求。这会在服务器上增加一些开销,但它是一个静态文件。

有关评论的说明:

  1. 浏览器会减少请求。这是事实,通过这种方式,浏览器会执行一个额外的请求。但是,它是在加载html和css之后,所以这不会对html造成很大的影响。

  2. 缓存。是的,我正在尽力抓住文件。如果<link>位于<body>内,可以对{{1}}的缓存进行一点,因为我不知道它对缓存的行为是否不同,我在问题中只假设是。

4 个答案:

答案 0 :(得分:6)

<强>更新

请注意,不能推荐提问者标记为已接受的答案 -
不要这样做!

任何类型的“预加载”CSS文件都没有任何意义,因为你永远不应该将你的CSS分成几个文件!

我原来的回答:

那么到底你真正的问题是什么?

以我的拙见,你做错了 - 抱歉!

通常作者打算

  • 为网站提供一致的外观/外观
  • 尽可能保持可维护性
  • 避免FOUC(无格式内容的闪现)
  • 最小化(HTTP)请求数
  • 支持缓存机制以减少带宽/数据量

仅提及一些最重要的方面。

所有这些都被你的方法所忽视。

当您在link元素中使用body元素时,我假设您使用的是HTML5。因为在其他HTML版本中,这将是无效的。

但是在HTML5中我不会依赖于此。看看这两个版本:

  1. http://www.w3.org/html/wg/drafts/html/master/document-metadata.html#the-link-element
  2. http://www.w3.org/html/wg/drafts/html/CR/document-metadata.html#the-link-element
  3. 比较部分(在顶部)“可以使用此元素的上下文:”。

    由于浏览器最需要来自CSS的信息来呈现页面,因此它应该是首先加载的内容之一。

    查看文章:“How Browsers Work: Behind the scenes of modern web browsers”,特别是在“Rendering engines”部分。

    因此,加载另一个样式表将强制浏览器重做所有工作,除了额外的HTTP请求,特别是在GSM连接上,由于更长的延迟,可能会导致“麻烦”。

    如果您网站的每个页面确实有如此多的个人风格规则,那么我会说这是一个“设计缺陷”。

    其中一个“设计原则”是:尽可能少 - 尽可能少!

    仅使用一个样式表的另一个(大)优势是它在第一次加载后由浏览器缓存。由于网站的CSS通常不会经常变化,这是一个很大的优势,远远超过了第一页访问时加载更多KB的缺点(顺便说一下,无论是进入/登录页面)!

    <强>结论
    我真的不建议使用你的方法!

    将所有样式(规范化,基本,媒体查询,打印)放在一个文件中,然后通过文档<link>中的<head>加载

    这是你能做的最好的事情。

答案 1 :(得分:5)

是的,你正在做的是完全有效和常见的

CSS也许是一个不好的例子,但是相同的原则(通过ajax btw加载最后一个)

就像说,图像。

我们位于我们网站的第1页,我们知道访问者将有99.999%的时间点击第2页,我们知道第2页我们有一些大型图片可供使用,是的,我们可能会加载他们在第1页加载后默默地进行 - 准备就绪,然后网站在导航时“感觉”很快。移动Web应用程序/ sites /

中的常见技巧

是的:

对于任何类型的文件,您可能希望为后续请求“预缓存”,这是相同的原则。

  • 加载页面
  • 当访问者'正在'读取加载的页面时,预先获取文件/数据 你希望他们可能会要求下一个。 (图像,结果数据,javascript和css的第2页)。 这些是通过ajax加载的,因为它不会阻止页面'onload'事件触发 - 与示例的关键区别

然而,要回答您的目标 - 允许加载页面尽可能快

如果我们不从静态服务器,无Cookie域以及最终内容交付网络提供静态文件,那么执行此操作或任何类型的“预先加载”技术对于“交付速度”来说是最小的。


实现允许尽可能快地加载页面的目标,静态文件的服务与动态内容不同(php render all all)

1)为这些资源(css,js,images / media)创建一个子域名 - static.yourdomain.com

2)专门针对此子域关闭Cookie,标头和调整缓存标头。

3)查看使用http://cdnify.com/或www.akamai.com等服务。

这些是提供静态内容的性能和速度步骤。 (希望没有吸蛋,只是直接关联这个问题,如果有人不熟悉这个)

'预先加载'技术仍然很棒, 但他们 现在与预加载数据相关的可用性与速度相关。


修改/更新

澄清'速度'和'可用性速度'。

  • 软件通常会在页面'onload'事件触发时判断速度(这就是为什么通过ajax加载这些'优先资源'很重要。

  • 感知速度(可用性)是用户查看内容并与内容交互的速度(即使页面加载事件可能未被触发)。


修改/更新

在帖子的几个方面和评论中提到了通过javascript / ajax加载这些额外的'预防'资源。

原因是没有延迟页面'onload'事件触发。

许多网站测试速度工具(yslow,google ..)使用此'onload'事件来判断页面速度。

我们延迟页面'onload'事件。

<body>

... page content 

<link rel="stylesheet" href="/nextpage.css"  />
</body>

这里我们通过javascript加载/某些情况Ajax(页面数据)并且不会阻止页面加载事件

<body>
.. page content

  <script>

    window.onload = function () {

       var style   = document.createElement( 'link' );
       style.rel   = 'stylesheet';
       style.type  = 'text/css';
       style.href  = '/nextpage.css';
       document.getElementsByTagName( 'head' )[0].appendChild( style );

   };

   </script>

(作为奖励,也可以解决在<link>中使用<body>标记的兼容性问题,如其他主题中所讨论的那样)     

答案 2 :(得分:3)

由于min.css包含正确最小化的所有样式,因此只需使用


为什么?

1.浏览器会减少请求

2.浏览器提取2到3次后,文件将被缓存。页面加载时间大幅减少!

3.浏览器不必浏览特定页面的css,从而减少了页面呈现所需的时间

4.代码易于维护。如果要更新css,只需为某个查询变量添加前缀,以便浏览器获取更新的css


我认为,上述原因足以让您只使用min.css

此外,不要忘记设置 reallyyyyy 长缓存到期日期,如果你按照我推荐的那样做

编辑: 由于OP不理解第2点,我会让自己明白一点。

浏览器不会在第一次遇到时缓存css文件,因为它认为:'嘿,我们不要立即缓存它。如果它改变了怎么办?我会看到,同样的css至少重新加载2次,以便获得缓存的好处'

首次加载时,缓存css没有意义。因为如果浏览器这样做,那么用户系统上会有大量的内容。因此,浏览器足够聪明,可以缓存已加载且未更改的文件

答案 3 :(得分:2)

您所描述的是一种预取/延迟加载模式,其中加载了资源以期在将来变得相关 - 例如,具有最小样式的基本登录页面开始在后台加载站点css。 / p>

以前在PageSpeed模块中已经完成了这项工作。事实上,它更具侵略性,但需要更少的开发工作!仅使用一小部分样式的vanilla登陆页面(如登录屏幕)可以利用prioritize_critical_css将相关规则内联到html并在页面底部加载css!与原始场景(必须执行两个连续请求)不同,not having stylesheet in the head的渲染阻止效果正在被抵消。第一次使用移动设备的访问者可以很好地感知到这种改进,他们受到更高的网络延迟和更少的同时http请求的限制。

这种自然进展将是延迟加载精灵,webfonts和其他静态可缓存内容。但是,我倾向于推测,具有良好结构的单独css的好处是probably肤浅的,并且通常可以将样式缩小到一个文件中。 5到50千字节文件之间的加载时间差异不是十倍,因为网站performance does not depend on bandwidth anymore可以忽略不计。作为旁注,您永远不必担心依赖关系管理(即记住包含与页面上特定元素相关的规则),这对于html + css来说并不容易自动化,并且对于大型项目来说非常繁琐。

如果你专注于静态资源的基本规则 - aggressive caching - 并记住指纹你的资产,以便部署不会变得混乱,你做得很好!如果你在这里和那里用一个位置优越的悸动者来解决感知的表现......