LoginSignup
31
36

More than 3 years have passed since last update.

DI コンテナは自分で new しないでフレームワークを探そう

Last updated at Posted at 2020-07-10

思ったより↓の記事がバズった。
DI (依存性注入) って何のためにするのかわからない人向けに頑張って説明してみる

自分で DI コンテナを new しないで

自分で DI コンテナのインスタンスを new して管理して、自分でコンテナからインスタンスを取得するようなコードは出来れば書かない方がいいです。
世の中に対応しているフレームワークがきっとあるので、それを使いましょう。車輪の再発明は勉強にはなるけど実際の製品コードでは書かない方がいいので気を付けましょう。

因みに勉強のために DI コンテナを土台にしたオレオレフレームワークを組んでみるのは楽しいです。

C# の場合

C# だと ASP.NET Core を使っていれば、フレームワーク自体がどっぷりと DI コンテナを前提とした作りになっています。

ASP.NET Core での依存関係の挿入

C# で Web アプリ (Web API, gRPC, SPA(Blazor)) を作るときは、ASP.NET Core の流儀に従いましょう。
流儀に従っていれば DI コンテナを使うように自然になりますし、その方が便利です。

ASP.NET Core は Startup.cs クラスの ConfigureServices メソッドの引数に渡されてくる IServiceCollection に色々なクラスを登録していきます。
ここで登録したクラスは Web API や Web ページを表すクラスに DI したりもできるし、コンテナ内にはフレームワークが提供する便利機能を持ったクラスも登録されているので、それを使う場合もコンストラクターの引数で受け取って使うことが出来て便利です。

WPF/UWP/Xamarin.Forms は Prism というフレームワークを使うと DI コンテナまわりの機能もついてくるのでそれを使うのがいいと思います。

Java 系の場合

Java 系言語の場合は Spring Boot がいいんですかね?最近 Java 系言語を追いかけてないのですが…。
15 年前に Spring Framework や Seasar2 あたりで DI コンテナに初めて触れたので、懐かしいです。

前の記事にはてなブックマークいっぱい

はてなブックマークのコメントをいくつかピックアップしてみたいと思います。


ちょっとしか読んでないけど、技術の歴史を踏まえないと正しい理解を持てないという典型に見える。
new Object()→Factoryパターン→DIという発展の中の最初の矢印しか説明してないのでDIを理解してない人に見えてしまう

説明のときにはしょったのは事実。説明時には別にいらないと思ったので。


うしてテスト用途が主という誤った考えが生まれるんだよなぁ。
コンポーネントとコンポーネントの結合を疎にし、短くて簡素で柔軟なプログラムを生むのに使うのが正しいのだけど/それにつけてもDJイベントの楽しさよ

静かな方が好きなので DJ のいるイベントは煩い印象なのでそんなに好きじゃない…。

コンポーネントとコンポーネントの結合を疎にするのは、実装クラスへの直接的な依存ではなくインターフェースを間に挟むことでお互いが実装に依存しないようになることで実現できる類のものに感じます。
短くて簡素なプログラムはメソッド分割やクラス分割。

柔軟なプログラムも上の手段を使って、うまく設計した結果得られるもの。

そういう風に設計されたクラスのインスタンス組み立てるためには DI コンテナ使うと楽出来るし、単体テストもしやすくなるので好き。
個人的には単体テスト可能なコードを書く方が、設計が素晴らしいコードを書くのよりは優先度が高め。優先度が高いだけで設計が素晴らしいコードは大好きです。


いや、違くない?この説明だとFactoryでいいという話になるよね(筆者もテストのMockingが容易ならDIいらないと言ってしまってるのでその認識っぽい)。
重要なのは依存を隠蔽することだよね。どっかで記事書こう

記事楽しみにしてます。
単体テストがしやすいコードを書いていく(もしくは保守性の高い設計を突き詰める)と DI コンテナを使わないと凄くメンドクサイので使ってる認識。
世の中のフレームワークは、割と DI コンテナを前提に作られていて、それは単体テストがしやすい保守性の高いコードを作るための現時点での最適解だという共通の認識があるからだと思ってます。

(別の具象クラスへの)依存を隠匿するためには C#/Java などではインターフェースを挟んだり外部から実装を注入してもらうようにしないといけないから、それを省力化するための DI コンテナがあるように感じてる。

省力化が必要なほど大変じゃないなら DI コンテナいらないと思ってるけど現状は DI コンテナを使うのがベストだと思っています。

追記

コメントの人が記事を書いてくれました!多謝!

DIコンテナのテスト以外での利点について


著者のプロフィールにちょっと引いてしまった。愛が重すぎる。

これ重いかなぁ?プログラミング楽しいよ。C# はいい言語だよ。

image.png

31
36
13

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
31
36