DIコンテナーの基礎
制御の反転、サービスの登録、.NET DIコンテナーによる依存関係の解決方法を理解します。
「DIコンテナーの基礎」はCoddyKit上の無料C# Academyレッスンです。 これはレッスン1/4です。 下記で完全なレッスンを無料で読むことができます。その後、ブラウザ内の組み込みコードエディタと24時間対応のAIチューターでハンズオン演習できます。 これはC# Academy学習パスの一部であり、ウェブとCoddyKitアプリ全体で進捗が同期されます。 C# Academyコースには全4レッスンが含まれています。
依存性の注入とは
Dependency Injection (DI) は、クラスが依存関係を自ら作成するのではなく、外部のソースから受け取るデザインパターンです。
クラス内にvar repo = new UserRepository();と記述する代わりに、クラスは必要なものを宣言し、DI コンテナーがそれを提供します。
制御の反転
DI は制御の反転 (Inversion of Control、IoC)原則を具体的に実装したものです。依存関係を作成する制御が、依存するクラスから外部のコンテナーへと反転します。
これにより、クラスのテストや置き換えが容易になります。
.NET DI コンテナーの設定
.NET アプリでは、DI コンテナーをProgram.cs内のIServiceCollectionを使って構成します。サービスを登録すると、実行時に解決されます。
var builder = WebApplication.CreateBuilder(args);
// Register services
builder.Services.AddScoped<IUserRepository, UserRepository>();
builder.Services.AddScoped<UserService>();
var app = builder.Build();
app.Run();インターフェイスと実装の定義
DIは、インターフェイスを前提にプログラミングすると最も効果を発揮します。サービス契約用のインターフェイスと、それを実装する具象クラスを定義します。
public interface IUserRepository
{
User? GetById(int id);
}
public class UserRepository : IUserRepository
{
public User? GetById(int id)
{
// fetch from database
return new User { Id = id, Name = "Alice" };
}
}コンストラクターによるサービスの解決
コンテナーは、登録済みサービスをコンストラクターに自動的に注入します。クラスは必要なインターフェイスを宣言するだけでよく、newキーワードは必要ありません。
public class UserService
{
private readonly IUserRepository _repo;
public UserService(IUserRepository repo)
{
_repo = repo;
}
public User? FindUser(int id) => _repo.GetById(id);
}複数のサービスの登録
必要な数だけサービスを登録できます。一般的な拡張メソッドにはAddTransient、AddScoped、AddSingletonがあり、それぞれ異なるライフタイムを定義します。
builder.Services.AddSingleton<IConfig, AppConfig>();
builder.Services.AddScoped<IUserRepository, UserRepository>();
builder.Services.AddTransient<IEmailService, SmtpEmailService>();
builder.Services.AddScoped<UserService>();IServiceProviderの直接使用
まれに、命令的にサービスを解決する必要があります。IServiceProviderを使用するとGetRequiredService<T>()を呼び出してサービスを解決できますが、ほとんどの場面ではコンストラクターインジェクションを優先してください。
// Anti-pattern (service locator) — use sparingly
public class ManualResolver
{
private readonly IServiceProvider _sp;
public ManualResolver(IServiceProvider sp) => _sp = sp;
public void DoWork()
{
var svc = _sp.GetRequiredService<UserService>();
svc.FindUser(1);
}
}オープンジェネリックの登録
.NET DIはオープンジェネリックの登録をサポートしています。IRepository<>を一度登録すると、任意のエンティティ型に対してRepository<T>に解決できます。
builder.Services.AddScoped(typeof(IRepository<>), typeof(Repository<>));
// Resolves as:
// IRepository<User> -> Repository<User>
// IRepository<Order> -> Repository<Order>起動時の検証
ValidateOnStart()またはValidateScopes = trueを使用すると、コンテナーは、Singleton内にScopedサービスを保持するような登録ミスを、実行時ではなくアプリケーションの起動時に検出できます。
builder.Services.AddScoped<IMyService, MyService>();
// Detect scope violations at startup
builder.Host.UseDefaultServiceProvider(options =>
{
options.ValidateScopes = true;
options.ValidateOnBuild = true;
});サービスのデコレーション
元のクラスを変更せずに、デコレーターでサービスをラップできます。まず内部のサービスを登録し、その後にそれをラップするデコレーターを登録します。
builder.Services.AddScoped<IUserRepository, UserRepository>();
// Decorator pattern
builder.Services.Decorate<IUserRepository, CachedUserRepository>();
// Requires Scrutor NuGet package実践例: DIを使用したMinimal API
Minimal APIでは、サービスがルートハンドラーのパラメーターに直接注入されます。コンテナーがサービスを自動的に解決します。
app.MapGet("/users/{id}", (int id, UserService svc) =>
{
var user = svc.FindUser(id);
return user is null ? Results.NotFound() : Results.Ok(user);
});クイックチェック
ほとんどのクラスで依存関係を取得する際に、どの方法を優先すべきですか。
まとめ: DIコンテナーの基礎
重要なポイント:
- DIでは依存関係の生成を逆転させます。クラス自身ではなく、コンテナーがオブジェクトを構築します
- AddTransient / AddScoped / AddSingletonでサービスを登録します
- コンストラクターインジェクションが標準的かつ推奨される方法です
- オープンジェネリック、デコレーター、ValidateOnBuildは強力な高度機能です
AI チューターと学ぶ C# — 無料
ブラウザでリアルコードを書いて実行し、24/7 の AI チューターから瞬時にサポートを受け、ウェブまたはアプリで続きから学習できます。
- コース
- 93
- レッスン
- 346
よくある質問
「DIコンテナーの基礎」レッスンは無料ですか?
はい。「DIコンテナーの基礎」の完全なテキストはこのウェブで無料で読めます。インタラクティブに演習し(組み込みコードエディタと24時間対応のAIチューター)、C# Academyコースの残りをアンロックするには、CoddyKit PROにアップグレードしてください。 C# Academyコースには全4レッスンが含まれています。
「DIコンテナーの基礎」で何を学びますか?
制御の反転、サービスの登録、.NET DIコンテナーによる依存関係の解決方法を理解します。 ブラウザで直接実行するハンズオンコードでC# Academyを演習し、24時間対応のAIチューターがレッスンを進める中での質問に答えます。
C# Academyを始めるのに経験は必要ですか?
事前経験は必要ありません。CoddyKitのC# Academyは初級者から上級者向けに構成されているため、ここから始めるか最初から始めて、自分のペースで進むことができます。 これはレッスン1/4です。
「DIコンテナーの基礎」レッスンにはどのくらい時間がかかりますか?
ほとんどのCoddyKitレッスンは約5~10分かかります。各レッスンはコンパクトでインタラクティブなので、着実に進歩し、ウェブとアプリ全体で正確に前回の場所から再開できます。
このC# Academyレッスンでコードを書いて実行できますか?
はい。すべてのC# Academyレッスンに組み込みコードエディタが含まれているため、ブラウザでリアルコードを書いて実行し、即座のAIフィードバックを取得できます。ローカル設定は不要です。