SPAアプリケーションの量を減らす別の方法(webpack)

つい最近、私は新しいツールを学ぶ必要がありました。 別のそのようなツールはwebpackでした 。 このツールは興味深いものですが、Google Closure *から移行した後、 webpackがGoogle Closure Stylesheetsのようにクラス名を絞り込まない理由が謎になりました。 1日、ひざの上で、この機能を非常にうまく実装するプラグインを書きました。 以下の詳細な説明。

それでは、TKから始めましょう。 これは、まず自分のために、そして次に、それが起こっていることをまだ理解していないが、どういうわけかこのページに載っている人のために行われます。 個人的に、私は大きくて美しい長いクラス名を書くのが好きです。

例:

.header { position: fixed; top: 0; ... } .header a { display: block; float: right; ... } .sidebar { float:right; max-width: 30%; ... } .sidebar a { font-size: 16px; .... } 

ただし、 ヘッダーhに、 サイドバーsに減らすことができるため、CSSだけでなくJSファイルでも多くのバイトを節約できます。 ほとんどの場合、JSにはクラス名によるセレクターが含まれます。

ただし、コードの可読性はこのような低下に悩まされ、その結果、開発速度が低下します。 したがって、この置換用のツールを自動的に作成する必要があります。

これがクロージャーでどのように機能するかの簡単な説明


Google Closureはいくつかのツールで構成され、そのうちの1つはGoogle Closure Stylesheetsです。これは、スタイルシートのプリプロセッサとポストプロセッサの両方です。

プリプロセッサとして、それはそのすべての兄弟に似ていますが、すべてのほとんどはSCSS / SASSに似ています。
ポストプロセッサとして、置換辞書を作成してクラス名を解析し、すべてのクラス名を短い表記に置き換えます。

たとえば、上記のコードは次のようになります。

 .a { position: fixed; top: 0; ... } .aa { display: block; float: right; ... } .b { float:right; max-width: 30%; ... } .ba { font-size: 16px; .... } 

代替の辞書は次のとおりです。

 { "header": "a", "sidebar": "b" } 

実際、はるかに多くの機能がありますが、この記事はそれについてではありません。 また、優れたテンプレートエンジンであるClosure Templatesもあります。このテンプレートエンジンでは、すべてのクラス名を特別なディレクティブでマークする必要があり、その後、テンプレートに置換辞書が適用されます。

例:

 {namespace test} /** * Test template * */ {template .test} <div class="{css header}">Header<a href="#">Home</a><a href="#">About</a><header> ... <div class="{css sidebar}">Sidebar<header> 

また、すべてのCSSクラスの名前を「洗練」する必要があるJSがあることを忘れないでください。

 var header = goog.dom.getElementByClass(goog.getCssName('header')); var sidebar = goog.dom.getElementByClass(goog.getCssName('sidebar')); 

そして、すべてのソースを修正し、それらを置換辞書とともにコンパイルに送信する場合にのみ、すべてが機能します。

この方法の主な欠点は、辞書がCSSでコンパイルされていることです。 JSからDOM要素を選択するためだけに使用されるクラスがある場合、辞書に入らない可能性があります(または、この記事がClosure Toolsのレビューではないことを予約します)。

プラグインに戻る


散乱関数はどこにでもあり、あまり便利ではないように思えたので、マスク___ <%className%> __でクラス名を設定することにしました。

したがって、スタイルが思い浮かびます:

 .___header__ { position: fixed; top: 0; ... } .___header__ a { display: block; float: right; ... } .___sidebar__ { float:right; max-width: 30%; ... } .___sidebar__ a { font-size: 16px; .... } 

そして、jQueryを例として使用して、JSでDOMを操作します。

  var header = $('.___header__'); var sidebar = $('.___sidebar__'); 

たとえば、React:

 function Header(props) { return ( <div className="___header__"> {props.children} </div> ); } 

たとえば、バックボーン:

 module.exports = Backbone.View.extend({ tagName: 'div', className: '___header__' }); 


UPD:
角度の場合、 は太いです。

次のような構造の予約をすぐに行います。

 var genClassName = function(v) { return '___' + v + '__'; } module.exports = Backbone.View.extend({ tagName: 'div', className: genClassName('header') }); 

動作しません。 スタイルと同様に:

 [class*="bold"] { font-weight:bolder; } 

最初のステップ


パッケージをインストールすることにより:

 npm install --save cssrename-webpack-plugin 

そして、 webpack.config.jsに少し手を加えて

 const CssRenameWebpackPlugin = require('cssrename-webpack-plugin'); ... module.exports = { ... plugins: [ CssRenameWebpackPluginConfig, ... ] }; 

アセンブリプロセス中に、次の行が表示されます。

利益:355

これは、保存されたバイト数を報告します。

不快感と解決策


しかし、JSの動物の多様な世界に1つのパーサーでカバーできない膨大な数のライブラリがある場合、この問題のCSSははるかに人道的であり、解析するのがはるかに簡単です(CSS)。

最も単純な形式では、1つの正規表現になります。 したがって、少なくともCSSにアンダースコアを追加しないようにする同様のローダーを追加してみてください。

 npm install --save cssrename-loader 

次の突然変異webpack.config.js

 module.exports = { module: { loaders: [ { test: /\.css$/, loader: "style-loader!css-loader!cssrename-loader" } ] } }; 

テストプロジェクトで何が起こったのか

更新:

これについては書きたくありませんでしたが、明らかに追加する必要があります。 さらに、スタイルのみが考慮されるため、JSとテンプレートでの賞金は数えられないほど簡単です。 Google Closure Stylesheetsの場合:
サイト/ファイル元のボリューム/ zip受信したボリューム/ zip貯蓄率(zip)
acss.io bundle.488facb7.css13.8KB / 4.4KB13.3KB / 4.0KB≈9%
getbem.com/introduction getbem.com.1.0.0.css13.3KB / 3.3KB12KB / 3.1KB≈6%
ブートストラップ121.2KB / 18.7KB96.9KB / 16.7KB≈10%
habrahabr.ru global_main.css212.3KB / 30.6KB155.2KB / 26.9KB≈13%

証明

Google Closure Stylesheetsに適合しなかったもの:

Atomicの場合、正規表現を2つ置き換える必要がありました。

 \\\(((?:(?!\\\)).)*?)\\\) => --$1-- \\. => -- 

BEMで「クロールしませんでした」:

 @supports (display: -moz-box) { [class*=LineClamp] { display: block } } @-webkit-keyframes bounce { 0% { -webkit-transform: translateY(-100%); transform: translateY(-100%); -webkit-filter: blur(5px); filter: blur(5px) } 100%, 40% { -webkit-transform: translateY(0); transform: translateY(0) } 60% { -webkit-transform: translateY(-10%); transform: translateY(-10%) } } @keyframes bounce { 0% { -webkit-transform: translateY(-100%); transform: translateY(-100%); -webkit-filter: blur(5px); filter: blur(5px) } 100%, 40% { -webkit-transform: translateY(0); transform: translateY(0) } 60% { -webkit-transform: translateY(-10%); transform: translateY(-10%) } } 

ブートストラップから「クロールしませんでした」:

 border-top: 4px solid \9; @media all and (transform-3d),(-webkit-transform-3d) @-ms-viewport { width: device-width } 

Habrから「クロールしませんでした」:

 @charset "UTF-8"; @-moz-document url-prefix() { .search-field__select { text-indent: .01px; text-overflow: '' } } 

Source: https://habr.com/ru/post/J316464/


All Articles