TeXの表記揺れをCIで自動チェックする

# TeXの表記揺れをCIで自動チェックする
## 背景
大学のプロジェクト学習という科目の講義で、プロジェクトの報告書を成果物として提出する必要があるため、TeXを用いて複数人で報告書を作成しています。

プロジェクト人数が30人を超え、報告書のページ数も100ページほどあるため、人力で表記揺れをチェックするのはすごく大変です。そのため、今回CIを用いて表記揺れチェックの作業を自動化してみました。

## tl;dr
作ったもの: https://github.com/natmark/TeX-Textlint

## 環境
Mac OS X El Capitan 10.12.4
Node.js 6.9.1
npm 3.10.8

## 　システム構成
![Group 2.png](https://qiita-image-store.s3.amazonaws.com/0/84888/46efa544-e845-31a0-f2aa-e0ff1bbddf74.png)

GitHubでTeXファイルを管理し、編集分をPushしてプルリクエストを作成する流れにしました。
プルリクエスト作成時にTravis CIのチェックを入れるようにしています。

## ファイル構成
```
TeX-Textlint
├── .travis.yml  　　# travis CIの設定用ファイル
├── .textlintrc  　　# textlintの設定用ファイル
├── main.tex     　　# TeXファイル
├── package.json 　　# パッケージ管理用のファイル
└── prh.yml       # 文章チェック用のルールファイル
```

## 実装
```yaml:.travis.yml
language: node_js
os: osx
node_js:
    -   "6"
before_script:
    -   npm install
script:
    -   npm run --silent textlint-check
cache:
    directories:
        -   node_modules
```

TravisCIの準備はこのあたりを参考にしてください

- http://edev.seesaa.net/article/426777689.html
- http://knowledge.sakura.ad.jp/tech/3754/


```json:.textlintrc
{
    "rules" : {
        "prh": {
            "rulePaths": [
                "./prh.yml"  //ルールファイルのパス
            ]
        }
    }
}
```

```json:package.json
{
  "name": "tex-textlint",
  "version": "1.0.0",
  "description": "TeX auto calibration using textlint + prh",
  "main": "index.js",
  "config": {
          "texpath": "main.tex" //チェック対象ファイルのパス
  },
  "scripts": {
    "textlint-check": "cp ${npm_package_config_texpath} output.txt && $(npm bin)/textlint output.txt && { rm output.txt ; exit 0 ; } || { rm output.txt ; exit 1 ; }",
    "textlint-fix": "cp ${npm_package_config_texpath} output.txt && $(npm bin)/textlint --fix output.txt && cp output.txt ${npm_package_config_texpath} && { rm
output.txt ; exit 0 ; } || { rm output.txt ; exit 1 ; }"
  },
  "author": "",
  "devDependencies": {
    "textlint": "^8.2.1",
    "textlint-rule-prh": "^4.0.1"
  }
}
```

npm(Node Package Manager)を用いて、プレーンテキストとMarkdownファイルのチェックが行える[textlint](https://github.com/textlint/textlint)と、textlintから校正補助ツールの[prh](https://github.com/prh/prh)を使用するためのプラグインである[textlint-rule-prh](https://github.com/azu/textlint-rule-prh)をインポートしています。

## TeXファイル
```TeX:main.tex
\documentclass{article}

% 年度の指定
\thisYear{2017}

% プロジェクト名
\jProjectName{サンプルプロジェクト}

% 1.0.1
\subsection{開発体制}
今年度はアプリ班とサーバ班に分かれて開発を行った. また, 開発と並行してビジネスモデルを考案するビジネス班を設置した.

\bunseki{田中}

% 2.0
\section{役割設定}
% 2.1.1
\subsection{プロジェクトリーダーの役割}
プロジェクトリーダは, プロジェクトが円滑に進むように, スケジュールの作成やタスク管理等を行なう.
\bunseki{佐藤}

% 2.2.1
\subsection{アプリケーション開発班の役割}
アプリケーション班は, ios班とandroid班に分かれて作業を行った. 前期はiOS班はSwiftの勉強, Android班はKotlinの勉強をメインに行った.
\bunseki{高木}

% 2.2.2
\subsection{サーバ班の役割}
サーバ班はAPI設計の勉強及び、 Ruby on Railsの勉強をメインに行った。
\bunseki{山田}

% 2.2.3
\subsection{ビジネスモデル班の役割}
ビジネスモデル班では, 既存アプリの調査をメインに行った.
\bunseki{加藤}
```
上記のようなサンプルを用意しました。

## ルールファイル
```yaml:prh.yml
# prh version
version: 1
rules:
    # よくある表記揺れ
    - expected: "アプリケーション"
      patterns:
          - "アプリ(?!ケーション)" # 正規表現も使える

    - expected: "iOS"
      patterns:
          - "IOS"
          - "ios"

    - expected: "リーダー"
      patterns:
          - "リーダ(?!ー)" # 正規表現も使える

    # 句読点
    - expected: ","
      patterns:
          - "、"
          - "，"

    - expected: "\\."
      pattern: "。"
```
YAMLでルールを記載します。
基本的には

- `expected` に統一する文字
- `patterns` に表記揺れしている文字セット

を記載すればOKです。

### 特殊なルール

```
- expected: "リーダー"
    patterns:
         - "リーダ"
```
みたいなルールは実行するたびに`リーダ`を`リーダー`に置換しようとするので、
`リーダーーーーーーーーーーー(ry`状態になってしまう。

正規表現が使えるので

```
- expected: "リーダー"
    patterns:
         - "リーダ(?!ー)" # 「リーダ」の後ろに伸ばし棒がなければ「リーダー」に置換
```

とする必要があります。

詳しいルールの例としては下記を参考にしてください。

- [azu/prh-textlint-example](https://github.com/azu/prh-textlint-example/blob/master/prh.yml)
- [prh/rules](https://github.com/prh/rules/tree/b21ed03ff752a961d22b7b47c1dc47a11c510f8f/media)

## プルリクエストを投げてみる

<img width="686" alt="スクリーンショット 2017-07-09 12.51.04.png" src="https://qiita-image-store.s3.amazonaws.com/0/84888/9bb534fc-b35f-5613-eac5-aafb45c0d29c.png">

Detailsから、CIのチェック状況を確認できます。

<img width="813" alt="スクリーンショット 2017-07-09 13.05.07.png" src="https://qiita-image-store.s3.amazonaws.com/0/84888/c3be6925-7b62-ba98-a0a5-3037ec590f97.png">

もしエラーがあれば、上の画像のように、linter errorが表示され、Travisのビルドが通らないようになっています。

<img width="685" alt="スクリーンショット 2017-07-09 13.06.01.png" src="https://qiita-image-store.s3.amazonaws.com/0/84888/2c389713-1460-4281-833d-35946d819e33.png">

エラー部分を修正して、再度Pushを行なうと
<img width="684" alt="スクリーンショット 2017-07-09 13.13.05.png" src="https://qiita-image-store.s3.amazonaws.com/0/84888/b238c8ab-24b5-c378-b9f2-3f7230dda9c6.png">

ビルドが通るようになります。

## 自動チェックと自動校正
ローカル環境で自動チェックと自動校正ができます。

`node.js`が必要なので、自分の環境になければ `$brew install node`を使用して、`node.js`をインストールしてください。

```zsh
$ cd TeX-Textlint # プロジェクトフォルダに移動
$ brew install node # node.jsが必要
$ npm install # ライブラリの導入
```

### 自動でチェックする場合
`textlint-check`コマンドを使用することで, `prh.yml`のルールに沿って自動チェックができます

```
$ npm run --silent textlint-check # 自動チェックする場合
```

### 自動で修正する場合
`textlint-fix`コマンドを使用することで, `prh.yml`のルールに沿って自動校正ができます.

```
$ npm run --silent textlint-fix # 自動校正する場合
```

## まとめ
TeXを複数人で書いている環境で、「うちはこうしてるよ！」というのがあればぜひ教えてください😊