Working with Java Spark Framework

3 min readWeb Development

browserlocalhost:4567MainClass.init(): Spark routesget("/") → main.ftl with home.ftl insideget("/removeUser") → removeUser.ftl + users as JSONput("/removeUser/:id") → mod.removeUser(id) 200 "User Removed" · 404 "No Such User Found"FreeMarkerEngine renders the ModelAndView with main.ftlmain.ftl: Bootstrap navbar, then <#include "${templateName}">nav: Home · Create · Get All · Update · Remove Userstatic files (css, js) served from /publicModel (mod)sendUsersId()removeUser(id)pom.xml, Maven · mvn clean installspark-core · spark-template-freemarkerjackson-core · jackson-databindexec-maven-plugin runs Driver.MainClasstests: JUnit + EasyMockUser checked directly: usr.isValid() true or falseModel mocked: EasyMock.createMock(Model.class),expect(model.createUser(...)).andReturn(1)
The application in the post. Spark routes in MainClass.init() answer the browser on port 4567: GET / renders home.ftl inside main.ftl through the FreeMarker engine, GET /removeUser renders the remove page with the users as JSON, and PUT /removeUser/:id asks the Model to delete and answers 200 or 404. Maven pulls in spark-core, the FreeMarker template module and Jackson, and runs Driver.MainClass; the tests use JUnit with EasyMock standing in for the Model.

Creating a Rest based full stack application requires quite a bit of hands on knowledge of Back end services as well as Front end services. In this post, we are looking on Java micro web framework named Spark. We will build a rest based system where we can do stuff with User Data.

Requirements to get along

Spark is probably the easiest framework available to build a micro project. It removes the configuration hassles required while working with Spring or JSP etc. Lets get to the business. We would use Java 8 and Maven before starting with the application. To install Java 8 and Maven, you can follow the following steps -

Install Java 8

On Ubuntu
$ sudo add-apt-repository ppa:webupd8team/java
$ sudo apt-get update
$ sudo apt-get install oracle-java8-installer 
$ sudo apt-get install oracle-java8-set-default

On Mac, One can directly download JDK 8 from Oracle Website 

Check Java Version
$ java -version
java version "1.8.0_72"

Install Maven

$ sudo apt-get install maven

It will take a while to install.

Creating the Package

A Maven application requires creating certain configuration files. One such file is Pom.xml. Whether you use NetBeans or Eclipse , Pom.xml is automatically created. We will require to edit this file in order to get started. Spark is required to be included in our package, So add the following dependencies in pom.xml

<dependencies>
    <dependency>
        <groupId>com.sparkjava</groupId>
        <artifactId>spark-core</artifactId>
        <version>2.3</version>
    </dependency>
    <dependency>
        <groupId>com.sparkjava</groupId>
        <artifactId>spark-template-freemarker</artifactId>
        <version>2.3</version>
    </dependency>
    <dependency
        <groupId>com.fasterxml.jackson.core</groupId>
         <artifactId>jackson-core</artifactId>
         <version>2.5.1</version>
    </dependency>
    <dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
          <artifactId>jackson-databind</artifactId>
          <version>2.5.1</version>
    </dependency>
</dependencies>
  • spark-core - Java Spark Framework
  • spark-template-freemarker - Free Marker Template for Front End
  • jackson-core - Basic JSON streaming API implementation

Folder Structure

The folder structure must look like below (this is the layout of the app code) -

pom.xml
src/
  main/
    java/
      Driver/MainClass.java
      Model/Model.java, UserTable.java
      TemplateEngine/FreeMarkerEngine.java
      User/User.java, Validable.java
    resources/
      TemplateEngine/main.ftl, home.ftl, createForm.ftl,
                     showUser.ftl, updateForm.ftl, removeUser.ftl
      public/css/, public/js/           Bootstrap, jQuery
  test/
    java/CreateUserTest.java, HtmlTest.java, UpdateUserTest.java

Main class

As all the MVC frameworks, Spark also requires writing Routes with get, put, post, delete methods. In our application, we want to first get import stuffs in our Driver Class.

import TemplateEngine.FreeMarkerEngine;
import java.io.IOException;
import static spark.Spark.*;
import spark.ModelAndView;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import java.io.StringWriter;
import java.util.HashMap;
import java.util.Map;

public class MainClass {
    
    /**
     *  Entry Point
     * @param args
     */
    public static void main(String[] args) {
        MainClass s = new MainClass();
        s.init();
    }

Now we shall write the init() function to define our first route. Here is the code -

private void init() {
        get("/", (request, response) -> {
           Map<String, Object> viewObjects = new HashMap<String, Object>();
           viewObjects.put("title", "Welcome to Spark Project");
           viewObjects.put("templateName", "home.ftl");
           return new ModelAndView(viewObjects, "main.ftl");
        }, new FreeMarkerEngine());
}

Front End

As described, we now need to write the .ftl file which will contain our Html code. We shall use a Bootstrap starter template to get started.

<html>
    <head>
        <title>Spark Project</title>
        <link rel="stylesheet" href="css/bootstrap.min.css">
        <link rel="stylesheet" href="css/bootstrap-theme.min.css">
        <link rel="stylesheet" href="css/starter-template.css">
    </head>
    <body>

        <div class="navbar navbar-inverse navbar-fixed-top" role="navigation">
            <div class="container">
                <div class="navbar-header">
                    <button type="button" class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
                        <span class="sr-only">Toggle navigation</span>
                        <span class="icon-bar"></span>
                        <span class="icon-bar"></span>
                        <span class="icon-bar"></span>
                    </button>
                    <a class="navbar-brand" href="#"></a>
                </div>
                <div class="collapse navbar-collapse">
                    <ul class="nav navbar-nav">
                        <li class="active"><a href="/">Home</a></li>
                        <li><a href="createUser">Create User</a></li>
                        <li><a href="getAllUsers">Get All Users</a></li>
                        <li><a href="updateUser">Update User</a></li>
                        <li><a href="removeUser">Remove User</a></li>
                    </ul>
                </div><!--/.nav-collapse -->
            </div>
        </div>
        <script src="js/jquery.min.js"></script>
        <script src="js/bootstrap.min.js"></script>
        <div class="container">
            <#include "${templateName}">
        </div>
    </body>
</html>

Now create your home file.

<div class="starter-template">
   <h2>${title}</h2>
</div>

Running the Application

In order to run the application, we need to add certain code to our POM.XML file to let maven know what to do. Here is the code -

<name>SparkProject</name>
    <build>  
        <plugins>  
            <plugin>  
                <groupId>org.codehaus.mojo</groupId>  
                <artifactId>exec-maven-plugin</artifactId>  
                <version>1.2.1</version>  
                <executions>  
                    <execution>  
                    <phase>test</phase>  
                    <goals>  
                    <goal>java</goal>  
                    </goals>  
                    <configuration>  
                    <mainClass>Driver.MainClass</mainClass>  
                    </configuration>  
                    </execution>  
                </executions>  
            </plugin>  
        </plugins>  
    </build>

Now we can run -

mvn clean install
navigate to http://localhost:4567/

You should see the app running.

Rest Framework

We want to make our application restful, hence we need to deal with JSON for almost everything. I’ll demonstrate on how we can delete a user. Check the below code -

get("/removeUser", (request, response) -> {
    Map<String, Object> viewObjects = new HashMap<String, Object>();
    viewObjects.put("templateName", "removeUser.ftl"); 
    viewObjects.put("users", toJSON(mod.sendUsersId()));
    response.status(200);
    return new ModelAndView(viewObjects, "main.ftl");
        }, new FreeMarkerEngine());

put("/removeUser/:id", (request, response) -> {
     String id = request.params(":id");
     if(mod.removeUser(id)) {
         response.status(200);
         return "User Removed";
     }
     else {
         response.status(404);
         return "No Such User Found";
     }
});

Here, we are using same url but with two different purpose. When you hit /removeUser/ , it renders the removeuser template, but when you create a put request on /removeUser/SomeID, that SomeID is checked in the database and if found, it is deleted else a simple message is sent back. See, how easily we can play with the response codes. Click here to see the full code

Test Cases

Java Spark can easily be integrated with JUnit library. We shall write Unit test cases for our application. It’s simple because we do not need to mock anything related to Spark. We just need to mock our Model, which represents the way we access the database. However it has a simple interface and mocking it is straightforward. Let’s look at some examples.

import Model.Model;
import User.User;
import org.junit.Test;
import static org.junit.Assert.*;
import org.easymock.EasyMock;
import static org.easymock.EasyMock.*;

public class CreateUserTest {
    
    public CreateUserTest() {}
    
    @Test
    public void aUserIsNotValid() {
        User usr = new User();
        usr.setId("T12");
        usr.setFirstName("Test");
        usr.setAge(10);
        usr.setGender('X');
        usr.setLastName("Test");
        usr.setPhone("122");
        assertTrue(!usr.isValid());
    }
    
    @Test
    public void aUserIsCorrectlyCreated() {
        User usr = new User();
        usr.setId("T12");
        usr.setFirstName("Test");
        usr.setAge(10);
        usr.setGender('M');
        usr.setLastName("Test");
        usr.setPhone("1234567891");
        assertTrue(usr.isValid());
        
        Model model = EasyMock.createMock(Model.class);
        expect(model.createUser("T13", "Test","","Test",20,'M',"1234567891",12 
        )).andReturn(1);
    }

}

As you can see, it is so easy to check each and every unit of our code.

Conclusion

You can very well follow this GitHub link to all the code. I hope this post gave a handful insight in writing a Full Stack rest based application with Java. Feel free to send comments and corrections as well as suggestions.