nikkie-ftnextの日記

イベントレポートや読書メモを発信

読書ログ | Clean Architecture 第14章 コンポーネントの結合についての3原則

はじめに

手をつなごう🎶 nikkieです。
アイうたがみんなに見られていて嬉しい限り♪

ちょうぜつ本(『ちょうぜつソフトウェア設計入門』)でパッケージ原則を知ったのを機に『Clean Architecture』に手を伸ばしてみています。
今回は結合に関する3原則篇の読書ログです。

目次

前回の『Clean Architecture』

ちょうぜつ本でパッケージ原則6つを知ったnikkie氏。

6つの原則は凝集性に関する3つと、結合に関する3つに分類されます。
凝集性に関する3原則について『Clean Architecture』13章を読みました。

今回は結合に関する3原則について14章を読んでいきます。

第14章 コンポーネントの結合

https://www.tumblr.com/asciidwango/176293765750/clean-architecture

コンポーネントの定義は12章より「デプロイの単位」です。
14章はデプロイの単位同士の関連についての章!

  • 非循環依存関係の原則
  • 安定依存の原則
  • 安定度・抽象度等価の原則

読み口はちょうぜつ本とは大違いでした。
かわいいイラストの代わりに、数式を使った解説が展開されました(※難しい式ではないです)

「二日酔い症候群」へのソリューションとしての非循環依存関係の原則

思春期症候群1ならぬ二日酔い症候群、これは大きいチームでの開発で安定版をビルドできない状態が何週間も続く症状とのこと。
二日酔い症候群へのソリューションが非循環依存関係の原則と解説されます。

二日酔い症候群自体は、開発環境をリリース可能なコンポーネントに分割して対処します。
コンポーネントの依存関係のグラフを書き、何にも依存していない(ただし依存はされている)コンポーネントから、依存関係の逆順にリリースしていきます。
依存関係のグラフからリリース順がわかり、また、変更の影響範囲も分かる!

しかし循環依存してしまうと、リリースが難しくなります。
循環依存したコンポーネントどうしは密結合し、「事実上一つの巨大コンポーネント」となります。

なので、「非循環依存関係の原則」(循環依存があってはならない)なのですが、持ち込まれた循環依存を取り除くにはどうするのでしょうか?
2つの方法が解説されます。

  1. 依存関係逆転の原則の適用
  2. 循環依存する2つのコンポーネントが依存する新コンポーネントを作成

ここでの話から「コンポーネントの構造をトップダウンで設計するのは不可能」(Kindle の位置No.1917-1918)という論が展開されます(「トップダウンの設計」の節)。
コンポーネント図は(リリース順を見たように)地図であり、依存関係は変わらないものではなく、システムの設計に合わせて育つもの。
13章のコンポーネントの凝集性についての設計でもありましたが、コンポーネントはずっと同じというわけではなく、育つ(時間変化する)点が繰り返し説かれていますね。

依存性管理の指標

(むずかしくない)数式タイムです!

安定度

「安定依存の原則」より

以下の説明はちょうぜつ本では見なかったので、目からウロコでした。

ソフトウェアを変更しづらくするには、多数のソフトウェアコンポーネントから依存されるようにすればいい。(Kindle の位置No.1962-1963)

✍️多くから依存させれば、変更が大変=変更しづらくなり、安定する
これが責務を負うということ

安定度の指標として不安定さが定式化されます。

指標 I(不安定さ)= ファン・アウト / (ファン・イン + ファン・アウト)

例としては

安定依存の原則(SDP)は、コンポーネントのIを依存するコンポーネントのIよりも大きくすべきというものである。(Kindle の位置No.2012-2013)

実現するために、依存関係逆転の原則の例(図14-10, 14-11)

安定度の高いコンポーネントもあれば、安定度の低いコンポーネントもあるようにしておきたい。(Kindle の位置No.2017-2018)

いろいろな安定度があっていいのですね。
✍️多様な安定度のコンポーネントからシステムは作られる

Python使い的に気になった箇所、手を動かしてみたい

(※RubyPythonでは(引用者注))依存関係を逆転させるときに、何らかの宣言をしたりインターフェイスを継承したりする必要がない (Kindle の位置No.2057-2058)

抽象度

「安定度・抽象度等価の原則」より

モチベーション:システムの上位レベルの方針を、安定度の高い(I=0)コンポーネントに配置したい

コンポーネントの安定度を高くしようと思えば、拡張できるようにインターフェイスと抽象クラスで構成すべき (Kindle の位置No.2077-2078)

安定依存の原則と安定度・抽象度等価の原則の組合せが、コンポーネント版の依存関係逆転の原則!
抽象度が高くなる方向へ依存する

抽象度の指標 Aの定式化は、コンポーネント内のクラスのうち、抽象クラスとインターフェイスの数の割合です。

安定度と抽象度の関連

コンポーネントを安定度と抽象度の2軸でプロットします。

この2点を結ぶ直線上が主系列。
書籍ではIA平面上の距離を定義し、主系列への適合度も論じます。
ただ一息で読むにはこのあたりで限界(そろそろかわいいを摂取せねば🤯)となったので、今回はこれくらいにしておいてやりました(えっへん

終わりに

ちょうぜつ本 2章をきっかけに手を伸ばした『Clean Architecture』14章の読書ログでした。
コンポーネントの結合に関する3原則を扱っていて

  • コンポーネントのリリース順
    • 依存関係からわかる
    • 循環依存はNG(非循環依存関係の原則)
    • 依存関係も育つ
  • 安定度と抽象度
    • それぞれ定式化できる(I, A, D)
    • 定式化により、安定依存の原則、安定度・抽象度等価の原則を確認できる

定式化は完全に予想外でした。
説明としてはきれいだと思います(他に適する手段がないがゆえの定式化かなと思います)

Uncle Bobが展開する深い議論への扉を開いてくれたちょうぜつ本、ありがとう!

P.S. 7/7(金) 第2章「パッケージ原則」のちょうぜつ本_読書py!

次回ちょうぜつ本_読書py(Python使い視点でちょうぜつ本を読む、みんなのアウトプット中心の読書会)は本日7/7(金)です!
このエントリも予習(寄り道)エントリなのでした。

パッケージ原則に興味ある方、大歓迎です!
ぜひぜひお気軽にお越しください〜


  1. 花楓ちゃん(おでかけシスター)観に行かないとな(消えちゃったかえでちゃん派の私は耐えられるかな...)