2016-10-07 35 views
0

[10/7/06 4:00編集されたサンプルコード] データベースに触れることなく(TestNGでJMockItを使用して)いくつかのコードをテストしようとしていますが、と呼ばれる。ここでは単純化の設定です:JMockIt Mockedメソッドがモックされていない

class DBRow { 
    public DBRow() { } 
    public DBRow(Object obj) { 
     initialize(obj); 
    } 
    public void insert() { 
     actuallyAddRowToDatabase(); 
    } 
} 

class MyObject extends DBRow { 
    MyObject(Object obj) { 
     super(obj); 
    } 
    public void insert(Object obj) { 
     doSomething(obj); 
     insert(); 
    } 
} 

class Factory { 
    static MyObject createObject(Object obj1, Object obj2) { 
     MyObject newObj = new MyObject(obj1); 
     newObj.insert(obj2); 
     return newObj; 
    } 
} 

は、私は、実際のデータベースに挿入を防止するために挿入操作を模擬したかったので、私はこのような何か試してみました:

@Test 
public void testCreation() { 
    new Expectations(MyObject.class) { 
     MyObject mock = new MyObject(null) { 
      @Mock 
      public void insert(Object obj) { } 
     }; 
    { 
     new MyObject(anyString); result = mock; 
    }}; 

    MyObject test = Factory.createObject("something", "something else"); 
} 

をしかし、本当のinsert(Object)があることが表示されますまだ呼び出されています。私はクラスが嘲笑されているので、すべてのインスタンスが嘲笑されるように指定していますよね?そして、私は挿入メソッドを嘲笑すべきだと指定しています。だから、なぜ実際のメソッドが呼び出されるのでしょうか?

上記にも2番目の問題があります。上記のようにExpectationsブロック内にモッククラスを定義すると、Row(Object)の代わりにRow()コンストラクターだけが呼び出され、そのオブジェクトが正しく初期化されていないようです。私はこれを@BeforeTestメソッドに移動し、そのクラスをインスタンス化することでこれを修正しました。ここではそれは次のようになります。

private MyObject mock; 

@BeforeTest 
public void beforeTest() { 
    new MockUp<MyObject>() { 
     @Mock 
     public void insert(Object obj) { } 
    }; 
    mock = new MyObject("something"); 
} 

@Test 
public void testCreation() { 
    new Expectations(MyObject.class) {{ 
     new MyObject(anyString); result = mock; 
    }}; 

    MyObject test = Factory.createObject("something", "something else"); 
} 

だから、これは呼び出されるべき正しいコンストラクタを取得しているようだが、まだinsert()が同様に呼び出されているようです。どんな洞察?あなたはすなわちfucntion private MyObject mock;が、実際のオブジェクトtest呼び出すために嘲笑オブジェクトを使用していない

答えて

0

私は最終的に正しいコンストラクタが呼び出され、実際のデータベース操作が行われないようにテストを書くことができました。私が問題にしていた問題の一部は、Expectationsブロックのメソッドの1つが、私が関心のないパラメータで期待していたものとは異なるオブジェクトを取得していたことでした。そして、私の問題の他の部分は、 MockUpクラスとExpectationsレコーディングの役割。

テスト中のコードは変更されませんでした。ここに私の単純化した例では、便宜上、再びです:

class DBRow { 
    public DBRow() { } 
    public DBRow(Object obj) { 
     initialize(obj); 
    } 
    public void insert() { 
     actuallyAddRowToDatabase(); 
    } 
} 

class MyObject extends DBRow { 
    MyObject(Object obj) { 
     super(obj); 
    } 
    public void insert(Object obj) { 
     doSomething(obj); 
     insert(); 
    } 
} 

class Factory { 
    static MyObject createObject(Object obj1, Object obj2) { 
     MyObject newObj = new MyObject(obj1); 
     newObj.insert(obj2); 
     return newObj; 
    } 
} 

は、ここで私が最終的にテストコードのためになってしまったものを、本質的です:

Object something; 
Object somethingElse; 

@BeforeTest 
public void beforeTest() { 
    new MockUp<MyObject>() { 
     @Mock 
     public void insert() { } // override the "actual" DB insert 
    };       // of Row.insert() 
} 

@Test 
public void testCreation() { 
    MyObject mock = new MyObject(something); // object correctly init'd 
               // by Row.initialize(Object) 
    new Expectations(MyObject.class) {{ 
     new MyObject(something);  result = mock; 
     mock.insert(somethingElse); 
    }}; 

    MyObject test = Factory.createObject(something, somethingElse); 
} 

のキーポイントは、A)私はDBを上書きするモックアップクラスを作成したことでしたB)期待通りを記録するために、その部分的に模倣されたインスタンスのローカルインスタンスを作成しました。

0

MyObject test = new MyObject("something", "something else"); 

コールmock代わりのtesttestStuff()

すべてのインスタンスが自動的に嘲笑されるわけではありません。模擬インスタンスで作業する必要があります。

+0

testStuff()は問題ありません。実際、私はそれを私の例から削除します。問題は建設中のinsert()です。うまくいけば私の例を編集するつもりです。しかし、 "すべてのインスタンスは自動的に嘲笑されません"と書かれていますが、 "Classオブジェクトが[Expectationsコンストラクタで指定されている場合] ...指定されたクラスのすべてのインスタンスは、 "あなたの声明を明確にすることはできますか? – Didjit

+0

引用した文書を参照してください。「期待」は、模擬的なインスタンスに対する呼び出しの記録段階であることを理解する。それは嘲笑されたオブジェクト作成段階ではありません。 '新しいMockUp'または' Mock'と 'jectn'によって作成されたモックされたオブジェクト –

+0

また、あなたのコードを読むのが非常に混乱します。あなたは 'MyObject'定義に' MyObject(Object obj) 'というコンストラクタしかありませんが、テストコードでは' new MyObject( "something"、 "something else"); '私は何を探しているのか分かりませんで。実際のメソッドが呼び出されている場合は、メソッドを偽のメソッドではなく実際のオブジェクトで呼び出す場合です。 –

関連する問題