モノレポの話をmessage passingでしていて、思った事。

morritaさんが後半言っている事はなかなかいいポイントをついていると思っていて、 モノレポという大雑把なしくみから、ベストプラクティスとして引き出すべき物というのがいろいろあるよなぁ。

モノレポから引き出されたベストプラクティスという事を考える材料として、 組織ごとに、もっと言えば会社ごとにレポジトリが分かれてしまうという問題について、 もうちょっと詳細を述べておきたい。 ここでは複数の会社を寄せ集めて、比較的小規模な一つのプロジェクトをやる、というケースについて考える。 なんで小規模なのに会社が複数あるの?と思う人にはちょっとわかりにくいシチュエーションかもしれないが。

組織の境界とバイナリの境界

少し乱暴に簡素化して話すと、レポジトリの分割というのは、開発の都合としてはある種のバイナリ的な境界で行われるべきだ。 例えばdeployの単位とか、ビルドして一つのアプリになるならそれは一つのレポジトリの方が良い、とか、 ライブラリとしてリリースされるならライブラリが一つのレポジトリとか。 これをバイナリ的な境界、と呼ぶ事にしよう。

これはそこで分けるべき、という話じゃなくて、そこよりも小さな単位で分けるべきでは無い、という話。 ライブラリごとにレポジトリを分けるべきかは分からない、だが少なくともライブラリの内部でレポジトリは分けない方が良い。

ある変更を行った時に、なるべく変更の単位は一つのレポジトリに収まる方が良くて、 いつも複数のレポジトリにまたがって変更を入れるのは良くない。 そうした事情を勘案して、複数あるバイナリ的な境界の中から適切な単位を選ぶ、 これがよくあるpolyrepo的な前提と言えると思う。

一方で、会社ごとにレポジトリを分ける、というのはこれとは違う。 会社はバイナリの境界では無く、開発する人間側の話だ。 会社は担当するバイナリ境界を持っている事が多いのでバイナリ境界と一致している事もあるのだけれど、 適切な境界を技術的な事情では無く組織的な事情で決めるので、やはり上記のpolyrepoとはだいぶ違う分かれ方となる。

組織の境界でレポジトリを切るという事の含意

なぜ会社ごとにレポジトリを分けるのか、そして相手のコードを見れなくするのか。 そこには、レポジトリを区切るという問題を超えた問題が背後にある。

なんでそういう事をしたがるのかというと、仕事の責任の境界をはっきりさせたいからだ。 ここより向こうで起きたものは向こうの会社の責任、ここよりこちで起きたものはこちらの会社の責任。 これはプロジェクトとしてbug fixとかのコストを下げるとかの開発的な効率よりも優先している何かでレポジトリを分割している、という事だ。

プロジェクトが失敗した時の予防線と言える。 プロジェクトが失敗しても、自分の所で火を吹かなければ問題が無い。 自分に被害が無いように境界をきっちりと定めて、その向こうの事はこっちに来ないように壁を厚くする。 そしてプロジェクトの終わりまでちゃんとお金が払われれば、それは「自分たちにとっては」失敗では無い。

こうした心理的な動きの結果、レポジトリを組織ごとに分けて、自分の組織の外のレポジトリの間には壁を置きたがる圧力が働く訳だ。 壁を作れば境界の所でバグは出やすくなるしバグの修正コストも上がる訳だけど、それをなるべく壁の外に押し出す事で自分たちが被害を受けなければそれで良い。 それは不毛なゼロサム・ゲームなのだけれど。

当然壁のどちらか、というのは、プロジェクト全体としてはあまり重要では無い。 バグはバグだし、直すコストはどちらが持つにせよ誰かは請け負う。それはプロジェクトの参加者なのは間違いない。 だからプロジェクトとしてはバグや開発のコストを下げるようにレポジトリの切り方は最適化した方が良いのだけれど、 それはなかなか難しい。

レポジトリの分割が、考え方を強化する

プロジェクトの参加者が、最初からそんなふうにプロジェクトの成功と自分たちの成功を分けている訳では無い。 だが、ひとたび会社ごとにレポジトリを分けてしまうと、どんどんそういう方向に考え方が強化されてしまう。

バグの根本的な原因を考えて対処するよりも自分の壁の外に押し出す事に労力を使ってしまう。 プロジェクトの成功の為に必要なことを考えるよりも、 失敗した時の被害を少なくする事に労力を使ってしまう。 そうした方向に思考を強化してしまうので、レポジトリの分割というのは重要な問題なのだ。

プロジェクトを運営していこうという時に、望ましい方向に思考は強化されるように体勢は作るべきで、 望ましくない方向に強化するような体制を作ってはいけない。システムとして解決すべきだ。

だから組織ごとにレポジトリを分割してしまう、というのは、表面上見えるよりもずっと影響力の大きな問題であり、 また、プロジェクトの運営という観点でとても重要な問題だ。

適切に行えば、プロジェクトの参加者に、プロジェクトの勝利条件と自身の勝利条件を一致させたい、という方向に誘導出来る。 これは会社を集めて何かをやる時には重要なポイントだ。 後述するように下請けの逃げ道を塞いで不利益を被せよう、とならないようにする必要があるが、 うまくやればパレート改善出来る。

でもプロジェクトのそうした決定をする人が、そうした事を理解していない事は良くある。 レポジトリで作業をするのは個々のプログラマな訳だが、 会社を超えたプロジェクト的意思決定にプログラマが関わるかどうかは、場合による。 複数の会社を寄せ集めるケースだと、Tech Leadが居ないというのは良くある光景だ。

そこで、個人的には日本のIT業界におけるTech Leadの地位の確保と向を!とか、そういう大きな話はおいといて、 プログラマじゃない人でもレポジトリの分割ってのが重要な問題で、それは組織論的な事を含んでいるんだよ、 という事を軽い読み物で触れる機会が増えたらいいな、くらいに思っている。

放っておくと、間違えた方向に進む

適切にソースコードを見る権限が無い、というのも、この自分たちの境界を決めようとする動きの延長と言える。 ソースコードを見れないのは、見れないようにする人たちがいるからで、それを望む人がいるからだ。 見えなければ自分たちの責任では無いので、見なくて済むようにする。 だから何もせずに放っておくと、自然と必要なソースが読めなくなって、バグの修正や機能の実装が困難になっていく。 困難にする事で自分たちを守っているからだ。

自然にまかせておくと、間違った分割がなされて、間違った可視性が与えられる。 開発効率の為に適切にソースやレポジトリにアクセス出来るようにする為には、何らかの対策が必要だ。

対策の事はおいといて、ここでは放っておくと間違った方向に進むという事、そのメカニズムの話をしておくに留める。

レポジトリの壁で組織を守らないための雑感

レポジトリを組織で分けない事で、プロジェクトの成功と各参加者の成功を日々近づけるような補助輪の力を発揮してくれる。 逆に考えればプロジェクトの運営者は、レポジトリを組織で分けない為には、プロジェクトの成功と各参加者の成功が一致している事で、 参加者が被害を受けないように考える必要がある。 レポジトリの壁で組織を守ろうという事を防ぐ為には、守る必要が無い、という事を知らせる必要がある。

プロジェクトの失敗を特定組織に帰さない

プロジェクトを運営する人は、基本的にはプロジェクトの成功を目指しているはずだ。 そしてプロジェクトが失敗すれば、プロジェクトを運営している人は失敗の損害を被る。 これは別に下請けのせいだ、と言った所で変わらないはずだ(損害賠償で取り戻すなら変わるけれど、さすがにそれはめったに無い事には同意してくれるはず)。 プロジェクトを運営する人にとっては、失敗が誰のせいかは実はそんなに重要では無い。 失敗するかしないかが大切で、失敗が誰のせいかはそんなに重要じゃない。

そういう前提に立てば、プロジェクトが失敗した時に特定の会社に責任を被せないようにするのは、そう難しい事じゃない。 結局お金は払うんだし、責任を明確にするって結局はディスってスカッとする程度のものでしかない。 だからプロジェクトの失敗は皆の失敗であって、特定の参加会社のせいでは無い、という事にした方が良い。 結局失敗のダメージを一番受けるのは、どう取り繕ってもプロジェクトを運営している人なのだから。 それはレポジトリの壁で各参加組織が自身を守っていても変わらない。 そういった意味では、それはより本質に近い形態と言える。

仕事を特定の組織に偏らせない

レポジトリの壁で仕事を防ぐのは、自分たちが無尽蔵に忙しくなるのを恐れているからだ。 プロジェクトが火を吹いた時に自分が被害を受けたくない。 その為には、プロジェクトが火を吹いた時に大量の仕事を押し付ける、ということが無いというのを納得してもらう必要がある。 プロジェクトが成功しようと失敗しようと、自分はそんな酷い事にはならない、という信頼が要る。

一番良いのは、火が吹かないようにする事だ。次点で、火が吹くような自体は失敗と認めてポシャらせる事だ。

どちらも難しいと考えるかもしれないけれど、自分がこれまで参加した複数企業参加型のプロジェクトで、火を吹いて激務になった事は一度も無い。 一方でレポジトリの壁で組織を守るプロジェクトは何回か遭遇した事がある。どちらを警戒すべきかは自分的には割と明らかと思う。

以前イメージされていた程、火を吹いてそれを下請けに押し付ける、ということは起こらなくなっている。 そもそも押し付けるのは時代的にもう無理だし、以前のような下請けという協力関係とは随分と変化している。 これは昔よりも下請けを見捨てるようになったという事の裏返しでいい事ばかりでも無いけれど、火を吹いた時に押し付ける、という事をしないと認める事は、 実はプロジェクト運営側に実際的な不利益はほぼ無いと言って良いのでは無いか。 時代遅れの体制がそのまま引きづられているだけで実体に即していないのを正すだけだと思うのだよなぁ。

この信頼関係を結ぶのは、ろくでも無いプロジェクト運営をしている場合は難しいかもしれない。 ただその場合でも、仕事の量から身を守るのに、レポジトリの壁以外の壁を使ってもらうようには説得出来る事もあると思う。 レポジトリの壁の問題点は、各会社の利益を優先するように思考を「強化する」ところにある。 各自がある程度の利益を確保するのは問題無くて、それが行き過ぎなければ良い。 だから違う方法で壁を作ってもらえば良いと思う(責任の切り分けの範囲をきっちりするがレポジトリの単位にはしない、というように)。

プロジェクト運営の意思

各組織をレポジトリの壁で守らせない、というのは、プロジェクト運営の意思というのがこもる決断である。

「プロジェクトの参加者は、プロジェクトの成功を目指す」という事に全員が同意する、ということの表明だ。 これは参加者に押し付けるだけではなく、運営側もそうなるようにする、という責任を負うという表明でもある。

「プロジェクトは多分失敗するけれど、自分はお金が払われるからいい」ということを無くす為に、運営は努力する、と言っている。

参加組織も、プロジェクトの成功を目指す、と同意している、と言っている事になる。

レポジトリの構成がプロジェクト運営の意思を表す。 良く分からないから、と勝手に任せるのは、プロジェクト運営に意思が無い、と言っている事に等しい。

モノレポの威力

モノレポというのは、不適切に分割されない為の武器として使える。 ある分割が適切か不適切かは判断が難しい。特に非プログラマのプロジェクト運営者の場合は難しいだろう。 でもモノレポかどうかは誰でも判断出来る。プログラマじゃなくても判断出来る。 そしてMSやGoogleやFacebookといったバカでかい前例がすでにあるので、 そんじょそこらの小規模プロジェクトで大きすぎるという事態はありえ無い、とは断言出来る。 これは非プログラマのプロジェクト運営者が誤った方向に進まない為の妥協案としては、なかなかアリなんじゃないか。 誰でも分かる。簡単。

morritaさんが先のリンクで矯正ギブスと言っていたが、そういう面でもモノレポは良いと思う。 モノレポで発生する問題というのを対処していく事は、ソフトウェア開発における外部の企業との協力関係というのをどうすべきか、 という事を修正していってくれる圧力になる。 そうして一通りの問題が解決した後に適切なバイナリ境界でレポジトリを分けるのは良いかもしれないが、 それは先の話という事で。

なんてろくでも無いブログ記事だ

とここまで書いていて、なんてろくでもない事を書いているんだ、自分は…とか思った。 ろくでも無い組織を知っている自慢とか本当にろくでも無いよなぁ。

複数の企業が集まるケースでも、ちゃんとレポジトリを構成出来ているプロジェクトなんていくらでもある。 ろくでも無いプロジェクトに参加するのは己の未熟さに過ぎないよなぁ。 実際にプロジェクト運営者がプログラマだったりプログラマ上がりだったりというのは良くある話だし、 運営する人の中にTech Lead的な立場の人が混ざっているのも普通の事だ。

ただ、Tech Lead的なものの重要さとかはそれはそれで重要だけれど、 非Techな人に、こうした組織的に重要な事でありながらプログラマの中でとどまりがちな事を伝える記事は、 それはそれで意味はある気がする。 こういうのは自分では無くて、非Techな人がプロジェクト運営を行う組織のプログラマとかが書いた方がいいとは思うが。