Masayan tech blog.

  1. ブログ記事一覧>
  2. Typescript用の軽量DIコンテナ「TSyringe」

Typescript用の軽量DIコンテナ「TSyringe」

公開日

環境

  • macOS Monterey 12.6
  • Windows 11
  • VSCode
  • node.js v18.6.0
  • npm 8.13.2
  • Typescript 4.6.4

TSyringeは、microsoft製の依存性注入(Dependency Injection(DI))ができるライブラリです

依存関係のインストール

tsyringe本体と、reflectを扱うためのpolyfillパッケージreflect-metadataをインストール

npm install --save tsyringe reflect-metadata

コンパイラオプションの変更

以下の2か所(デコレーター)を有効にする

tsconfig.json

{
  "compilerOptions": {
    "experimentalDecorators": true,
    "emitDecoratorMetadata": true
  }
}

いざDI

  • reflect-metadataパッケージをトップレベルのスクリプトでimport
  • 本記事では、DIコンテナ用クラスを用意しているが、必須ではない
  • resolveメソッドの引数に指定されたクラス名から、依存関係を解決しインスタンスを返す

src\core\ServiceContainer.ts

import 'reflect-metadata';
import { container, InjectionToken } from 'tsyringe';

export class ServiceContainer<T> {
  public resolve(token: InjectionToken<T>): T {
    return container.resolve(token);
  }
}

index.ts

  • サービスコンテナクラスを介して、useCaseをのインスタンスを生成する
  • これで、サービスコンテナクラスをnewするだけで他のインスタンスについては呼び出し側でnewしなくてもよくなる
import { ServiceContainer } from '@/core/ServiceContainer';
import Member from '@/domain/member/Member';
import MemberMonthlyFeeCalcUseCase from '@/usecase/member/MemberMonthlyFeeCalcUseCase';

const useCase = new ServiceContainer<MemberMonthlyFeeCalcUseCase>().resolve(MemberMonthlyFeeCalcUseCase);

const fee = useCase.calc(new Member('aa', 25, 'individual'), 'annual');
console.log(fee); // 14160

まとめ

いかがでしたでしょうか。本記事ではTypescript用の軽量DIコンテナ「TSyringe」の導入手順や、実際の使い方について紹介しました。インスタンスの生成を簡潔で柔軟なコードが記述できるというメリットがあり、簡単に導入できますのでぜひ参考にしてみてください。