paint-brush
How to Deploy a Spring Boot Application on Choreoby@jaadds
348 reads
348 reads

How to Deploy a Spring Boot Application on Choreo

by Amila De SilvaNovember 7th, 2023
Read on Terminal Reader
Read this story w/o Javascript
tldt arrow

Too Long; Didn't Read

With these recent updates, deploying applications written in Node, Java, Go, or Ruby on Choreo has become effortless. In this post, I will guide you through the steps of deploying a Spring Boot application on Choreo. Before we begin, please make sure that you have the following prerequisites in place.
featured image - How to Deploy a Spring Boot Application on Choreo
Amila De Silva HackerNoon profile picture

Introduction

With the introduction of Buildpacks, Choreo offers the flexibility to host services written in various languages, enabling development teams to leverage the benefits of Choreo while working on polyglot applications.


With these recent updates, deploying applications written in Node, Java, Go, or Ruby on Choreo has become effortless.


In this post, I will guide you through the steps of deploying a Spring Boot application on Choreo. Before we begin, please make sure that you have the following prerequisites in place.

Prerequisites

  • An active Choreo account. Make sure you have not exceeded your free component limit. Create a new account here if you don’t have one already.


  • Java 17 or higher.

Our Spring Boot Application

For this guide, I’ve chosen a popular Spring Boot example: employee service. This service facilitates the management of employee details. You can access the code for this application here. Feel free to fork the repository and change it.


Our Spring Boot application provides a simple REST API with the following four operations;


@RestController
@RequestMapping("/api")
public class EmployeeController {
    @Autowired
    private EmployeeService employeeService;

    @ResponseStatus(HttpStatus.OK)
    @GetMapping("/employees")
    public List<Employee> getEmployees() {
        return employeeService.getEmployees();
    }

    @ResponseStatus(HttpStatus.CREATED)
    @PostMapping("/employees")
    public Employee createEmployee(@RequestBody EmployeeRequest employee) {
        return employeeService.createEmployee(employee);
    }

    @ResponseStatus(HttpStatus.OK)
    @PutMapping("/employees/{employeeId}")
    public Employee updatedEmployee(@RequestBody EmployeeRequest employee, @PathVariable int employeeId) {
        return employeeService.updateEmployee(employeeId, employee);
    }

    @ResponseStatus(HttpStatus.NO_CONTENT)
    @DeleteMapping("/employees/{employeeId}")
    public void deleteEmployee(@PathVariable int employeeId) {
        employeeService.deleteEmployee(employeeId);
    }
}


Since I’m using JPA for data persistence, I have enabled an in-memory H2 database.


To test the application locally, clone the repository, and run the application using the following commands:

git clone [email protected]:jaadds/employee.git

cd employee

./mvnw spring-boot:run


You should see the application starting up.

  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::                (v3.1.4)

2023-10-23T15:46:41.186+05:30  INFO 20491 --- [           main] c.example.employee.EmployeeApplication   : Starting EmployeeApplication using Java 19.0.2 with PID 20491 
2023-10-23T15:46:41.188+05:30  INFO 20491 --- [           main] c.example.employee.EmployeeApplication   : No active profile set, falling back to 1 default profile: "default"
2023-10-23T15:46:41.654+05:30  INFO 20491 --- [           main] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data JPA repositories in DEFAULT mode.
2023-10-23T15:46:41.699+05:30  INFO 20491 --- [           main] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 37 ms. Found 1 JPA repository interfaces.
2023-10-23T15:46:42.166+05:30  INFO 20491 --- [           main] o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat initialized with port(s): 8080 (http)
2023-10-23T15:46:42.178+05:30  INFO 20491 --- [           main] o.apache.catalina.core.StandardService   : Starting service [Tomcat]
....


Let’s give it a try

curl http://localhost:8080/api/employees | jq


You should get the following output:

[
  {
    "id": 1,
    "firstName": "Bilbo",
    "lastName": "Baggins",
    "email": "[email protected]"
  }
]


Now that we know our service is working, let’s continue with deploying it on Choreo.

Preparing the Repository for Deployment

Choreo needs certain details to create an endpoint for your service, such as the service port, context path, and service definition. Additionally, you need to specify the endpoint’s visibility level, choosing between public (accessible over the internet) or internal (available only to services running within Choreo). All these details should be defined in the endpoints.yaml file.


For this tutorial, we will expose our employee service as a public endpoint. Create a .choreo/endpoints.yaml file in your project and add the following content:

version: 0.1
endpoints:
- name: Employee API
  port: 8080
  type: REST
  networkVisibility: Public
  context: /
  schemaFilePath: openapi.yaml


This is a short description of the attributes. For a detailed explanation, you can refer to the official documentation.

  • name: The name Choreo will use to create the endpoint. This name will also be used in the Developer Portal if you decide to publish a Managed API later.


  • port: The port on which your service is running. Update this value if you have changed the port using the server.port property.


  • type: The type of API/interface you are exposing. Valid values are REST, GraphQL, and gRPC.


  • networkVisibility: The level of visibility for the service over the network. Valid values are Project, Organization, and Public. We'll set this to Public for this tutorial.


  • context: The context path of your application. If you have changed the context path using the server.servlet.context-path property, use that value here. Since we haven't changed it, we'll leave it as /.


  • schemaFilePath: The schema of the Service. For a REST API, this will be the OpenAPI Specification. For GraphQL and gRPC, you can specify SDL and proto files, respectively. The location is read from the repository root, not from the ./.choreo folder.


Since we specified a schema file path, we need to generate and place the OpenAPI Specification in the specified location.

Generating the OAS

While it’s possible to manually create the OpenAPI Specification (OAS) for a small API like this, Spring’s rich ecosystem provides tools to do it easily. Add the springdoc-openapi dependency to your pom.xml, and start your application.

 <dependency>
    <groupId>org.springdoc</groupId>
    <artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
    <version>2.1.0</version>
 </dependency>


Get the OAS in YAML format using the following command:

curl http://localhost:8080/v3/api-docs.yaml > openapi.yaml


Commit these changes to your repository.

Deploying Changes to Choreo

Now that everything is set up, it’s time to deploy our Spring Boot application on Choreo. In case you missed any step, you can cross-check your work with the main branch of this repository. In addition to the steps mentioned here, I’ve updated the snakeyaml dependency to avoid security scan failures.


Before deploying our Spring Boot Application on Choreo, we’ll have to create a component on Choreo. As our Application behaves as a service, we’ll be creating a Service type component.

Creating a Service Component

  1. Select the “Service” Tile.

    Project Listing — Select Service component


  2. Provide the following details:

Field Name

Value

Component Name

Employee Service

Description

Service for managing employee details

Organization

Your GitHub account ID

Repository

The repository containing your code

Branch

The branch with the deployable changes (in this case, it’s main)

Build Preset

Java

Java Project Directory

Leave this as is

Language Version

Select the Java version from your POM (only LTS versions are available). In this case, it’s 17.

3. Click Create to finalize the component.

Deploying the Service

  1. Navigate to the Deploy page.

  2. In the Build Area section, verify component details and the latest commit.

    Deploy Page — Your commits and builds will appear here


  3. Click Configure & Deploy, which will initiate a three-step wizard.

    • First screen: Screen for adding environment variables. Skip this since we have none.
    • Second screen: For specifying file mounts. We can skip this too.
    • Final step: Verify details from endpoints.yaml and click Deploy.

  4. Clicking Deploy will initiate the build process. Choreo will compile the source code, build a container out of it, do a vulnerability scan, and deploy it to the development environment. Wait for the status to change to Active.


Viewing Logs

Once you see the Active label on the Development environment, your service should be up and running. If you want to further confirm if the service was started properly, you can check the logs.


Go to the Observability section to view logs. You’ll see logs similar to those you saw when running locally.

Logs in Observability page


Testing the Service

Finally, we can test the service. The Test section provides a variety of tools to do this. For our case, we will choose the Swagger Console. You may notice that the endpoint you specified in the YAML file appears in the drop-down menu. If you have defined multiple endpoints, all of them will appear in this drop-down.


Also, observe that an API Key has been generated. This is because when exposing endpoints for consumption, Choreo automatically secures them, requiring consumers to use a proper token.


Swagger Console on Test page

You can expand on a resource and click Execute.


This will give the response like this.

A successful invocation


Congratulations!! You’ve successfully deployed a Spring Boot application on Choreo.

What’s Next?

Learning and experimenting with the platform will help you to use Choreo better and develop production-grade applications in no time. Here are a few things you can do to familiarize yourself with the platform:


  1. Add logs to your resources, and use the Logs view in Choreo to trace requests end-to-end. This will be helpful for troubleshooting and debugging your application.


  2. Promote your Service to Production, and check whether everything runs smoothly. Experience how easily you can propagate changes across environments.


  3. Publish your service as an API in the Developer Portal. Manage, document, and share your API with other developers.


  4. Follow the official documentation of Choreo to learn more about concepts like Projects, Components, and Environments.


Stay tuned for the next post, where I will talk about built-in capabilities for securing and authorizing Services on Choreo.


Happy Coding!!


Also published here