Assertions Part 1 Tutorial

Have you ever written some logic into your code and you stumble into situation where you almost know for certain that a condition will never happen? Do you put a lot of println() methods into your source code in the early stages of development only to comment them out or remove them completely? If the answer is yes to either of the above questions, then assertions are the perfect production source code debugging tool for you. Assertions are built using the Java keyword assert.
Consider the following code:
class AssertionsOne {
     String state;
     AssertionsOne(String state) {
         this.state += state;
     }
     public static void main(String args[]){
         AssertionsOne ao = new AssertionsOne("YES");
     }
}
In the code above are we fairly certain that our state for the ao object will equal "YES"?
Sure why not ... everything appears to be in order. Being the thorough programmers that we are, we decide to put in a quick if statement to alert if the unexpected occurs. Now we have the resulting code:
class AssertionsOne {
     String state;
     AssertionsOne(String state) {
         this.state += state;
     }
     public static void main(String args[]){
         AssertionsOne ao = new AssertionsOne("YES");
         if (!ao.state.equals("YES")) {
             System.out.println("Ut-oh!! unexpected result in state: "+ao.state);
         }
     }
}

When we run the above source code we get "Ut-oh!! unexpected result in state: ??????" (I'll explain in the video). The point here is not that we received an unexpected result, the point here is that we have an if statement in our source code that shouldn't be allowed into production code. We never want the end user to see the message "Ut-oh!! unexpected result in state: ??????" under any circumstances. So we will have to either comment the if statement or remove it prior to production, there is no other solution, correct? Assertions to the rescue! I'll demonstrate that exact same thing above only we will never have to remove our debug logic, and better yet, we can enable our debug logic live in the field on production code! Here is how:
class AssertionsOne {
     String state;
     AssertionsOne(String state) {
         this.state += state;
     }
     public static void main(String args[]){
         AssertionsOne t = new AssertionsOne("YES");
         assert (ao.state.equals("YES")) : "Ut-oh!! unexpected result in state: "+ao.state;
     }
}
Let's break down the assert statement above. The assert (ao.state.equals("YES")) portion is evaluating a boolean result from the expression ao.state.equals("YES"). It is important to note that an assert statement can only evaluate an expression that returns a boolean result, it is no different from an if statement in that respect. The next thing that you will see is a colon :, and after the colon you can have whatever output you would like displayed to the console - sort of. In reality the assert mechanism simply throws a new AssertionError(your output into the constructor) if the result of the expression is false. Say what??? That is right, if an assert statement evaluates to false an AssertionError is thrown and your program will come to a crashing halt! That is a good thing and that is precisely what we want when we use an assert statement.

Remember this - by default the JVM will ignore all assert statements! We have to include a special flag to tell the JVM that to enable all assert statements, and if you think about it carefully, you would only want to do so when an unexpected result has occurred.
In order to enable assertions we simply include the -ea or -enableassertions flag when invoking the class using the java command. Something like this:
java -ea AssertionsOne
Okay, enough talk, let's jump right in and see how it works.



Open the command prompt (CMD - see the Getting Started ) and type in the following commands.

C:\Windows\System32>cd \
C:\>md Java
C:\>cd Java
C:\Java>
C:\Java>md AssertionsOne
C:\Java>cd AssertionsOne
C:\Java\AssertionsOne>Notepad AssertionsOne.java

Copy and Paste, or type the following code into Notepad and be sure to save the file when you are done.


class AssertionsOne {
    String state;
    
    AssertionsOne(String state) {
        this.state += state;
    }

    public static void main(String args[]){
        AssertionsOne t = new AssertionsOne("YES");
        if (!t.state.equals("YES")) {
            System.out.println("Ut-oh!! unexpected result in state: "+t.state);
        }
        //assert (t.state.equals("YES")) : "Ut-oh!! unexpected result in state: "+t.state;
    }
}

Now switch back to the command prompt (CMD) and type in javac AssertionsOne.java and press Enter.
Now type in java AssertionsOne and press Enter.


C:\Java\AssertionsOne>javac AssertionsOne.java
C:\Java\AssertionsOne>java AssertionsOne
Exception in thread "main" java.lang.AssertionError: Ut-oh!! unexpected result in state: nullYES
    at AssertionOne.main(AssertionOne.java:13)


Final thoughts

It is pretty cool that we can debug our program on the fly in a live production type setting. Careful planning in the design phase is the key to making assertions part of your debugging arsenal. Stay tuned for more tutorials on this subject where I will discuss proper usage and improper usage of the assert statement.


Tutorials