<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    thinking

    one platform thousands thinking

    Mocking Static Calls

    How can you test methods that contain static method calls? This is a question we're facing at the moment while working on an application of which parts have been written by another development team. In order to gain insight into functionality and quality of the codebase, we are writing JUnit tests. But a lot of the code is dependent on either the JSF FacesContext or the Spring ApplicationContext being available.

    It is however impossible to mock static method calls like FacesContext.getCurrentInstance(). So how do we go around testing these calls out of container? We've thought up three different approaches, but each has its pros and cons. Let us first take a look at these three approaches...

    1. Extract method
    Introduce a method in each class that looks like the following:

     
    protected FacesContext getFacesContext() {
    return FacesContext.getCurrentInstance();
    }
     

    This can be easily mocked out in your test by creating the class with an overridden method, as follows:

     
    FacesContext mockContext = EasyMock.createMock(FacesContext.class);
    new MyObjectUnderTest() {
    protected FacesContext getFacesContext() {
    return mockContext;
    }
    }
     

    Pros

    • Easy to refactor using extract method

    Cons

    • Lots of code duplication

    2. Static Helper
    Our second option is to introduce a static helper class which has the following implementation:

     
    public class FacesContextHelper {
    private static FacesContext context;
     
    public static FacesContext getCurrentFacesContext() {
    return context != null ? context : FacesContext.getCurrentInstance();
    }
     
    public static void setFacesContext(FacesContext facesContext) {
    context = facesContext;
    }
     
    public static void reset() {
    context = null;
    }
    }
     

    Now in a testclass we can just write down the following line to mock out the FacesContext:

     
    FacesContextHelper.setFacesContext(EasyMock.createMock(FacesContext.class));
     

    Pros

    • No real painful code-duplication
    • Easy to do search-replace to convert all calls to FacesContext.getCurrentInstance() to FacesContextHelper.getCurrentFacesContext().

    Cons

    • Never forget to call reset() in the teardown of your test to prevent another test from picking up your mock.
    • Doesn't feel right to write static setter methods in your code just to enable testing it. Not an OO approach?

    3. OO Helper class
    Our third and last option is to introduce an interface and implementation of the FacesContextHelper:

     
    public interface FacesContextHelper {
    FacesContext getCurrentFacesContext();
    }
     
    public class FacesContextHelperImpl implements FacesContextHelper {
    public FacesContext getCurrentFacesContext() {
    return FacesContext.getCurrentInstance();
    }
    }
     

    We now need to introduce an instance of the FacesContextHelperImpl to each class. For this example, we will use a package protected variable in each class. It is of course also possible to use a setter method. For our test cases we now need to introduce a new FacesContextHelper:

     
    public class MockFacesContextHelper implements FacesContextHelper {
    private FacesContext mockContext;
     
    public MockFacesContextHelper(FacesContext mockContext) {
    this.mockContext = mockContext;
    }
     
    public FacesContext getCurrentFacesContext() {
    return this.mockContext;
    }
    }
     

    In our test cases we can now easily mock out the FacesContext again by setting the package protected field:

     
    someClazz.facesContextHelper = new MockFacesContextHelper(EasyMock.createMock(FacesContext.class));
     

    Pros

    • Feels more natural and OO than the static helper solution

    Cons

    • Need to introduce a new field to each and every class which needs the FacesContext mocked out.

    That's it. I myself am still doubting as to which method is the lesser evil, not one feels absolutely right. What do you think, which method do you consider better? Did I overlook another option perhaps?

    posted on 2010-02-25 09:12 lau 閱讀(355) 評論(0)  編輯  收藏 所屬分類: Unit Test

    主站蜘蛛池模板: 亚洲一区二区三区电影| 亚洲精品无码国产片| 麻豆安全免费网址入口| 午夜a级成人免费毛片| 亚洲中文字幕乱码熟女在线| 巨波霸乳在线永久免费视频 | A片在线免费观看| 亚洲人成在线播放网站| 999zyz**站免费毛片| 亚洲高清在线播放| 最近中文字幕大全免费视频| 亚洲区视频在线观看| 国产香蕉九九久久精品免费| 亚洲av永久中文无码精品| 免费观看国产精品| 精品乱子伦一区二区三区高清免费播放| 中文亚洲AV片不卡在线观看| 无码国产精品一区二区免费模式| 亚洲毛片基地日韩毛片基地| 在线观看人成视频免费| 丁香六月婷婷精品免费观看| 亚洲成a人片77777kkkk| 免费国产作爱视频网站| 色窝窝亚洲av网| 亚洲精品乱码久久久久久| 91免费播放人人爽人人快乐| 国产精品久久久久久亚洲影视| 亚洲综合亚洲综合网成人| 日韩人妻一区二区三区免费| 亚洲熟女www一区二区三区| 亚洲情侣偷拍精品| 在线永久免费的视频草莓| 亚洲av永久无码天堂网| 在线观看亚洲av每日更新| 97热久久免费频精品99| 黄色a三级三级三级免费看| 亚洲一级二级三级不卡| 四虎永久在线精品免费观看地址 | 亚洲精品无码Av人在线观看国产| 无人在线直播免费观看| 九九久久精品国产免费看小说|