Search code examples
javaunit-testingjunitmockingjmockit

How to Replace The Call to A Private Method of The Class Being Tested


Well, I am right now testing legacy code. And, I am somewhere near to pass this test, but its stuck at the line having comments on it. Here is the snippet

    new NonStrictExpectations(){
        SASCustomerDataAssemblerBD assembleBd;
        CustomerTOs tos;
        CustomerSASTO to;
        Another rowTo;
        SelectionJobLogBD logBd;    

        {
                SASCustomerDataAssemblerBD.getInstanceUsingEjbRef(); result = assembleBd;
                assembleBd.getData(); result = tos;
                ..
                ..
                //This line is not being invoked. 
                //Instead the actual line of code is working. Which is,
                //Collections.max(someCollection, someComparator);
                //Hence I am stuck because getting null in "to"
                invoke(Collections.class, "max", new ArrayList(), new MaxDateComparator()); result = to;
                to.getSasDataRow(); result = rowTo;
                SelectionJobLogBD.getInstanceUsingEjbRef(); result = logBd;                                 
                ..
        }
    };

    new TaskSASCustomerReading().execute(); 

Whereas, all the values of result are mocked up.


Solution

  • Solved it, in another way :). Mocked the original method -- only the method that calls Collections.max() under the hood.

        new MockUp<TaskSASCustomerReading>()
        {
            @Mock
            // This original method is invoking Collections.max(). 
            // Therefore, I just mocked this one, other methods are all original
            String findLatestSelectionDate(Collection customerTOs) {
               return "";
            }
        };
    
        new Expectations(){
            SASCustomerDataAssemblerBD assembleBd;
            CustomerTOs tos;         
            SelectionJobLogBD logBd;
            {
                try {
                    SASCustomerDataAssemblerBD.getInstanceUsingEjbRef(); result = assembleBd;
                    assembleBd.getData();  result = tos;
                    SelectionJobLogBD.getInstanceUsingEjbRef();  result = logBd;                                
                }catch(Exception e){}
            }
        };
    
        new TaskSASCustomerReading().execute(); 
    

    None the less, I was totally misunderstood the thing in the first place, when I asked the question. In my original question, I am in fact trying to invoke a method, instead of replacing it. (P.S. Never work after hours. ;))