Dwango Erlang Utility Library "moyo"

[株式会社ドワンゴ](http://info.dwango.co.jp/)で使っている[Erlang Utility Library **"moyo"** ](https://github.com/dwango/moyo)について紹介する。

#なぜ作ったのか

"moyo"を作ったのには、Erlangを書き始めた人のだいたいが感じるだろう **理由** が存在する。それは、 *Erlangで標準に存在しているライブラリに足りないと感じるものが多い* からである。（偏った用途の関数は充実している。）Erlangを書いている多くの人が、同じようなライブラリを書いているのではないかと思われる。

#Githubリポジトリ

Githubのリポジトリは以下である。

[dwango/moyo | Github](https://github.com/dwango/moyo)

基本的な使い方は、[README.md](https://github.com/dwango/moyo/blob/master/README.md)に書かれているので参考にしてもらいたい。

#ライブラリ

全部で **16つ** のモジュールがある。そのモジュールを紹介する。

* <font color="red">**moyo_assoc**</font>
    * 連想リスト(assoc_list)に関する処理を集めたユーティリティモジュール.
    * proplistsと確実に違うところは、リスト内のすべての要素が ```{Key, Value}``` になっているところである。
        * ```Atom``` は存在しない。
    * proplistsの代わりによく使っている。
* <font color="red">**moyo_binary**</font>
    * バイナリに関する処理を集めたユーティリティモジュール.
    * Erlangでは ```string()``` があるが実際は ```list()``` であるため操作しづらいことがある。代わりに文字列を扱うときに ```binary()``` を使うことがあり、そのための関数が追加されている。
* **moyo_clock**
    * 日付や時間に関する処理を集めたユーティリティモジュール.
* **moyo_command**
    * 外部コマンドの実行に関する処理を集めたユーティリティモジュール.
    * ```{Key, Value, Opts}``` 形式のリストでコマンドを生成することもできる。
* **moyo_cond**
    * 条件分岐処理関連のユーティリティ関数を提供するモジュール.
    * 条件によっては何もしたくないときに使うための関数等が存在する。
        * ∵ ```if``` , ```case``` が条件に一致しない時も返す値を設定しなければならない
* **moyo_file**
    * ファイル関連の処理を集めたユーティリティモジュール.
    * ```file:open/2``` , ```file:close/1``` 等で、（元々、ok/error形式のものを）例外を投げるようにした関数等が定義されている。
* **moyo_frac**
    * 分数を扱うモジュール.
    * recordで ```fraction()``` データを内部で定義して、簡単な計算ができるようになっている。
* **moyo_fun**
    * 関数に関する処理を集めたユーティリティモジュール.
    * ```apply``` , ```call``` で例外が発生した場合に、 ```{error, Reason}``` を返す関数等が実装されている。
* <font color="red">**moyo_list**</font>
    * リストに関する処理を集めたユーティリティモジュール.
* **moyo_math**
    * 数学的な関数を集めたモジュール.
    * ```ceil``` , ```floor``` , ```gcd``` 等、一般的な関数が存在する。
        * 逆に言うと標準のライブラリにこれらの関数が存在しない…。
* **moyo_monad**
    * モナドに関する処理を集めたユーティリティモジュール.
* **moyo_pipe**
    * ポート(外部コマンド)に対するパイプ入出力機能を提供するためのモジュール.
* **moyo_string**
    * 文字列(整数値のリスト)に関する処理を集めたユーティリティモジュール.
* **moyo_url**
    * URL関連の処理を集めたユーティリティモジュール.
    * URLをエンコード/デコードするための関数等がある。
* <font color="red">**moyo_validator**</font>
    * バリデーションに関する処理を集めたユーティリティモジュール.
    * typeだけでなく、その他制限を掛けて評価するためのバリデータ関数がある。
* **moyo_xml**
    * XMLに関する処理を集めたユーティリティモジュール.

##よく使う関数の紹介

###[moyo_assoc](https://github.com/dwango/moyo/blob/master/doc/moyo_assoc.md)

元々、mapsがなかったときに、それでするだろう処理を行うために使っていた（使っている）モジュールである。OTP 17からmapsが使えるようになったので、maps用の関数を作ったほうが有用かもしれない（個人的な意見）。

* ```fetch/2,3``` , ```lookup/2``` , ```delete/2``` , ```store/3```
    * 連想リストに対して値を追加したり削除したりする関数
* ```fetch_as/3``` , ```lookup_as/3``` , ```lookup_entries_as/2``` , ```lookup_value_as/2```
    * 連想リストに対して、 ```EntrySpecList``` で指定された方式で、エントリー(要素)一覧を取得する関数
        * 指定方法の詳細は[moyo_validator](https://github.com/dwango/moyo/blob/master/doc/moyo_validator.md)モジュールを参照
* ```push/3``` , ```pop/2```
    * 指定したキーに対して値を追加する。
* ```from_record/2``` , ```to_record/3```
    * record-連想リスト間で相互に変換する。
* ```equal/2``` , ```diff/2```
    * 連想リストとして、等しいかどうか比較する。
        * *連想リストとして等しい* : 順番が関係なく要素が等しい。

###[moyo_binary](https://github.com/dwango/moyo/blob/master/doc/moyo_binary.md)

* ```strip/1-4```
    * 両端から文字を取り除く。
* ```join/2```
    * バイナリを連結する。
* ```abbreviate/2,3```
    * 入力バイナリが指定した最大長を超えている場合に指定された省略文字列を使って切り詰めを行う。
* ```to_binary/1```
    * どんなErlang項( ```term()``` )をバイナリに変換する。
* ```try_binary_to_existing_atom/2```
    * 変換後の ```atom()``` が存在しなかったら ```binary()``` のまま返す。

###[moyo_list](https://github.com/dwango/moyo/blob/master/doc/moyo_list.md)

* ```maybe_foldl/3``` , ```maybe_foldr/3``` , ```maybe_foreach/2``` , ```maybe_map/2```
    * 基本的にはlistsモジュールの ```foldl/3``` , ```foldr/3``` , ```foreach/2``` , ```map/2``` と同様の処理を行う。
    * リストの各要素への関数の適用時、返り値が ```{error, Reason}``` になった時点で処理を中断する。
* ```take/2```
    * 指定した要素を除いたリストを返す。
* ```take_if/2```
    * 関数を適用して最初に ```true``` になった要素とその要素を除いたリストを返す。
* ```find_if/2```
    * 指定した関数が最初に ```true``` となった要素を返す。

###[moyo_validator](https://github.com/dwango/moyo/blob/master/doc/moyo_validator.md)

* 存在する関数は ```validate/2,3``` のみ
    * 型や制限を指定して、値をバリデートすることができる。
        * 制限はand/orで指定できる。
    * どんな制限があるかを紹介したい
        * ```integer()``` , ```float()``` に対して掛けられる制限
            * ```positive``` , ```negative``` , ```non_negative```
                * 正負を指定する。
            * ```even``` , ```odd```
                * 遇奇を指定する。
            * ```more``` , ```range``` , ```less```
                * 値の範囲を指定する。
        * ```binary()``` , ```string()```
            * ```{max_length, integer()}```
                * 長さを指定する。
            * ```{regexp, binary()}```
                * 正規表現を指定する。

# 最後に

紹介した以外にも、社内で普段から使っている関数がまだまだある。興味がある人は使って頂いて、フィードバック等をいただけるとありがたい。