Archiv für den Monat: Januar 2015

How to overwrite static methods

Normally it is not possible to overwrite a static method in Java. But recently I had a bug in a project context. The reason for the bug had tow dimensions:

  1. One reason was an overwritten static method
  2. and the other reason was a missing unit test

The context look like this:

Classdiagramm-BaseComponent

The class AbstractClassWithStatic defines the static method getLanguageZoAnswer(String), the class ClassImpl extends AbstractClassWithStatic and the class BusinessClass uses the static method.

Until now the static method is not overwritten. The classes described above are all located in one module.

This module is now used by a customer module. In the customer module is also a class ClassImpl and in the class a static method with the same signature is with different behavior defined.

ComponentDiagramm

If the classpath is defined in a way that the class ClassImpl from the customer module is loaded before ClassImpl from the base module then the static method is overwritten.

But what could go wrong here?

Originally the class BusinessClass called the the static method by ClassImpl.getLanguageToAnswer(String) (see row 15 in the code sample below).

   1: package de.sevendroids.projects.java.staticoverride;
2: 
3: import java.util.Locale;
4: 
5: /**
6: * @author 7droids
7: *
8: * This class uses the functions provided by AbstractClassWithStatic
9: * and his sub classes.
10: *
11: */
12: public class BusinessClass {
13: 
14: public String findLanguage(String sampleText) {
15: Locale language = ClassImpl.getLanguageToAnswer(sampleText);
16: switch (language.getLanguage()) {
17: case "en":
18: return "English is spoken";
19: case "de":
20: return "Es wird Deutsch gesprochen";
21: default:
22: return "Unknown language: " + language.getLanguage();
23: }
24: }
25: }

The bug was inserted in the code when someone changed line 15 to AbstractClassWithStatic.getLanguageToAnswer(String). With this minor innocent looking change the overwritten static method from the customer module was not used anymore. The bug was not found immediately because no unit tests exists.

The units test should exist for the class BusinessClass in both(!) modules. If a (static) method is overwritten in a (customer) module then all classes that use the overwritten method should have there own unit tests in the customer module.