- Overview
- Create new Jooby Application
- Application Code Layout
- Building the Application
- Running Jooby Web Application
- Adding Additional Features to Jooby
- Creating a New Web Service
- Adding Dependencies
- Handling Static Content
- Session Management in Jooby
- Application Configuration Settings
- Wait, there is more…
- Why you should use Jooby for your own applications
- Download the Code
Overview
Jooby is a scalable fast micro web server framework that allows you to build microservices as well as full stack applications with backend service and a front-end build using any of the following template engines.
Among the many Java/Kotlin based frameworks for web developments Jooby
shines because of its simplicity and high performance.
TechEmpower, a publisher posting Web Framework benchmarks, have found that it is one of the fastest servers in the marketplace. As a matter of fact, they find it to be almost 300% faster than the most popular Java Spring framework.
In this post,I will go over the details of how to create a web application with Jooby. I will go over the details of creating both a GET as well as a POST service. In addition, we will add static content to the application as well.
Let’s go…
Create new Jooby Application
There are a few ways to create a Jooby
application. I will take the easiest one, which is by using the Jooby application generator.
Download the zip file and unzip it anywhere on your file system. I have unzipped the Jooby
files in the location C:\apps
.The folder structure should look similar to the image below.
jooby
- bin
- jooby
- jooby.bat
- lib
- jooby-cli-2.16.1.jar
Open a command shell and enter the following file to create a new Jooby App.
D:\temp> C:\apps\jooby\bin\jooby create joobyapp --server jetty
This command will create Jooby
App joobyapp
in the location D:\temp\joobyapp\
, using Jetty as the bundled server. Jooby
comes with options to select either Netty or Undertow as the bundled engine.
Note: You can switch between any of these by updating pom.xml with the relevant repository entry
Do note that Jooby
also has a Maven
archetype. You can use it to create a sample project with necessary dependencies by using the following command.
mvn archetype:generate -B -DgroupId=com.baeldung.jooby -DartifactId=jooby -Dversion=1.0 -DarchetypeArtifactId=jooby-archetype -DarchetypeGroupId=org.jooby -DarchetypeVersion=2.16.1
Application Code Layout
joobyapp
- conf
- application.conf
- logback.xml
- src
- main
- java
- app
- App.java
- test
- java
- app
- IntegarationTest.java
- UnitTest.java
- pom.xml
- README.md
Under the conf folder you will find two files:
application.conf
: Configuration file to enter variables that can be used by the application to configure and initialize resources. In this file you can enter values to configure databases, cache or use for your own custom variables.logback.xml
: Jooby uses Slf4j for logging. You are free to use either LogBack or Log4J2.
Below the src
folder you will find you general code files, adding more as your application grows.
The test
folder has the test files for creating integration and unit test cases using JUnit.
pom.xml
is the standard file required for use with Maven build tools.
…
Full video coming soon to YouTube.
Building the Application
Before we build the application, let’s start by looking at the pom.xml to understand the structure of the project so we know what is going on. First, we look at the core dependencies, which basically show that the Jetty
engine is being used with LogBack
for logging.
<dependency>
<groupId>io.jooby</groupId>
<artifactId>jooby-jetty</artifactId>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
</dependency>
Next, there are test dependencies.
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>io.jooby</groupId>
<artifactId>jooby-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
<scope>test</scope>
</dependency>
Here in addition to JUnit you will find OkHttp
dependency which is used for building test cases.
Main Jooby Application
The heart of Jooby is in the man App.java file where the loop for creating web requests is created.
public class App extends Jooby {
{
get("/", ctx -> "Welcome to Jooby!");
}
public static void main(final String[] args) {
runApp(args, App::new);
}
}
There are three main lines in this code block.
- Line 1: The main application class extends
Jooby
. This brings in all relevantHTTP
methods such as GET and POST. - Line 3: Here we create a simple GET route “/” that returns the message calling this web service. In this app, we are using Java Lambda expression to write our code. Jooby also provides
MVC
API which is an alternative method to define routes using annotations. In a later post, I will go over how to build services using MVC API. - Line 7: using the static runApp method of
Jooby
class a new Web Application loop is created.
Running Jooby Web Application
Now that we have seen the files created by the Jooby app generator, we are now going to run the application. You can run the application from the IDE (Eclipse, IntelliJ or Netbeans) of your choice.
For this initial test run, we are going to use the command line to run our application. Since I have put the application at D:\temp\joobyapp, I will go there and run the following commands.
D:\temp\joobyapp> mvn build
D:\temp\joobyapp> java -jar target\joobyapp-1.0.0.jar
The first command will build the application and the second will execute the built jar. On successful run you will see the following messages generated by Jooby web application.
[2022-10-19 22:32:35,543]-[main] INFO org.eclipse.jetty.util.log - Logging initialized @1269ms to org.eclipse.jetty.util.log.Slf4jLog
[2022-10-19 22:32:35,651]-[main] INFO org.eclipse.jetty.server.Server - jetty-9.4.48.v20220622; built: 2022-06-21T20:42:25.880Z; git: 6b67c5719d1f4371b33655ff2d047d24e171e49a; jvm 17.0.2+8-86
[2022-10-19 22:32:35,678]-[main] INFO org.eclipse.jetty.server.handler.ContextHandler - Started o.e.j.s.h.ContextHandler@2a54a73f{/,null,AVAILABLE}
[2022-10-19 22:32:35,806]-[main] INFO org.eclipse.jetty.server.AbstractConnector - Started ServerConnector@4009e306{HTTP/1.1, (http/1.1)}{0.0.0.0:8080}
[2022-10-19 22:32:35,806]-[main] INFO org.eclipse.jetty.server.Server - Started @1537ms
[2022-10-19 22:32:35,809]-[main] INFO app.App - App started with:
[2022-10-19 22:32:35,809]-[main] INFO app.App - PID: 13212
[2022-10-19 22:32:35,809]-[main] INFO app.App - jetty {port: 8080, workerThreads: 200, bufferSize: 16384, maxRequestSize: 10485760, httpsOnly: false}
[2022-10-19 22:32:35,809]-[main] INFO app.App - env: [dev]
[2022-10-19 22:32:35,809]-[main] INFO app.App - execution mode: default
[2022-10-19 22:32:35,809]-[main] INFO app.App - user: sohai
[2022-10-19 22:32:35,809]-[main] INFO app.App - app dir: D:\temp\joobyapp
[2022-10-19 22:32:35,809]-[main] INFO app.App - tmp dir: D:\temp\joobyapp\tmp
[2022-10-19 22:32:35,809]-[main] INFO app.App - routes:
GET /
listening on:
http://localhost:8080/
The server is running on port 8080 on localhost. You can access it through your browser.
Adding Additional Features to Jooby
Simple though Jooby
is to start with, it comes with a lot of features. Many of these are configurable through the application.conf
file. In this section I will be adding the following features to our base JoobyApp.
- Create a new web service.
- Implement the Post method.
- Add module dependencies.
- Handle static content, such as an image and HTML page.
- Session management in Jooby.
- Playing with application.conf file: Change the default server port from 8080 to 8888.
- Database integration with MySql.
- Configure logging and write to the log file.
- Create test case for our new web service.
Creating a New Web Service
Add a new Java class named AuthService
.java and extend it using Jooby
as the base class.
First, I will add a User class with the properties username
and password
. I will also add getters and setters for the properties. My User.java file will now be:
public class User {
private String username;
private String password;
// Omitting the getters and setters
}
Add an initialization block to your class and create a GET
route named /auth/user/{username}
. The {username}
adds a path parameter to the route.
I will also add a POST path for the user authentication mechanism.
public class AuthService extends Jooby {
{
get("/auth/user/{username}", (Context ctx) -> {
var user = new User(ctx.path("username").value(), "nopass");
return user;
});
post("/auth/authenticate", ctx -> {
var user = ctx.body(User.class);
return user;
});
}
}
Let go over the code:
- Line 4: A new route is defined that accepts a path parameter {username}.
- Line 6: Read the value of the path parameter from the URL.
- Line 13: Read the posted user information from the body of the request.
Once my service class and user class have been created, I will add them to the App.java
file to enable the new routes.
install(AuthService::new);
Adding Dependencies
In my requests, I am working with JSON
. The data with POST
body is going to be in JSON
format and the responses I send back are in JSON as well.
Although you can add Gson
or Jackson
jars and do this process of conversion yourself, Jooby
provides a Modules for this functionality to make coding easier.
To support JSON, there are modules for Gson
, Jackson
, JSON-B
. I will be using Gson
module. For this add the correct Maven dependency.
<dependency>
<groupId>io.jooby</groupId>
<artifactId>jooby-gson</artifactId>
</dependency>
Now you need load it and you do that by adding the following to the initialization block of the App.
install(new GsonModule());
Now we are ready to deal with appropriate Accept
and Content-Type
headers.
Using Authentication Web Service
Now that all the coding changes are in place I will build the code. Check the directions above, if missed earlier on how to build the code.
Handling Static Content
Jooby
supports serving static content in addition to building web services using the framework. As a matter of fact you can build full-stack web application using Jooby
and one of the templating frameworks such as HandleBars
or ThymeLeaf
.
I won’t get into using the available templating engines but would add an index.html file. So let’s start…
Create a folder in the root of the project. I will name it public
but you can name it whatever you would like. Once the folder is created, delete the default get(“/”) route from App. Our index.html
will serve this function. add the line shown below to the App class.
assets("/*", Paths.get("public"));
get("/", ctx -> "Welcome to Jooby!");
What do the two changes above do:
- Line 1: Use the folder public in the file system and serve content mapped to “/” located in it.
- Line 3: Delete this line as we are no longer using the route path.
Testing Changes
Rebuild the code using mvn build
and execute the jar file. Go to the browser and enter the URL, http://localhost:8080/
or http://localhost:8080/index.html
.
Contents of the index.html
will be displayed.
Session Management in Jooby
Jooby
provides multiple ways to manage sessions. The default method uses cookie based sessions stored in memory. You can modify this to use a header instead.
Using default session mechanism means that if the server is behind a load balancer and or proxy, then you will need to have a sticky sessions proxy to ensure that each subsequent request to the server comes back to the same server.
One way to manage sessions without dependency on a particular application server is by storing session information in a cache
like Redis
, which can be available to all Jooby
application instances.
Jooby
provides ways to manage the state in a session-less manner by using either signed sessions or using JWT
s.
Let’s look at the most basic ways to create and use sessions. Below is the POST request modified to get a session and use it in the return data.
post("/auth/authenticate", ctx -> {
var user = ctx.body(User.class);
Session session = ctx.session();
session.put("username", "Hello " + user.getUsername());
user.setUsername(session.get("username").toString());
return user;
});
Let’s look at the code
- Line 4: Get a session. If this is a first time call and a session does not exist a new one is created. You can also use sessionOrNull(), in which case a null is returned when there is no existing session.
- Line 5: Store a value in the session.
- Line 7: Get the value from the session.
After the changes when I compile and run the code, a modified username is returned in the JSON, but if I look at the header I will find that a session id is returned in a session cookie. Shown below is a sample screenshot of what the response will be.
Application Configuration Settings
Jooby
provides a mechanism to load property settings from config(.conf) files after startup. Using key value entries in the config file you can specify settings for the database, cache or just custom variables your application may need.
In this section I will show you how you can change the port Jooby
‘s embedded server listens on. By default it is 8080 and I will change it to 9090.
Enable Jooby HTTPS Support with Self Signed Certificate
Open the file <project_root>/conf/application.conf in your editor and add the following entries in the file.
server.port = 9090
server.securePort = 9443
server.ssl.type = self-signed
server.httpsOnly = false
server.http2 = true
Let go over details of what each line does.
- Line 1: Change the default
port
. This setsJooby
to start listening onport
9090. - Line 2: Set secure
SSL port
to 9443. - Line 3: Enable self signed certificate mode.
- Line 4: This option I added only to show that you can set up
Jooby
to listen only on HTTPS and ignore all requests on non-secure port. To activate this mode change this to true. I am going to keep the false(which is the default option anyways) so the server listens on both secure and non-secure ports. - Line 5: The default value for
Jooby
is to support HTTP/1.1. With this config setting you can enable HTTP/2 support as well, which I suggest that you do for all of your services.
Testing Changes
Rebuild the code using mvn build
and execute the jar file. Monitor the console logs generated during the server startup. At end you should find the following two lines:
listening on:
http://localhost:9090/
https://localhost:9443/
That is is. You have successfully changed the values of the ports your applications are listening on using .conf file settings.
There is a lot more you can do and in subsequent posts, I will bring you more information. Keep checking on the website for new articles.
Wait, there is more…
Jooby has a lot more to it then what I have shown here. Other than build in functionality, the team has added support for many integrations using modules. Below is a partial list by category.
Cloud
AWS Support is built in as an extension module. Currently SDK 1.x is supported.
JSON
Multiple options are available such as Gson, Jackson and JSON-B.
Data
- Ebean ORM
- Flyway migration
- GraphQL
- HikariCP for connection pooling
- Hibernate
- Jdbi
Templating Engines
Session Stores
- Caffeine cache
- JWT
- Redis cache
Dependency Injection
- Guice
- Spring
- Weld
Security
- Jasypt: For encrypted configuration files.
- Pac4j: Build secure applications with multiple authentications built in such as for Google, Twitter and JWTs.
Development
- Jooby Run: Run and hot reload your application.
- Node: Download, Install and Run node locally.
- Whoops: Pretty page stacktrace reporter.
- Metrics: Application metrics from the excellent metrics library.
Other
- OpenAPI
- Node: Node integration module.
- Quartz: Quartz scheduler module.
The best part is you can extend Jooby further by writing your own Modules.
There is a lot more to Jooby and I will be bringing you more information as our journey proceeds.
Why you should use Jooby for your own applications
I have built the back-end web services of this web site using Jooby. I have found it to be an excellent framework to create web services. The performance has been excellent.
There are a few drawback such as lack of info across the web making it difficult to find answers but you have options to look at the excellent documentation they provide as well as a forum where you can post questions. I have found responses on the forum take a little bit of time but someone always seems to get in touch.
Other than the issue of help resources on the web I found not many broken glasses lining my path to the creation of useful web services.
Check out Jooby
on their own website or on GitHub.
Let me know what you think about Jooby. If you have questions, do post in the comments below.
Download the Code
You can download the complete from GitHub.