2. Introduction
Aside from what is defined as conventional bad java coding practices such as
variables/methods/package naming, code formatting, among others. There are
some others that I had the chance to experience during my years as a JEE
engineer that I would like to share.
Therefore in the following slides I am going to explain five bad coding practices by
giving a short description of the problem then showing a poorly implemented code
snippet, on the other hand a suggestion on how to fix or prevent this issue will be
given along with a code snippet containing the correct implementation.
3. Bad coding practices examples
Problem: Presentation layer has high coupling with business
logic layer
One of the principles of good software
design is loose coupling, if the
presentation layer for example the web
application must have the business
layer logic referenced in his classpath
creates high coupling, which creates
dependency making different jars
dependant.
Solution: Create interfaces within a new jar to be
referenced from client applications.
By exposing business logic methods
through interfaces coupling is reduced
this allows seamless modification of
the business logic without having to
tweak the clients, also a good practice
is to put the entities along with these
interfaces so it is possible to pass
them as parameters.
public interface IGoodAppController { //Client jar code
public String calculateGoodness(ScheduledMachine schMach);
}
public class GoodAppController implements IGoodAppController {
@Override //Business jar logic
public String calculateGoodness(ScheduledMachine schMach) {
return "All good!";
}}
//Single jar logic
public class BadAppController {
public String calculateGoodness(ScheduledMachine schMach) {
return "Im highly coupled to you now!";
}
}
4. Bad coding practices examples (Cont. 2/5)
Problem: Hard coded environment dependant variables
Hard coding variables can lead to
application crashes while moving from
development to test / production
environments for example while looking
for IPs that only exists on a given
environment, furthermore if they are left
in a .java file they will be compiled to an
uneditable .class.
Solution: Make a properties file for constants or store them
in the database.
By putting everything in a single place
to change we can overcome this
problem, by creating a .properties file:
public class Good {
public static final String DB_HOST = "ipaddr";
public static void main(String[] args) {
Properties prop = new Properties();
InputStream input = null;
String ipAddr;
try {
input = new FileInputStream("envconst.properties"); // load prop file
prop.load(input); // get the property and print it
ipAddr=prop.getProperty(DB_HOST);
… //continues in the next slide
Another alternative is to create within
the catalog table of the database one
catalog that holds all these variables.
public class Bad {
public static final String DB_HOST = "192.168.1.1";
public static void main(String[] args) {
Properties prop = new Properties();
InputStream input = null;
String ipAddr;
try {
ipAddr=DB_HOST; // set the property value
… //continues in the next slide
5. Bad coding practices examples (Cont. 3/5)
Problem: Catching the Exception superclass
Throwing a very general exception
makes an application recovery almost
impossible and increases debug
complexity by making the source of the
exception hard to trace, this can lead to
frequent application crashes and
extended application downtimes:
Solution: Catch exceptions related to the sentences being
executed in that block of code.
Create a catch block for every kind of
expected subclass exception and in
the last block finally catch the
Exception superclass so it's easier to
identify the problem:
//continues from the previous slide
} catch (FileNotFoundException e){
System.out.println("File not found Exception"); //Short description of
the exception
e.printStackTrace(); //Print the trace to see what is wrong
} catch (IOException ex) {
System.out.println("I/O General Exception"); //A more general exception
is thrown
ex.printStackTrace();
} catch (Exception ex) {
System.out.println("General Exception"); //The base Exception superclass
will catch any other exception
ex.printStackTrace();
}
//continues from the previous slide
} catch (Exception ex) {
System.out.println("General Exception");
ex.printStackTrace();
}
6. Bad coding practices examples (Cont. 4/5)
Problem: Files cannot be accessed / cannot open any more
database connections.
If there is a file opened / being edited or
a database connection opened, if a
close statement is not issued the
resource will remain open until the
database times it out, preventing access
to that resource or exhausting it (full
database connection pools).
Solution: Whenever a resource is opened close it in the
finally block.
Prior to Java SE 7 all the objects which
implements java.io.Closeable must be
closed otherwise they will keep using
resources, from java 7 onwards this is
leveraged by java.lang.AutoCloseable
//continues from the previous slide
finally {
if (input != null) {
try {
input.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
//continues from the previous slide
//In solution number 2 a new FileInputStream was opened the compiler won’t
issue a compilation error but when the app needs the file again it will throw
a runtime exception
}
}
7. Bad coding practices examples (Cont. 5/5)
Problem: Excessive garbage allocation
When creating many short lived objects
the garbage collector executes
continuously, this degrades application
performance, for example since strings
are immutable each time a different
string is stored a new space in memory
is allocated.
Solution: Use mutable alternatives when instancing new
objects.
To prevent creation of new objects
while looping, alternative mutable
classes should be used in the example
is possible to replace StringBuilder
instead of String.
//App: count to one million
public class Bad {
public static void main(String[] args) {
String oneMillionCount = "";
for (int i = 0; i < 1000000; i++) {
oneMillionCount = oneMillionCount+ i+ ",";
}
System.out.println(oneMillionCount);
}}
//App: count to one million
public class Good {
public static void main(String[] args) {
StringBuilder oneMillionCountSB = new StringBuilder();
for (int i = 0; i < 1000000; i++) {
oneMillionCount.append(i);
oneMillionCount.append(",");
}
System.out.println(oneMillionCount.toString());
}}