【CSS】CSSファイルをJavaScriptで後読みするサンプル

2018年3月6日CSS, JavaScriptWEBサイト高速化

Googleのスピードテストで出てくる「スクロールせずに見えるコンテンツのレンダリングをブロックしている JavaScript/CSS を排除する」という最適化項目

余談:ん、「PageSpeed Tools」ちょっと変わったみたいですね

JavaScriptはHTML内での読み込みがそのまま可能なので読み込みが遅れても問題ないスクリプトであれば簡単に対処できますがCSSは一癖ありますね

説明に「CSS 配信を最適化」というリンクがありますので確認

翻訳して引用

ブラウザはコンテンツをレンダリングする前に、現在のページのすべてのスタイルとレイアウト情報を処理する必要があります。その結果、外部スタイルシートがダウンロードされて処理されるまで、ブラウザはレンダリングをブロックします。これにより、複数のラウンドトリップが必要になり、最初のレンダリングまでの時間が遅れることがあります。 レンダリングツリーの構築、レイアウト、ペイントを参照して、重要なレンダリングパスの詳細を確認し、レンダリングのブロックを解除してCSSの配信を改善するヒントを参照してください。

小さいCSSはインライン化

外部CSSリソースが小さい場合は、それらをインライン展開と呼ばれるHTMLドキュメントに直接挿入できます。このように小さなCSSをインライン展開すると、ブラウザはページのレンダリングを続行できます。CSSファイルが大きい場合、CSSを完全にインライン化すると、PageSpeed Insightsは、表示可能なコンテンツの優先順位を上げてページの上の部分が大きすぎると警告することがあります。大きなCSSファイルの場合は、折り畳みコンテンツのレンダリングに必要なCSSを識別してインライン化し、折り畳みコンテンツの後まで残りのスタイルの読み込みを遅らせる必要があります。

小さいCSSとはどこまでのサイズを指すのでしょうか

Googleのブログサービス「Blogger」のデフォルトのシンプルテンプレートを確認すると、縮小していない記述のCSSで400行あたりインライン記述されています

公式内から選べる凝ったテンプレートになるともっと記述は多そうですね

「Blogger」のインラインCSS記述が多いのはテンプレートファイル一枚で全ページのデザインをカスタマイズ可能にする為の仕様で、表示スピードが目的ではないと思いますが、実際これくらいは全然許容範囲な気もします

style属性でのインラインCSSは非推奨?

項目「CSS属性をインライン化しない」より引用

<p style=…>可能であれば、 HTML要素(たとえば、)のCSS属性をインライン展開することは、不要なコードの重複を招くことがあります。さらに、HTML要素のインラインCSSは、コンテンツセキュリティポリシー(CSP)によってデフォルトでブロックされます 。

ちょいちょいコンテンツ作成中にstyleで書いちゃって、そのまま残っちゃってるのがあるんですよね body内にlink hrefで書くことも非推奨ですが、世の中には結構あると思うんですよね どのレベルで非推奨なのか良くわからないです

JavaScriptでCSSファイルを後読みする

bodyタグの最後にJavaScriptでCSSを後読みにする事は可能で、この方法は「CSS 配信を最適化」でも推奨?紹介されています

紹介されているJavaScript

var loadDeferredStyles = function() {
var addStylesNode = document.getElementById("deferred-styles");
var replacement = document.createElement("div");
replacement.innerHTML = addStylesNode.textContent;
document.body.appendChild(replacement)
addStylesNode.parentElement.removeChild(addStylesNode);
};
var raf = window.requestAnimationFrame || window.mozRequestAnimationFrame ||
window.webkitRequestAnimationFrame || window.msRequestAnimationFrame;
if (raf) raf(function() { window.setTimeout(loadDeferredStyles, 0); });
else window.addEventListener('load', loadDeferredStyles);

これでは僕には難解です

とにかく最終的にはheadにCSSリンクをappendChildできれば良いみたい

色々と参考にして複数のCSSファイルを後読みできる様にしてみました

JavaScript

window.addEventListener('load', function(){
      const css = ['A.css','B.css','C.css']

      for(i in css){
       let html = document.createElement('link');
       html.rel = 'stylesheet';
       html.href = css[i];
       document.head.appendChild(html);
     }

});

関数をつかったパターン

JavaScript

function addCss(css) {
       let html = document.createElement('link');
       html.rel = 'stylesheet';
       html.href = css;
       document.head.appendChild(html);
};

window.addEventListener('load', function(){
      addCss('A.css');
      addCss('B.css');
      addCss('C.css');
});

Googleのスピードテストはクリアするけど

確かにJavaScriptで後読み込みを実装する事でGoogleのスピードテスト「PageSpeed Tools」の最適化条件はクリアできモバイルなら80点台の最適化なのが99点にまでなりました(残りは多分アドセンス)

ですが、感想だとメインとなるCSSの読み込みを後読みにするのは微妙でした

確認できるかどうかの瞬間、CSSなしで表示されるくらいなら良いですが、同じ瞬間とはいえはっきり確認できるレベル

あと、これだとおそらくWEBキャプチャされた時にCSSが乗ってない状態でキャプチャされる場合があるかもです

今だとブログカードが主流ですし、自分だけでなくリンクしてくれてる人もキャプチャが崩れてて困るかもですね

初期ビュー表示に影響を与えない部分といっても大規模なデザインは実装してないし別けてないので、使えてアイコンCSSとか大きくデザインに影響しない部分でしょうか

あとPCだと逆に「PageSpeed Tools」で「表示可能コンテンツの優先順位を決定する」という項目が出たりします、ふむふむ

JavaScriptで読み込んだ場合のブラウザキャッシュ

後読みとはいえ、CSSが繁栄されるまで思ったより時間かかってたのでブラウザキャッシュされてるのかについて調べました

→わかりませんでした

これだと、キャッシュされないのでしょうか

2018年3月6日CSS, JavaScriptWEBサイト高速化

Posted by Yousuke.U