Java – Initializing objects in Constructor

constructorsjava

I have below constructor, where it creates a workbook in constructor. I read that, ideally, we should not create objects in Constructor, instead, we should have just assignments which are passed.

public ExcelWriter() {
        workbook = new HSSFWorkbook();
        //other code
    }

Is it okay to create fixed objects like above?
What is ideal alternative solution?
and from Unit Testing perspective?
If to pass workbook from calling method code in other class, we have to create the workbook object even there also.

Is later is better approach? How it is better or matters compared to constructor approach?

Best Answer

For beginning programmers this is fine.

However, like you said, if you want to unit test this ExcelWriter class, you could perhaps give the HSSFWorkbook object as an argument in the constructor rather than creating it yourself. This way, you can use the real one in your code, and use a mock in the unit tests. This practice is called dependency injection.

So your constructor would look like:

public ExcelWriter(HSSFWorkbook hssfWorkBook) {
    workbook = hssfWorkBook;
    // other code
}

Then, somewhere else in your code, you call that constructor:

HSSFWorkbook myWorkbook = new HSSFWorkbook();
ExcelWriter myExcelWriter = new ExcelWriter(myWorkbook);

And your unit test would be something like:

HSSFWorkbook myMockedWorkbook = // create a mock
ExcelWriter testWriter = new ExcelWriter(myMockedWorkbook);

If you want to do this even better, use interfaces, so you'll end up with two separate classes:

public interface IWorkbook {}

public class RealWorkbook implements IWorkbook {
    // this is the one for in your code
}

public class FakeWorkbook implements IWorkbook {
    // this is the one you use in your unit test
}