2010-07-02 39 views

Trả lời

11

EasyMock là một khuôn khổ kiểm tra cho "cho các giao diện (và các đối tượng thông qua việc mở rộng lớp)", do đó bạn có thể thử một lớp học mà không có một giao diện. Xem xét việc tạo ra một đối tượng interfaced với một accessor cho lớp tĩnh của bạn và sau đó giả định rằng acessor thay thế.

CHỈNH SỬA: Btw, tôi sẽ không khuyên bạn nên thực hiện các lớp tĩnh. Tốt hơn là bạn nên giao tiếp mọi thứ nếu bạn đang thực hiện TDD.

3

Nói chung, không thể giả lập một phương thức tĩnh mà không sử dụng một kiểu truy cập nào đó, mà dường như đánh bại mục đích sử dụng một phương thức tĩnh. Nó có thể khá bực bội.

Có một công cụ mà tôi biết được gọi là "TypeMock Isolator" sử dụng một số loại ma thuật Satanic để giả lập các phương pháp tĩnh, nhưng công cụ đó khá tốn kém.

Vấn đề là, tôi biết không có cách nào để ghi đè lên một phương pháp tĩnh. Bạn không thể khai báo nó ảo. bạn không thể đưa nó vào một giao diện.

Xin lỗi là một nelly tiêu cực.

9

Chỉ trong trường hợp PowerMock không có sẵn cho bất cứ lý do:

Bạn có thể di chuyển các cuộc gọi tĩnh đến một phương pháp, ghi đè phương pháp này trong instantiation của lớp thử nghiệm trong lớp kiểm tra, tạo một giao diện địa phương trong các thử nghiệm lớp và sử dụng phương pháp của nó trong phương pháp overidden:

private interface IMocker 
{ 
    boolean doSomething(); 
} 

IMocker imocker = EasyMock.createMock(IMocker.class); 

... 

@Override 
void doSomething() 
{ 
    imocker.doSomething(); 
} 

... 

EasyMock.expect(imocker.doSomething()).andReturn(true); 
0

Thêm một dụ về cách thực hiện mô hình tĩnh cùng giả thường xuyên của lớp tiêm với EasyMock/PowerMock, vì dụ như liên kết chỉ cho thấy mô hình tĩnh.

Và với PowerMockRunner các dịch vụ @Mock không được kết nối trên dịch vụ @TestSubject để kiểm tra.

Hãy nói rằng chúng ta có một dịch vụ chúng tôi muốn kiểm tra, ServiceOne:

import org.springframework.beans.factory.annotation.Autowired; 
import org.springframework.stereotype.Service; 

@Service 
public class ServiceOne { 

    @Autowired 
    private ServiceTwo serviceTwo; 

    public String methodToTest() { 
     String returnServ2 = serviceTwo.methodToMock(); 
     return ServiceUtils.addPlus(returnServ2); 
    } 
} 

nào gọi một dịch vụ mà chúng tôi sẽ muốn thử, ServiceTwo:

import org.springframework.stereotype.Service; 

@Service 
public class ServiceTwo { 

    public String methodToMock() { 
     return "ServiceTwoReturn"; 
    } 
} 

Và trong đó kêu gọi một lớp học chính thức phương pháp tĩnh, ServiceUtils:

public final class ServiceUtils { 

    public static String addPlus(String pParam) { 
     return "+" + pParam; 
    } 
} 

Khi gọi ServiceOne.methodToTest() chúng tôi nhận được "+ServiceTwoReturn" là sự trở lại.


thử nghiệm Junit với EasyMock, chế giễu chỉ dịch vụ xuân ServiceTwo tiêm:

import static org.easymock.EasyMock.expect; 
import static org.easymock.EasyMock.replay; 
import static org.easymock.EasyMock.verify; 
import static org.junit.Assert.assertEquals; 

import org.easymock.EasyMockRunner; 
import org.easymock.Mock; 
import org.easymock.TestSubject; 
import org.junit.Test; 
import org.junit.runner.RunWith; 

@RunWith(EasyMockRunner.class) 
public class ExempleTest { 

    @TestSubject 
    private ServiceOne serviceToTest = new ServiceOne(); 

    @Mock 
    private ServiceTwo serviceMocked; 

    @Test 
    public void testMethodToTest() { 
     String mockedReturn = "return2"; 

     expect(serviceMocked.methodToMock()).andReturn(mockedReturn); 
     replay(serviceMocked); 

     String result = serviceToTest.methodToTest(); 

     verify(serviceMocked); 

     assertEquals("+" + mockedReturn, result); 
    } 
} 

Junit Thử nghiệm với EasyMock & PowerMock, chế giễu các dịch vụ xuân ServiceTwo tiêm mà còn trận chung kết lớp và phương pháp tĩnh của nó:

import static org.easymock.EasyMock.expect; 
import static org.junit.Assert.assertEquals; 
import static org.powermock.api.easymock.PowerMock.createMock; 
import static org.powermock.api.easymock.PowerMock.mockStatic; 
import static org.powermock.reflect.Whitebox.setInternalState; 

import org.easymock.Mock; 
import org.junit.Before; 
import org.junit.Test; 
import org.junit.runner.RunWith; 
import org.powermock.api.easymock.PowerMock; 
import org.powermock.core.classloader.annotations.PrepareForTest; 
import org.powermock.modules.junit4.PowerMockRunner; 

@RunWith(PowerMockRunner.class) 
@PrepareForTest(ServiceUtils.class) 
public class ExempleTest { 

    private ServiceOne serviceToTest; 

    private ServiceTwo serviceMocked; 

    @Before 
    public void setUp() { 
     serviceToTest = new ServiceOne(); 
     serviceMocked = createMock(ServiceTwo.class); 
     // This will wire the serviced mocked into the service to test 
     setInternalState(serviceToTest, serviceMocked); 
     mockStatic(ServiceUtils.class); 
    } 

    @Test 
    public void testMethodToTest() { 
     String mockedReturn = "return2"; 
     String mockedStaticReturn = "returnStatic"; 

     expect(serviceMocked.methodToMock()).andReturn(mockedReturn); 
     expect(ServiceUtils.addPlus(mockedReturn)).andReturn(mockedStaticReturn); 
     PowerMock.replayAll(); 

     String result = serviceToTest.methodToTest(); 

     PowerMock.verifyAll(); 

     assertEquals(mockedStaticReturn, result); 
    } 
} 
Các vấn đề liên quan