リファクタリング:Rubyエディション 第一章 写経してみた

初めて写経というものをやってみた。

ただ本を読むよりも、内容を深く理解できると感じた。

写経すると能動的な頭の使い方になって、内容を深く咀嚼できるのかな。

もちろん普通に読むより時間がかかる。当面は重要な本に絞って写経するようにしたい。

写経の方法は、以下のツイートを参考にさせていただいた。

作成したリポジトリを試しに公開してみる。もしほかの方にとって利用価値があるとすれば、テストをRSpecで書いているという点と、個人的に誤記に見える箇所を記録しているという点だと思う。(自分には、公式の正誤表を見つけられませんでした。ご存じの方はご指摘頂けると助かります。)

github.com

Node.js, npm, electron

Node.js, npm, Electronについて、言葉だけ知っていたが内容や関連がわからなかったので調べてみた。

端的に言うと以下のとおりだと認識した。

JSのサーバーサイド実行環境がNode.js。 Node.jsのパッケージマネージャーがnpm。 有名パッケージのひとつがelectron。 electronを使うと、マルチプラットフォームのデスクトップアプリがかんたんに作れる。

以下、もう少し詳しく書く。

Node.jsってなに?

JavaScriptの実行環境。サーバーサイドでJSが動かせるようになる。

$ node
> console.log('hello world!');
hello world!
undefined
> ⏎

npmってなに?

Node Package Manager。 公開されているJSパッケージをかんたんに取り込める。 パッケージの配布もできる。(自分の場合はインストールの利用が主だろう。) さまざまなパッケージが登録されている。"the world’s largest software registry."とのこと。

npmのコマンドはどんなのがあるの?

このあたりが気になった。

npm -l # display full usage info
npm config list
npm run <command> # Run arbitrary package scripts
npm ls # List installed packages

例えばどういうパッケージがあるの?

electron(デスクトップアプリ作成), Grunt(JSタスクランナー), Webpack(モジュールバンドラー)

electronについてもう少しくわしく

JSでマルチプラットフォームのデスクトップアプリが作れるようになるパッケージ。 メインプロセスでうウィンドウを制御する。 各ページはレンダラープロセスが担う。

メインプロセスってなに?

プログラムのエントリーポイント。main.jsとかindex.jsという名前であることが多い。 例えば、requireされるときにこのファイルの返り値が返される。詳細は下記の通り。 docs.npmjs.com

試しに、インストールしたモジュールの中を覗いてみた。

github.com

上記のelectron-quick-startでnpm installしてから、 適当にelectron-downloadモジュールの中を見てみる。 electron-quick-start/node_modules/electron/package.json では "main": "build/index.js", と記載されていた。 そして、 electron-quick-start/node_modules/electron-download/build/index.js はたしかに存在していた。

npmに対抗馬はいないの?

yarnがある。npmの欠点を解消すべく作られた。GoogleFacebookのひとたちも参加してるらしい。 www.webprofessional.jp

余談。yarnは、デフォルトでバージョンのロックファイルを生成する、というのをウリのひとつにしている。 npmでは自動で生成されないということを示唆していると思うのだが、electron-quick-startをnpm installしたら、package.json.lockが生成された。 どういうことだろう…npmも自動生成するようになったのか?node, npmのバージョンは下記の通り。

$ npm --version
5.5.1
$ node --version
v9.2.0

以上

git-flow調査メモ

git-flowとは?

Gitの活用ガイドライン
Gitは自由。運用方法は強制されない。いろいろ配慮が必要。
リリース準備はどう行う?並行機能開発はどう行う?複雑な並行開発に耐える方法をいちいち考えるのは大変。

2010年、Vincent Driessen氏がブログで「こんな感じで運用したらうまくいったよ」というのを報告。
nvie.com

できがいいので広まった。

メリットは?

規約ができる。考える、決める手間が省ける。

どういう開発を想定?

バージョンを切って、ある程度長い(数週間とか)スパンでリリースする開発。
常に最新がデプロイされているような開発は”GitHub Flow”のほうが向いている。

競合は?

GitHub Flow。プルリクエストを投げるやつ。
常にmasterがデプロイされるような、リリーススパンの短い開発に向いている。

git-flowのデメリットは?

学習が大変。Git自体のコマンドを理解していなければならない。
→ 専用ライブラリの導入で楽になる!git flowライブラリ

git-flowの発想は?

master,developがメインのブランチ。feature,release,hotfixがサポート。

  1. メイン
    1. master…常に、リリース準備完了の状態を持つ。
    2. development…次のリリースのための開発ブランチ。リリースのための開発が完了したら、masterに反映する。そしてタグを切る。
  2. サポート
    1. feature…機能開発のためのブランチ。developから分岐させ、完了したらdevolopにマージする。
    2. release…開発完了後、本番化直前の最後の微調整を行うブランチ。バグの修正など。リリースブランチが切られたら、次のバージョンのfeature開発に入れる。masterとdevelopにマージする。
    3. hotfix…本番化後のバグの緊急修正用ブランチ。masterから分岐させる。修正後、masterとdevelopにマージする。 ホットフィックスはマスター、リリースはデベロプをベースにしている。ほかは一緒。

git-flowプラグインの使い方は?

基本的に以下のとおり。操作対象と操作内容の組み合わせ。

git flow [feature|release|hotfix] [start|finish|publish|pull] [name]

疑問

・リモートリポジトリはフォークでなく、共通のがひとつあるだけでいいのか? →たぶんそう。 ・ローカルでマージしたdevelopブランチは、リモートにどう反映するのか? →たぶん普通にプッシュする。

git push origin [ブランチ名]

でプッシュする。
そこは特に専用コマンドはない模様。
release,hotfixで追加したタグは、以下のコマンドでリモートにも追加するのを忘れないようにすること。

git push --tags

(Qiitaで検索すると、リモートへの反映はPull Requestを活用するやり方が紹介されている。元ネタと違うように見えるが派生版か?)

参考

git-flowの考えを発表した元祖の記事 nvie.com

プラグインGithubリポジトリ(nvie版とavh版がある。以下はaptで導入できるavh版) github.com

プラグインの解説記事 jeffkreeftmeijer.com チートシート
http://danielkummer.github.io/git-flow-cheatsheet/index.ja_JP.html
チーム開発の運用ワークショップ d.hatena.ne.jp

tmux入れてみた

端末の画面を分割して表示したいと思った。

linuxの画面分割について調べてみると、tmuxやterminatorとかいうソフトウェアで実現できるとのこと。

terminatorは端末エミュレーターのひとつ、tmuxは端末マルチプレクサーのひとつらしい。 端末エミュレーター、端末マルチプレクサーとはなにか?よくわからなかった。今のところ以下のようにぼんやりと解釈している。合っているかはわからない。

  • 端末エミュレーター… 端末をエミュレートする。GUIからコンソールを覗ける?有名なのはgnome terminal, terminator, iterm2(Mac)など。
  • 端末マルチプレクサー…ひとつの仮想端末から複数のログインセッション(?)を扱える?有名なのはtmux,GNU screen, byobuなど。

画面分割機能はterminator,tmuxのどちらでも実現可能。 リモートからSSH接続したときでも画面分割が利用できるので、tmuxを入れることにする。

.tmux.confファイルに設定を記入する。ここを参考にした。 qiita.com

上記リンクのコピーモード設定はMacのもの。下記のページ群を参考に、Ubuntu版をファイルに記入した。 Everything you need to know about Tmux copy paste - Ubuntu · rushiagr coderwall.com qiita.com

# キーストロークのディレイを減らす
set -sg escape-time 1

# マウス操作を有効にする
setw -g mouse

# 256色端末を使用する
set -g default-terminal "screen-256color"

# ステータスバーの色を設定する
set -g status-fg white
set -g status-bg black

# ウィンドウリストの色を設定する
setw -g window-status-fg cyan
setw -g window-status-bg default
setw -g window-status-attr dim

# アクティブなウィンドウを目立たせる
setw -g window-status-current-fg white
setw -g window-status-current-bg red
setw -g window-status-current-attr bright

# ペインボーダーの色を設定する
set -g pane-border-fg green
set -g pane-border-bg black

# アクティブなペインを目立たせる
set -g pane-active-border-fg white
set -g pane-active-border-bg yellow

# コマンドラインの色を設定する
set -g message-fg white
set -g message-bg black
set -g message-attr bright

# ステータスバーを設定する
## 左パネルを設定する
set -g status-left-length 40
set -g status-left "#[fg=green]Session: #S #[fg=yellow]#I #[fg=cyan]#P"
## 右パネルを設定する
set -g status-right "#[fg=cyan][%Y-%m-%d(%a) %H:%M]"
## リフレッシュの間隔を設定する(デフォルト 15秒)
set -g status-interval 60
## ウィンドウリストの位置を中心寄せにする
set -g status-justify centre
## ヴィジュアルノーティフィケーションを有効にする
setw -g monitor-activity on
set -g visual-activity on
## ステータスバーを上部に表示する
set -g status-position top

# コピーモードを設定する
## viのキーバインドを使用する
setw -g mode-keys vi
## コピーモードの操作をviライクに設定する
bind-key -t vi-copy v begin-selection
bind-key -t vi-copy y copy-pipe "xsel --input --clipboard"

なお、普通にマウスでコピーしたいときは、shiftキーを押しながらコピーすればよい。地味に大事な情報だと思う。

Highcharts

Highchartsは、グラフを描画するJavaScriptのライブラリです。 商用利用にはお金がかかります。

第一引数にグラフ書き込み先のID、第二引数にoptionオブジェクトを渡すのが基本の使い方です。

Highcharts.chart('container', options);

といった形です。

optionオブジェクトで細かく描写を指定できます。指定方法はこちらにリファレンスがあります。

実際に描写を設定したいときは、上記のリファレンスから適当な単語で検索すればいいと思います。例えばタイトルの配置場所を変えたいとき、「title」で検索すると一覧に「title.align」が見つかります。

どのような単語で検索すればいいか見当がつかないときは、コンセプトのページやそのリンク先を見れば、HighCharts的になんという単語があてがわれているかがわかると思います。

たとえば、月別降水量のグラフ描写を設定していて、月と月の間に引いてある短い線の描写を設定したいとします。英語でなんと呼ぶか、highCharts的になんと呼ぶか、わからないとします。そのようなときは、上のコンセプトのページから「Axes」のページに飛ぶと、該当部分は「tick marks」と呼ばれていることがわかります。リファレンスで「tick」と検索欄に入力すると、関連する設定が出てきます。

JavaScript 分割代入

developer.mozilla.org

分割代入について。 配列からデータを変数に代入する、さまざまな方法が書いてあった。

  • テンポラリ変数を作らずに変数同士をスワップできる。
  • 不要な戻り値は無視し、必要なもののみ選択して受け取れる。「正規表現のマッチから値を取り出す」は真似したいと思った。

未サポートのブラウザが多いので注意。

自分は読み飛ばしたが、リンクには、オブジェクトからの取り出しについても記載がある。

モジュール、凝集度、結合度

モジュール

ソフトウェアは複雑だ。すぐ人間に管理できなくなる。 言い換えると、仕様変更があったとき、どこを変更すればいいのか、すぐわからなくなる。 そうならないために、プログラムを分割して複雑さを低く保つという考えがある。分割したひとつひとつをモジュールと呼ぶ。どういうふうにモジュールを区切ればいいかの指標として、結合度と凝集度という考え方がある。

凝集度

モジュール内の要素がすくないほど複雑度は減る。とはいえ、ひたすら細かく別モジュールに分けるべきではない。管理の手間がむしろ増える。関わりの強い要素をうまくひとつのモジュールとして切り出すべきだ。モジュール内の要素の関わりの強さを凝集度と呼ぶ。 じつは、すべての入出力操作をひとつにまとめたモジュールというのは、凝集度が低い。論理的な関係よりも、機能の関連度で評価するべきだからだ。そういう意味で、オブジェクト指向の多くのクラスは凝集度が低い。各メソッドで凝集度を高くなるように意識すべきだ。 ひとつの機能を実行するためにすべての命令が関連しているモジュールは、凝集度が高い。たとえば、秒速を時速に変換するメソッドだ。

結合度

モジュール内の変更が他のモジュールに影響を及ぼさないように注意すべきだ。他のモジュールへの影響しやすさのことを結合度と呼ぶ。結合度は低いほうが良い。 たとえば、あるモジュールが他のモジュールの内部を直接参照する実装は結合度が高く、避けるべきだ。 結合度が低い(=良い)状態とは、入力データと出力データをやり取りする形でモジュールが結合しているという状態だ。モジュール内を変更しても、入出力形式が同じなら、ほかのモジュールへの影響はない。