1
/
5

Rubyアプリのコードレビューを支えるsaddler

こんにちは、むらはし こと sanemat です。
rubocopをコード増分だけに適用して通知したい。lintを増分だけ掛けたい。あると思います。

曰く「増分だけに対応してほしい」
曰く「テスト遅くなるのは嫌だ」
曰く「引っかかってもテストは落ちないで欲しい」
卜部「大量にwarningでるとやる気が尽きるのでは」

いやーテキ屋とサクラかな、とおもった。
rubocopを増分だけに適用してGitHubのpull requestに通知する、便利なツールがあります。

rubocopを増分だけに適用してGitHubのpull requestに通知する、便利なツール

こんな感じに通知できます。

overcommitでもいいんだけど、bundlerなどで固定してるバージョンで、やりたいですね。

マネーフォワードではCIにJenkinsを使っているので、ここではJenkinsです。設定はCI as a Serviceのほうが便利なのですが、金突っ込んだら強いマシンが使えるのでJenkinsは強い。あとGitHub pull request builder pluginアリを前提にします。

さて、jenkins上では、コミット差分でdiff取りたい。CI用に直接sedなどで設定書き換えてたりもあるし。ローカルでは、コミット前のものも検出したい。

では、こちらでどうでしょう。

#!/bin/bash
# Usage:
#
# on Jenkins (post build task on post build actions)
#
# ```
# cd path/to/project
# NOTIFY_TO_PULL_REQUET="./notify-to-pull-request.sh"
# if [ -f $NOTIFY_TO_PULL_REQUET ]; then
#   bash $NOTIFY_TO_PULL_REQUET
# fi
# ```
#
# Add access token. E.g. Environment Injector Plugin
# GITHUB_ACCESS_TOKEN=write_your_access_token_here
#
#
# on local
# NOTE: This is too slow, please use editor's checker or IDE's one.
# ```
# NOTIFY_BASE=upstream/release bash ./notify-to-pull-request.sh
# ```
#
# Dependencies:
#
# Gemfile
# group :development, :test do
#   gem "checkstyle_filter-git", require: false
#   gem "rubocop", require: false
#   gem "rubocop-checkstyle_formatter", require: false
#   gem "rubocop-select", require: false
#   gem "saddler", require: false
#   gem "saddler-reporter-github", require: false
# end

set -eu

# http://qiita.com/ngyuki/items/b2e291e07f6d2b2c353e
if [ -n "${JENKINS_URL-}" ]
then
  NOTIFY_BASE=origin/$ghprbTargetBranch
  DIFF_RANGE=$NOTIFY_BASE..
  SADDLER_ARGS=' --require saddler/reporter/github --reporter Saddler::Reporter::Github::PullRequestReviewComment'
else
  DIFF_RANGE=$NOTIFY_BASE:./
  SADDLER_ARGS=' --require saddler/reporter/text --reporter Saddler::Reporter::Text'
fi

TARGET_FILES=$(git diff -z --name-only $DIFF_RANGE \
             | xargs -0 bundle exec rubocop-select)

if [ "${TARGET_FILES}" == "" ]; then
  echo "no rubocop target found"
  exit 0
fi

git diff -z --name-only $DIFF_RANGE \
  | xargs -0 bundle exec rubocop-select \
  | xargs bundle exec rubocop \
      --require rubocop/formatter/checkstyle_formatter \
      --format RuboCop::Formatter::CheckstyleFormatter \
  | bundle exec checkstyle_filter-git diff $DIFF_RANGE \
  | bundle exec saddler report $SADDLER_ARGS

ローカルではこんな感じに実行する。
$ NOTIFY_BASE=upstream/release bash ./notify-to-pull-request.sh
起動おっそ! ローカルはエディタやIDEでチェックしてください。

jenkins上では
post build actionsのpost build taskで

cd path/to/project
NOTIFY_TO_PULL_REQUET="./notify-to-pull-request.sh"
if [ -f $NOTIFY_TO_PULL_REQUET ]; then
  bash $NOTIFY_TO_PULL_REQUET
fi

こんな感じで。

Environment Injector Plugin かなにかでaccess tokenをつっこんでおく。
GITHUB_ACCESS_TOKEN=write_your_access_token_here

jenkinsのプラグイン周りに思ったより苦戦しましたね。まだ動かないケースあるようです。すまん。
fatal: Not a valid object name (Git::GitExecuteError) on Jenkins · Issue #44 · packsaddle/ruby-saddler

展望

xargs

xargs 使ってるので、必然mac or linuxなのはのちのち。

gitlab

gitlab? おっ そうだな。
マネーフォワード社は多くのプロダクトはGitHubに移行済み。いくつかのプロダクトはセキュリティ要件的に自社Gitlabなので、reporter作らないと。reporterだけ作ればいけるはずだけど、gitlabのapiドキュメントまだ読んだこと無いのでまたいつか。

手作業

botを確認するのにリリース前にあちこち手作業で確認している(!) のは何を言っているかわからないので、いい感じに確認できるようにしたい。そろそろgithub hook受けられる確認用の割とまっさらなjenkins server立てようかと。

test

めっちゃテスト書きにくいところはテスト書いてないので変更がツライ。

参考URL

en packsaddle/ruby-saddlervi Saddler – công cụ giúp CI chạy rubocop và comment lỗi trực tiếp vào pull request. – Appconus Blogja jser/jser.github.ioの記事をpull request時にLintする仕組み | Web Scratch変更したファイルにrubocopやjscsを実行して pull requestに自動でコメントする – Saddler – checkstyle to anywhereCircleCI – Androidのコードを自動で解析し、GitHubのpull requestにコメントする – Qiitapull requestした差分にrubocopの結果を自動でコメントしてCircleCIをfailedにするよ – Qiita

以上デース

最後に

マネーフォワードでは、botが気になって夜しか眠れないエンジニアを募集しています。
ご応募お待ちしています。

株式会社マネーフォワードでは一緒に働く仲間を募集しています
元記事: Rubyアプリのコードレビューを支えるsaddler
1 いいね!
1 いいね!

今週のランキング

小川 昌之さんにいいねを伝えよう
小川 昌之さんや会社があなたに興味を持つかも