eyecatch
Wed, Aug 29, 2018

React + Reduxアプリケーションプロジェクトのテンプレートを作る ― その4: CSS ModulesとPostCSSとstylelintとstyled-components

ReactとReduxを学ぶために、開発環境というかプロジェクトテンプレートをスクラッチから作っている。 (最終的な成果はGitHubに置いた。) 前回はPrettierとESLintをセットアップした。 (adsbygoogle = window.adsbygoogle || []).push({}); CSS 前回までで作った環境で、Reactを使ってHTMLのDOMツリーを構築することができるようになったが、これは基本的にUIに表示する情報の構造しか定義しない。 UIの見た目(スタイル)を決めるのはCSSなので、それをアプリに組み込むことを考えないといけない。 組み込み方には現時点で大きく3通りある。 CSSを別途設計する 一つ目はCSSを別途設計する方法。 Reactコンポーネントからレンダリングされる要素にclassが付くようにしておいて、設計したCSSをbundle.jsとは別途読み込んでスタイルを適用することにはる。 この場合、CSSのスタイル定義はすべてグローバルなので、設計効率やメンテナンス効率を維持しつつ、各コンポーネントに意図したスタイルが適用されるようにするため、テクニックを凝らしてCSSクラスを設計する必要がある。 例えばBEM (2009年3月誕生)、OOCSS (2009年3月誕生)、SMACSS (2011年9月誕生)、FLOCSS (2014年4月誕生)など。 CSS自体は、素のCSSを書くことはあまりなく、普通はSassなどのAltCSSやPostCSSを使って書く。 さらに、stylelintでリンティングすることで、CSSの品質を上げられる。 リンティングルールは、stylelintプロジェクトから提供されているstylelint-config-recommendedかstylelint-config-standardを使えば十分。 後者がGoogleやAirbnbのCSSスタイルガイドを反映していていい感じ。 書いたCSSは、webpackのcss-loaderで読み込める。 webpackはJavaScriptのimport './App.css';みたいなコードを見つけると、css-loaderに処理を渡す。 css-loaderは、import文で指定されたCSSファイルだけでなく、@importやurl()で定義される依存関係をたどって関連するCSSを一通り読み込む。 読み込んだCSSは、webpackのstyle-loaderを使ってDOMに適用できる。 style-loaderは、読み込んだCSSを<style>タグで囲ってHTMLのヘッダに挿入してくれる。 CSSの処理にはPostCSSを使うとして、プロジェクトに以下のパッケージを追加する。 (PostCSSについてはQiitaの記事が参考になった。) css-loader: CSSを読み込むためのwebpackのローダ。 style-loader: CSSをDOMに追加するためのwebpackのローダ。 postcss-loader: PostCSSを実行するためのwebpackのローダ。 postcss-preset-env: CSSのエッジな機能を使うためのPostCSSプラグイン。 autoprefixer: CSSプロパティにベンダプレフィックスを追加してくれるPostCSSプラグイン。 postcss-flexbugs-fixes: Flexboxのバグを修正してくれるPostCSSプラグイン。 cssnano: CSSをミニファイしてくれるPostCSSプラグイン。 stylelint: CSSのリンタ。 stylelint-config-standard: stylelintのルール設定集。 stylelint-config-prettier: Prettierが施すコード整形とコンフリクトするルールを無効にするstylelintルール設定集。 yarn add -D css-loader style-loader postcss-loader postcss-preset-env autoprefixer postcss-flexbugs-fixes cssnano stylelint stylelint-config-standard stylelint-config-prettier PostCSSとstylelintの設定は、それぞれpostcss.config.jsとstylelint.config.jsを書いてプロジェクトルートに置けばいい。 postcss.config.js: module.exports =
eyecatch
Thu, Aug 23, 2018

React + Reduxアプリケーションプロジェクトのテンプレートを作る ― その3: PrettierとESLint

ReactとReduxを学ぶために、開発環境というかプロジェクトテンプレートをスクラッチから作っている。 (最終的な成果はGitHubに置いた。) 前回はReactをセットアップした。 (adsbygoogle = window.adsbygoogle || []).push({}); フォーマッタとリンタ プロジェクトにフォーマッタとリンタを導入する。 フォーマッタはソースの体裁を整えるツール。 フォーマッタを使うことで体裁が統一され、ソースが読みやすくなり、品質向上につながる。 リンタはソースを静的解析して、潜在的なバグ、構造的な問題、体裁の問題を検出して警告してくれるツール。 フォーマッタは体裁だけ整えるのに対し、リンタは論理構造にも制約を課せるので、コーディングスタイルがより統一できたり、ミスをしやすい論理構造が無くなったりして、品質向上につながる。 JavaScriptのような動的型付け言語では、実行時まで顕在化しないバグを作りこみやすく、また実行時エラーの原因解析が静的型付け言語に比べて難しいので、フォーマッタとリンタでプログラム実行前に問題をできるだけ取り除いておくのが重要。 またチーム開発では、コードレビューでコーディンスタイルを見る必要がなくなり、効率化につながる。 Prettier フォーマッタにはPrettierを使う。 Prettierは2017年1月にリリースされた新しいツール。 構文解析をしてASTを構築し、そこからフォーマット済みコードを出力するので、従来のツールよりも厳密な整形(e.g. 行の最大長を考慮した整形)ができる。 また、opinionated(独断的)であることも特徴で、Prettierプロジェクトが推奨するフォーマットをほぼ強制し、設定がほとんどない。 このため導入が簡単だけど、かゆいところに手が届かないこともある。 JavaScriptの他、JSX、CSS、Markdown、GraphQLのフォーマットにも対応している。 まずプロジェクトにインストールする。 yarn add -D prettier v1.14.0が入った。 設定はprettier.config.jsというファイルを書いてプロジェクトルートに置けばいい。 prettier.config.js: module.exports = { printWidth: 100, // 行の最大長 tabWidth: 2, // インデント長 singleQuote: true, // 文字列をシングルクオートで囲う trailingComma: 'all', // オブジェクトのプロパティとか関数の引数を複数行で書いたときに、全行の末尾にカンマをつける }; また、フォーマット対象外のファイルを指定するファイルである.prettierignoreをプロジェクトルートに置く。 .prettierignore: node_modules/ dist/ node_modulesはnpmパッケージが入るディレクトリ。 実際はnode_modulesはデフォルトで無視されるから書かなくていいんだけど。 prettier-ignoreコメントを書くことで、ソースを部分的にフォーマット対象外とすることもできる。 最後に、npmスクリプトを書く。 package.json: (前略) "scripts": { + "format": "prettier --write **/*.jsx **/*.js **/*.css", "build": "webpack --config webpack.prod.js", "start": "webpack-dev-server --hot --config webpack.dev.js" }, (後略) これで、yarn formatを実行するとプロジェクト内ソースを一通りフォーマットできる。 ESLint リンタにはデファクトスタンダードのESLintを使う。 ESLintは2013年6月にリリースされたそこそこ歴史のあるツール。 リンティングルールがプラガブルで、豊富なルールを細かく制御できるのが特徴。 フォーマッタとしての機能もあるけど、そこはPrettierにまかせることにする。 JavaScriptもJSXもリンティングできる。 リンティングルールはAirbnbによるeslint-config-airbnbが有名なのでこれを使う。 ESLintを導入するために、以下のパッケージをプロジェクトにインストールする。 eslint: ESLint本体。 eslint-loader: webpackからESLintを実行するやつ。 eslint-config-airbnb: ESLintルール設定集。 eslint-plugin-import: eslint-config-airbnbのピア依存。import文を処理するためのESLintプラグイン。 eslint-plugin-jsx-a11y: eslint-config-airbnbのピア依存。JSXを処理するためのESLintプラグイン。 eslint-plugin-react: eslint-config-airbnbのピア依存。React特有のリンティングルールを追加するESLintプラグイン。 eslint-config-prettier: Prettierが施すコード整形とコンフリクトするルールを無効にするESLintルール設定集。 ピア依存をインストールするのにはちょっとコツがいるので、eslint-config-airbnbのドキュメントを参照すべし。 今回は以下のコマンドでインストールした。 yarn add -D "[email protected]>=1.6.0 <5.0.0" eslint-loader eslint-config-airbnb "[email protected]^2.12.0" "[email protected]^6.0.3" "[email protected]^7.9.1" eslint-config-prettier ESlintはv4.19.1が入った。 ESlintの設定は、設定ファイルである.eslintrc.jsをプロジェクトルートに置けばいい。 .eslintrc.js: module.exports = { env: { browser: true, }, extends: ['airbnb', 'prettier'], }; アプリの実行環境はブラウザなのでenv.browserをtrueにしている。 これにより、ブラウザ環境でデフォルトで使えるグローバル変数(e.g.
eyecatch
Wed, Aug 22, 2018

React + Reduxアプリケーションプロジェクトのテンプレートを作る ― その2: React

ReactとReduxを学ぶために、開発環境というかプロジェクトテンプレートをスクラッチから作っている。 (最終的な成果はGitHubに置いた。) 前回はNode.jsとYarnとBabelとwebpackをセットアップした。 (adsbygoogle = window.adsbygoogle || []).push({}); Reactとは 以前にも同じような事を書いたけど、改めてReactについて書く。 ちょっとコーディングの詳細にも触れながら。 ReactはViewを記述するためのライブラリで、特徴はVirtual DOMとJSX。 Virtual DOM Virtual DOMはDOMを仮想化するもので、JavaScriptからVirtual DOMでUIを記述してやると、それが実DOMに効率的に反映されるようになっている。 JSX Virtual DOMはJSXというHTMLみたいな言語で記述できる。 import React from 'react'; import ReactDOM from 'react-dom'; ReactDOM.render( <h1>Hello, world!</h1>, document.getElementById('root') ); こんな風に書くと、idがrootであるHTML要素の中に、<h1>Hello, world!</h1>がレンダリングされる。 上記コードの<h1>Hello, world!</h1>の部分がJSX。 コンポーネント JSXではコンポーネントを定義して新たなタグとして使うことができるので、再利用できるコンポーネントを作って、それらを組み合わせてUIを構築することで、効率的な開発ができる。 import React from 'react'; import ReactDOM from 'react-dom'; // Welcomeコンポーネントの定義 function Welcome() { return <h1>Hello, World</h1>; } // Welcomeコンポーネントのレンダリング ReactDOM.render( <Welcome />, document.getElementById('root') ); 上記コードではコンポーネントをfunctionで定義しているが、アロー関数で書いても全く一緒。 const Welcome = () => ( <h1>Hello, World</h1>; ); 関数の代わりにclassで定義することもできる。 class Welcome extends React.Component { render() { return <h1>Hello, World</h1>; } } 関数による定義とclassによる定義はおおむね変わらないが、stateとライフサイクルメソッドを使いたいときはclassにする必要がある。 props コンポーネントはレンダリングの際にpropsというパラメータを受け取って使うことができるので、上手く設計すれば汎用的なコンポーネントが書ける。 import React from 'react'; import ReactDOM from 'react-dom'; // Welcomeコンポーネントの定義 (props付き) function Welcome(props) { return <h1>Hello, {props.name}</h1>; } // Welcomeコンポーネントのレンダリング (props付き) ReactDOM.render( <Welcome name="Kaitoy" />, document.getElementById('root') ); propsはイミュータブルにしてコンポーネント内で変更しない(i.e.
eyecatch
Sun, Aug 19, 2018

React + Reduxアプリケーションプロジェクトのテンプレートを作る ― その1: Node.jsとYarnとBabelとwebpack

昔、Dojo Toolkitを使ってFlashなUIをJavaScriptに書き換えた時以来、仕事でWeb UIを触ることはなかったんだけど、最近になってWeb UIを書かなければいけなくなるような気がして再学習を始めた。 題材はReact (とRedux)。 今一番人気のフロントエンドフレームワークで、昔触ったこともあるので。 前回の記事でReactが生まれた経緯を学んだので、今回から実習に入る。 (adsbygoogle = window.adsbygoogle || []).push({}); プロジェクト作成 ちょっとCreate React Appを触ってみたけど使わないことにした。 すぐ開発始められるのはよかったんだけど、裏でなにが起こっているかわからな過ぎて肌に合わないし、使うライブラリが結構固定されちゃいそうだったし、トラブルシュート(特にライブラリのバグを踏んだ時)が大変そうだったので。 代わりに、公式で紹介されているブログ記事であるCreating a React App… From Scratch.を見ながら、スクラッチからプロジェクトを作ることにした。 環境はWindows 10 Home。 最終的な成果はGitHubに置いた。 Node.jsインストール なにはともあれNode.js。 Node.jsのバージョン管理には以前はnodist使っていたんだけど、こいつは2年ほど前に開発が止まっているので、代わりにnvm for Windowsを入れた。 nvm installで任意のバージョンのNode.jsをインストール出来て、nvm useで使うNode.jsのバージョンを切り替えられる。 今回使うNode.jsのバージョンは、現時点でLTS版の最新である8.11.4にする。 C:\>nvm install 8.11.4 Downloading node.js version 8.11.4 (64-bit)... Complete Creating C:\Users\kaitoy\AppData\Roaming\nvm\temp Downloading npm version 5.6.0... Complete Installing npm v5.6.0... Installation complete. If you want to use this version, type nvm use 8.11.4 C:\>nvm use 8.11.4 Now using node v8.11.4 (64-bit) Yarnインストール パッケージマネージャにはYarnを使う。 Yarnちょっとバギーだとか、npm 5がlockファイルをサポートしてYarnの優位性が減ったとか、Yarnからnpmに戻るためのツールが出てきたりしてるけど、現時点では深く考えずにYarnでいいと思う。 YarnはWindows環境ではMSIファイルをダウンロードして実行すればインストールできる。 (npmでもインストールできるけど邪道。) Yarnはv1.7.0を使う。 package.json生成 プロジェクトの構成情報を記述するファイルであるpackage.jsonをYarnで生成する。 C:\>mkdir react-redux-scaffold C:\>cd react-redux-scaffold C:\react-redux-scaffold>yarn init yarn init v1.7.0 question name (react-redux-scaffold): question version (1.0.0): question description: React Redux Scaffold question entry point (index.js): src/index.jsx question repository url: https://github.com/kaitoy/react-redux-scaffold.git question author: kaitoy question license (MIT): question private: success Saved package.json Done in 40.38s.