チーム移行するときに抑えておくべきポイント

概要

夏頃チーム移行があった。
移行してから驚いたことが多かったので、次回の機会のためにメモしておく。

  • すべての項目に遭遇したという話ではない
  • システムによって特性は異なるので優先順位や、必要かどうかは変化する

チェックすべきポイント

リポジトリを事前に見せてもらう

これから関わるプロダクトがどういうものか?事前に確認する必要がある。

ナレッジが管理されているか?

チームで活動していく上で必要なドキュメントが揃っているか?更新されているか?参照しやすい・検索しやすい状態になっているか?

各種図が存在するか?更新されているか?

システム構成図、ER図、クラス図、サーバ一覧などがあるか?
pngなど編集できないようなファイル形式で作らない。
ない場合は、システムの理解や問題発見につながるので早めにつくる。

セキュリティ対策できているか?

基本的なセキュリティについて、対策できているならその理由をまとめておく。
対策できていない場合は、ユーザやシステムに被害が出ないように最優先で対応する。

障害は検知できているか?

障害が起きてもわからないという状況をさけるため、障害検知は優先的におこなうべき。

ログ集約・監視はしているか?

「サーバ入ってファイルを見る」のような運用は辛いので、ログ集約・監視はやっておきたい。

パフォーマンスモニタリングできているか?

自分たちのシステムは、普段どれくらいのリクエストが来るか?CPU・メモリ利用率はどれくらいの値か?把握しておくべき。
パフォーマンスの異常を検知することで、障害の早期発見・事前解決につながる。

テストは書いてあるか?

単体テスト結合テスト、統合テストは書いてあるか?

遭遇した問題

  • 単体テストの中で外部APIを呼び出したり、DB処理をおこなっている。
    APIのテスト、DB処理のテストは必要だが、単体テストの中でおこなうと、テスト失敗の原因が分かりづらくなったり、単体テストに時間がかかるので分けるべき。
    さらにこのようテストをCI上でおこなうと、API呼び出しのためのトークンの登録なども必要になってくる。
  • 単体テストが書いていないのでコード変更の影響範囲がわかりづらい、結合テストが書いていないので検証に時間と労力がかかる。

CI・CDフローは整っているか?

自動テスト、自動デプロイできるようになっているか?
なるべく短い期間でデプロイするのが理想なので、デプロイに時間がかかったり、ミスが起きやすいフローになっている場合は修正する。

まとめ

これらの問題に対してチーム全体で話し合い、システムがどのような状況なのか?どこまでできるようにするのか?認識を合わせておく必要がある。
そうしないと、開発チーム間で認識の不一致が起きてストレスを抱えながら開発することになる。

Qiita記事をローカル管理するツールが入門としてよかった話

概要

Goの入門としてQiitaをローカル管理するツールを作った。
リポジトリは以下。
https://github.com/ma-bo-do-fu/qsync
今回はその感想をメモしておく。対象読者はGo言語やツール開発初心者。

環境

$go version
go version go1.10.3 darwin/amd64

モチベーション

  • Goの練習したい
  • Qiita記事をGithub管理したい
  • ドキュメント管理をCIに載せたい

作ったもの

詳細は下記参照。
https://github.com/ma-bo-do-fu/qsync/blob/master/README.md
概要だけ記載する。

$qsync pull

すべての投稿を指定した場所に保存する。

$qsync push /path/to/entry

保存した投稿を更新する。

$qsync post

新規に投稿する。

入門としてよかった点

題材が練習としてちょうどよかった。 今回のツールを通して以下の処理について学ぶことができた。

  • APIクライアント
  • josnやyamlエンコードとデコード
  • 文字列操作
  • ファイル読み書き
  • 日付操作

問題点

画像添付できない

画像添付用のAPIがないので画像が添付できない状態。
運用としてローカルで画像保存用のディレクトリ(例:YYYY/mm/dd/images)を作ってそこで管理し、記事公開時に改めてブラウザ側で添付するなどか…
Qiitaの画像はS3で管理されているので、

$qsync attach 記事ID /path/to/image

とかでS3のURLが返ってきたらローカルで作業が完結できそう。

マークダウンの表示が異なる

VSCodeのマークダウンプレビューととQiitaの編集画面とで表示が異なる。 結局微調整のためにブラウザで編集することに…

感想

  • テストを書かずに開発するのはつらい
    とりあえず動くものを作ろうとテストを書かずに開発したら苦労した。次はテストの書き方を覚える予定。
  • 毎回go build/go installをするのが大変
    コード変更したら自動でビルドとインストールが走るようにしたい。
  • プロジェクトの名前が被っていた
    ツールを作るときはGoogleGithubで検索して被っていないか調べたほうが良い。
  • rangeの書き方が馴染んだ
    tour of goをやっているときにrangeの書き方に戸惑ったが、ツールを書いていたら馴染んだ。
  • gometalinterを早めに入れればよかった
    linterは開発初期から入れるべき。後から入れると修正が大変。
  • ちゃんと設計しないと後からつらくなる
    README駆動開発という言葉もあるように、最初に要件定義を書くと全体の見通しが立ちやすいと思う。

何かのサービスのAPIクライアントを作るのは、その言語に初めて触れるときに良い練習になると感じた。 新しい言語を学びたいけど作るものに困っている方はAPIクライアントにチャレンジしてみるとよいかもしれない。

php artisan migrateでautoload.phpがなくて失敗する

環境

$ php -v
PHP 7.1.10 (cli) (built: Aug 22 2018 18:45:08) ( NTS )
Copyright (c) 1997-2017 The PHP Group
Zend Engine v3.1.0, Copyright (c) 1998-2017 Zend Technologies
    with Xdebug v2.6.1, Copyright (c) 2002-2018, by Derick Rethans

発生したエラー

$php artisan migrate

Warning: require(/var/www/app/bootstrap/../vendor/autoload.php): failed to open stream: No such file or directory in /var/www/app/bootstrap/autoload.php on line 17

状況

  • /var/www/app/bootstrap/../vendor/autoload.phpが存在しない
  • vendor/は存在する

原因究明

$composer install -vvv

とすることでcomposer installデバッグログが見れる。
すると下記のようなエラーが(docker-comopseで実行していた)

app_1    | 
app_1    |                                                                 
app_1    |   [RuntimeException]                                            
app_1    |   /var/www/app/vendor does not exist and could not be created.  
app_1    |                                                                 
app_1    | 
app_1    | Exception trace:
app_1    |  () at phar:///usr/bin/composer.phar/src/Composer/Util/Filesystem.php:186

解決方法

プロジェクトルート(今回は/var/www/app/)に書き込み権限を与えて解決

業務の引き継ぎの難しさを考える

概要

現在チームが変わって業務の引き継ぎを受けている。
自分は引き継ぎを受ける側が二回目ぐらい(昨年の前チーム参画時)で、現状のつらい点、こうしたら個人的には嬉しいという点を記録する。
引き継ぐときに読み返して引き継ぎ元のチームが楽できるようにしていきたい。

つらい点

引き継ぐプロダクトの数が多い

4つのプロダクトを一気に引き継いでいる。エンジニア3人(うち一人は教育期間中の新人)、デザイナ1人なので人数が足りない。
1プロダクトに最低1人はほしい。

ミーティング多すぎ

引き継ぎミーティングがあったが、そのほとんどが、ドキュメントを見ながらそのとおりに話すというものなので、かなり苦痛だった。
しかも1件4時間くらいありかなり長い。
顔を突き合わせてドキュメントを読む必要性あるのか疑問に感じた。
言わなくても読めばわかるし、わからなかったら資料にコメントしたり、まとめて通話で質問して、それをメモすればよいと思う。

また、説明だけ受けてこれで引き継ぎは終わりです。といった感じだったので、かなり違和感を感じた。
引き継ぎの目的は、引き継ぎ元が説明することではなく、引き継ぎ先のチームが業務を遂行できることであると思う。

ドキュメントは必要であるが、そこに書いてある詳細なことはその知識が必要なときに都度調べればよい。

理想として、下記4つをこなすといいのではないかと思った。

  • 全体像・概要・役割を自分で説明できる
  • ナレッジがどこにあるか把握できる
  • 業務がリスト化されその手順がまとまっている
  • 上記手順に沿ってハンズオン形式で業務を経験する

ドキュメントが足りない・品質が低い

システム構成図、クラス図、ER図などが足りない。または古くなっている。バージョン管理されてない。
jpgになっており編集できない。

ツールは何でもいいけど、バージョン管理してて後続のチームが更新できるようになっていれば良いと思う。

リリースのハードル高杉

ブランチ運用の流れが独自運用になっててつらい。
8個くらい手順が書いてあって、「必ず〇〇すること」のように赤字で注釈がたくさんついており、運用でカバーしている様子が溢れている。
先日早速事故りそうになった。

github-flow/git-flowに寄せたい。引き継ぐとき「github-flowです」の一言で済ませたい。

今後の目標

その他にも

  • テストが書いていない
  • アプリがバージョン管理されてない
  • コードの中身もお察し

という感じで頭が痛くなってきたので一旦終了。

まずは運用周りを整備してストレスなくリリースできるところまで持っていきたい。

IntelliJがシステム環境変数を読み込むタイミングについて

概要

IntelliJがシステム環境変数を読み込むタイミングはIDE起動時。 途中でシステム環境変数を設定した場合はIDE再起動すること。

環境

$go version
go version go1.10.3 darwin/amd64

IntelliJ IDEA 2018.2.1 (Ultimate Edition)
(Goのプラグインを入れている)

再現手順

  1. HOGE="fuga"という環境変数を設定
  2. 以下のコードをIntelliJでctrl+shift+dでデバッグ
package main

import (
    "fmt"
    "os"
)

func main() {
    hoge := os.Getenv("HOGE")
    fmt.Println(hoge)
    fmt.Println("end")
}
  1. 出力結果
end

対応

IDEを再起動する。

感想

焦ってNode.jsで同じコードを書いて確認した。 go runしたらちゃんとシステム環境変数が読み込まれるので、IDEに問題があることに気づけた。

TODO

システム環境変数を更新したら毎回再起動するのは面倒なのでなにかいい方法がないか調べる。

vagrant up時にThe box 'bento/centos-6.8' could not be foundと表示される

問題

vagrant upしようとすると下記メッセージが出て失敗する。

$vagrant up
Bringing machine 'webserver' up with 'virtualbox' provider...
Bringing machine 'database' up with 'virtualbox' provider...
==> webserver: Box 'bento/centos-6.8' could not be found. Attempting to find and install...
    webserver: Box Provider: virtualbox
    webserver: Box Version: >= 0
The box 'bento/centos-6.8' could not be found or
could not be accessed in the remote catalog. If this is a private
box on HashiCorp's Atlas, please verify you're logged in via
`vagrant login`. Also, please double-check the name. The expanded
URL and error message are shown below:

URL: ["https://atlas.hashicorp.com/bento/centos-6.8"]
Error: The requested URL returned error: 404 Not Found

https://atlas.hashicorp.com/bentohttps://app.terraform.io/bento にリダイレクトされたので表示されているURLが古いっぽい。

解決方法

vagrantのバージョンをあげる。
アップデート前

$vagrant --version
Vagrant 1.9.3

アップデート後

$vagrant --version
Vagrant 2.1.2

CircleCI上でDockerfileのCMDが動かない

問題

CircleCI上でDockerイメージを使うとDockerfileのCMDが動かない。 ローカルでDockerコンテナを起動するとCMDが動く。

原因

最初のコンテナはcommandを書かないとエントリポイントが動かない https://circleci.com/docs/2.0/configuration-reference/#docker

For primary container (listed first in the list) if no command is specified then command and image entrypoint will be ignored, to avoid errors caused by the entrypoint executable consuming significant resources or exiting prematurely. At this time all steps run in the primary container only.

以下のようにDockerイメージをビルドしてコンテナに入ると、エントリポイントのスクリプトが動いている事がわかる。

$ cat Dockerfile 
FROM selenium/standalone-chrome
$ docker build . -t test:test
…
Successfully built 251941c07ece
Successfully tagged test:test
$ docker run -itd 251941c07ece
2848233eeaed57f855915a9046836f0f193d6bea71daa231df95203d8fbfac09
$ docker exec -it 2848233eeaed57f855915a9046836f0f193d6bea71daa231df95203d8fbfac09 /bin/bash
seluser@2848233eeaed:/$ ps auxw
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
seluser      1  0.2  0.1  20980  3332 pts/0    Ss+  15:44   0:00 /bin/bash /opt/bin/entry_point.sh
seluser     10  0.0  0.0   4500  1616 pts/0    S+   15:44   0:00 /bin/sh /usr/bin/xvfb-run -n 99 --server-args=-screen 0 1360x1020x24 -ac +extension RANDR java -jar /opt/selenium/selenium-server-standalone.jar
seluser     21  0.2  2.0 213644 41396 pts/0    Sl+  15:44   0:00 Xvfb :99 -screen 0 1360x1020x24 -ac +extension RANDR -nolisten tcp -auth /tmp/xvfb-run.JaVrPQ/Xauthority
seluser     26  5.8  2.5 2968504 51176 pts/0   Sl+  15:44   0:01 java -jar /opt/selenium/selenium-server-standalone.jar
seluser     46  0.7  0.1  21188  3668 pts/1    Ss   15:44   0:00 /bin/bash
seluser     53  0.0  0.1  37360  3228 pts/1    R+   15:44   0:00 ps auxw

エントリポイントをたどると以下のようになっている

しかし、CircleCI上で動かすと、selenium-server-standaloneなどが動いていないことが確認できる。

config.yml

version: 2
jobs:
  build:
    docker:
      - image: selenium/standalone-chrome
    steps:
      - checkout
      - run: ps auxw

workflows:
  version: 2
  build_and_test:
    jobs:
      - build

f:id:mMQnaZ7vL2DWkoU:20180712004910p:plain

対応

config.ymlにcommandを追加する。

version: 2
jobs:
  build:
    docker:
      - image: selenium/standalone-chrome
        command: ["/opt/bin/entry_point.sh"]
    steps:
      - checkout
      - run: ps auxw

workflows:
  version: 2
  build_and_test:
    jobs:
      - build