かずきのBlog

C#やJavaやRubyとメモ書き

目次

Blog 利用状況

ニュース

わんくまBlogが不安定になったため、前に書いてたはてなダイアリーにメインを移動します。
かずきのBlog@Hatena
技術的なネタは、こちらにも、はてなへのリンクという形で掲載しますが、雑多ネタははてなダイアリーだけに掲載することが多いと思います。
コメント
プログラマ的自己紹介
お気に入りのツール/IDE
プロフィール
経歴
広告
アクセサリ

書庫

日記カテゴリ

[Java]Spring Framework 2.5入門 「DIコンテナのメリット」

前回:[Java]Spring Framework 2.5入門 「依存性の注入」

前回までで、Spring Framework2.5のDIコンテナとしての基本的な機能は使えるようになってきました。
といっても、beanタグとpropertyタグとconstructor-argタグを使うだけですが。今回は、DIコンテナのメリットを書いてみようと思います。

一般的にDIコンテナを使ったプログラムでは、インターフェースを定義して、それを実装したクラスをDIコンテナに登録して使います。これまでのエントリでは、インターフェースは使わずに具象クラスのみ使っていました。

ということで、前回やったMyServiceとMyLogicをインターフェースを使うように変えてみます。
下記の4つを定義します。

  1. springbean.beans.MyLogicインターフェース
  2. springbean.beans.MyLogicImplクラス
  3. springbean.beans.MyServiceインターフェース
  4. springbean.beans.MyServiceImplクラス

実装は特に悩むことはなく、単純にインターフェースと実装クラスのペアをつくっていくだけです。

MyLogicインターフェース

package springbean.beans;

public interface MyLogic {
    int add(int lhs, int rhs);
}

MyLogicImplクラス

package springbean.beans;

public class MyLogicImpl implements MyLogic {
    public int add(int lhs, int rhs) {
        return lhs + rhs;
    }
}

MyServiceインターフェース

package springbean.beans;

public interface MyService {
    int execute();
}

MyServiceImplクラス

package springbean.beans;

public class MyServiceImpl implements MyService {
    // インターフェースを受け取るようにする
    private MyLogic logic;

    private int lhs;
    private int rhs;

    public int execute() {
        return logic.add(lhs, rhs);
    }

    public void setLhs(int lhs) {
        this.lhs = lhs;
    }

    public void setLogic(MyLogic logic) {
        this.logic = logic;
    }

    public void setRhs(int rhs) {
        this.rhs = rhs;
    }


}

ここで大事なのが、MyServiceImplクラスが依存するものがMyLogicインターフェースになるという部分です。MyLogicインターフェースを実装するクラスなら何でもMyServiceImplに設定することが出来るようになります。

当然application.xmlも変更が入ります。MyLogicImplとMyServiceImplを定義するように変更します。

application.xml(beansタグの内側だけ抜粋)

<bean id="myLogic" class="springbean.beans.MyLogicImpl" />

<bean id="myService" class="springbean.beans.MyServiceImpl">
    <property name="logic" ref="myLogic" />
    <property name="lhs" value="100" />
    <property name="rhs" value="200" />
</bean>

Mainは特に変更はありませんが一応mainメソッド内部だけのせておきます。

ApplicationContext ctx = new ClassPathXmlApplicationContext("application.xml");

// インターフェースに対してプログラムを書く
MyService service = (MyService) ctx.getBean("myService");
System.out.println("service#execute = " + service.execute()); // 300と表示される

これで、一般的なDIコンテナを使ったプログラムっぽい形になりました。正直、こんなめんどくさいことを何故するんだろう?と最初思いましたが、こうすることで”ユニットテストが非常にやりやすい”形になっています。

MyServiceImplクラス内には、外部のクラスに直接依存する部分は排除される形になっています。MyServiceImplクラスを動かすための要件は、MyLogicインターフェースを実装したクラスがあるということだけになります。

つまり、テストをしたければ、MyLogicインターフェースを実装したMyLogicMockみたいなクラスを作って、それを使ってテストが出来るようになります。

ということでやってみましょう。Spring Frameworkには単体テストを支援する色々な機能が組み込まれていますが、ここでは、その機能は使わずに書いてみます。

MyServiceImplが単体として満たさなければいけない要件は、以下の2つになると思います。

  1. logicのaddメソッドにlhsフィールド, rhsフィールドの値をちゃんと渡す。
  2. logicのaddメソッドの結果をちゃんと返す。

ということで、早速MyLogicインターフェースを実装したMockクラスを定義します。

package springbean.beans;

import static org.junit.Assert.*;

public class MyLogicMock implements MyLogic {
    public int add(int lhs, int rhs) {
        // 要件1をちゃんと満たしているか確認
        assertEquals(100, lhs);
        assertEquals(200, rhs);

        return 1000; // 固定値を返す
    }
}

このMockクラスは、引数が100と200がわたってきているか確認した後に、固定値で1000を返します。このMockクラスを使うように定義したspringbean.beans.MyServiceTest-context.xmlファイルを作成します。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">
    <!-- ロジックはMockを使う -->
    <bean id="logic" class="springbean.beans.MyLogicMock" />
    <bean id="service" class="springbean.beans.MyServiceImpl">
        <property name="logic" ref="logic" />
        <property name="lhs" value="100" />
        <property name="rhs" value="200" />
    </bean>
</beans>

テストクラスのセットアップで、この定義ファイルを読み込んでApplicationContextを作ってserviceを取得します。
そして、取得したserviceに対してテストを実施します。

package springbean.beans;

import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import static org.junit.Assert.*;

public class MyServiceTest {

    private MyService service;

    @Before
    public void setUp() {
        // テスト用の定義ファイル読み込み
        ApplicationContext ctx = new ClassPathXmlApplicationContext(
                "springbean/beans/MyServiceTest-context.xml");
        service = (MyService) ctx.getBean("service");
    }

    @After
    public void tearDown() {
        service = null;
    }

    @Test
    public void execute() throws Exception {
        // 要件2を満たしているか確認
        assertEquals(1000, service.execute());
    }
}

といった感じにクラス間が疎結合になり、単体テストがとてもやりやすくなるのがDIコンテナのメリットの1つでもあります。

今回の例では、単純すぎてあんまりメリットは感じないですが、たとえばMyLogicがDBにアクセスするような処理だったら、Mockに簡単に差し替えることでDBに依存しないでMyServiceのテストが出来るということは大きなメリットになると思います。

ということで今回はおしまい。

投稿日時 : 2009年2月15日 11:12

Feedback

# sac longchamp 2012 2012/12/15 15:26 http://www.saclongchampachete.com/category/longcha

We are impressed by products you can information for this website. There are a whole lot of good methods here.

# bags burberry uk 2012/12/15 22:51 http://www.burberryuksale.info/category/burberry-u

The stars of your pool will be the comments and therefore the pictures tend to be secondary.

# longchamp achete 2012/12/16 17:52 http://www.saclongchampachete.com/category/sacs-lo

I benefit from earbuds overseas because of their portability, even though I favor over the actual ear.

# burberry coats sale 2012/12/17 2:44 http://www.burberrycanadaoutlet.info/category/burb

Think it as being a journal or even a magazine about general interest proper to study. Funny, witty, controversial, entertaining, useful, acerbic, thoughtful, serious, curious, unexpected comebacks are actually welcome.

# burberry uk sale 2012/12/18 14:29 http://www.burberryuksale.org/category/burberry-sa

You truly know ones own stuff...

# women bags burberry 2012/12/18 20:18 http://www.burberryoutlet2012.info/category/burber

I am sure I will probably visit the following place ever again soon.

# destockchine 2013/01/10 22:30 http://www.destockchinefr.fr/maillot-de-club-pas-c

Specifically where you will find marriage with no love, you'll see love with no marriage.
destockchine http://www.destockchinefr.fr/maillot-de-club-pas-cher/serie-a-pas-cher/

# where to buy baricitinib https://baricitinibrx.com
baricitinib eua fact sheet
2021/12/12 16:22 Buksdldj

where to buy baricitinib https://baricitinibrx.com
baricitinib eua fact sheet

# no prescription clomid https://clomidt.com
clomid pills 2022/01/03 19:13 Clomid

no prescription clomid https://clomidt.com
clomid pills

# vibramycin 100 mg https://doxycyline1st.com/
where can i get doxycycline 2022/02/26 8:21 Jusidkid

vibramycin 100 mg https://doxycyline1st.com/
where can i get doxycycline

# where to purchase doxycycline https://doxycyline1st.com/
doxycycline hyclate 100 mg cap 2022/02/26 17:48 Jusidkid

where to purchase doxycycline https://doxycyline1st.com/
doxycycline hyclate 100 mg cap

# buy prednisone mexico http://prednisonefast.site/ 2022/04/17 6:47 Prednisone

buy prednisone mexico http://prednisonefast.site/

# lasix uses https://buylasix.icu/
lasix 20 mg 2022/06/25 1:05 LasixRx

lasix uses https://buylasix.icu/
lasix 20 mg

# clomiphene generic https://clomidonline.icu/ 2022/07/12 23:51 Clomidj

clomiphene generic https://clomidonline.icu/

# ivermectin for cattle tractor supply https://stromectolbestprice.com/ 2022/07/30 8:19 BestPrice

ivermectin for cattle tractor supply https://stromectolbestprice.com/

# can i buy prednisone from canada without a script https://deltasone.icu/
prednisone 100 mg 2022/08/22 17:34 Prednisone

can i buy prednisone from canada without a script https://deltasone.icu/
prednisone 100 mg

# medication for ed https://ed-pills.xyz/
ed drug prices 2022/09/16 14:49 EdPills

medication for ed https://ed-pills.xyz/
ed drug prices

# best erection pills https://ed-pills.xyz/
best ed pills at gnc 2022/09/17 14:59 EdPills

best erection pills https://ed-pills.xyz/
best ed pills at gnc

# antibiotic without presription https://antibiotic.best/ 2022/10/08 8:52 Antibiotic

antibiotic without presription https://antibiotic.best/

# doxycycline hyclate https://buydoxycycline.icu/ 2022/10/08 17:13 Doxycycline

doxycycline hyclate https://buydoxycycline.icu/

# Everything information about medication. Read information now.
https://edonlinefast.com
Best and news about drug. Generic Name. 2023/02/18 16:57 EdOnline

Everything information about medication. Read information now.
https://edonlinefast.com
Best and news about drug. Generic Name.

# can i buy prednisone online in uk - https://prednisonesale.pro/# 2023/04/22 10:31 Prednisone

can i buy prednisone online in uk - https://prednisonesale.pro/#

# buy cytotec over the counter - https://cytotecsale.pro/# 2023/04/29 6:30 Cytotec

buy cytotec over the counter - https://cytotecsale.pro/#

# over the counter bv treatment https://overthecounter.pro/# 2023/05/09 0:34 OtcJikoliuj

over the counter bv treatment https://overthecounter.pro/#

# online ed pills: https://edpills.pro/# 2023/05/15 22:15 EdPillsPro

online ed pills: https://edpills.pro/#

# canadian drug https://pillswithoutprescription.pro/# 2023/05/16 11:32 PillsPro

canadian drug https://pillswithoutprescription.pro/#

# buying ed pills online https://edpill.pro/# - over the counter erectile dysfunction pills 2023/06/27 16:03 EdPills

buying ed pills online https://edpill.pro/# - over the counter erectile dysfunction pills

# paxlovid generic https://paxlovid.pro/# - buy paxlovid online 2023/07/02 23:12 Paxlovid

paxlovid generic https://paxlovid.pro/# - buy paxlovid online

# purchase cytotec https://cytotec.ink/# - buy cytotec pills 2023/07/26 20:29 PillsFree

purchase cytotec https://cytotec.ink/# - buy cytotec pills

# male ed pills https://edpills.ink/# - online ed medications 2023/07/27 2:26 EdPills

male ed pills https://edpills.ink/# - online ed medications

# ed pills gnc https://edpillsotc.store/# - best over the counter ed pills 2023/10/08 2:50 EdPills

ed pills gnc https://edpillsotc.store/# - best over the counter ed pills

# ï»¿plavix generic https://plavix.guru/ antiplatelet drug 2023/10/24 1:58 Plavixxx

plavix generic https://plavix.guru/ antiplatelet drug

タイトル
名前
Url
コメント