Chapter 7. OptaWeb Vehicle Routing development guide

This section describes how to configure and run the back and front end modules in development mode.

7.1. OptaWeb Vehicle Routing project structure

The OptaWeb Vehicle Routing project is a multi-module Maven project.

Figure 7.1. Module dependency tree diagram

The back end and front end modules are at the bottom of the module tree. These modules contain the application source code.

The standalone module is an assembly module that combines the back end and front end into a single executable JAR file.

The distribution module represents the final assembly step. It takes the standalone application and the documentation and wraps them in an archive that is easy to distribute.

The back end and front end are separate projects that you can build and deploy separately. In fact, they are written in completely different languages and built with different tools. Both projects have tools that provide a modern developer experience with fast turn-around between code changes and the running application.

The next sections describe how to run both back end and front end projects in development mode.

7.2. The OptaWeb Vehicle Routing back end module

The back end module contains a server-side application that uses Red Hat Business Optimizer to optimize vehicle routes. Optimization is a CPU-intensive computation that must avoid any I/O operations in order to perform to its full potential. Because one of the chief objectives is to minimize travel cost, either time or distance, OptaWeb Vehicle Routing keeps the travel cost information in RAM memory. While solving, Red Hat Business Optimizer needs to know the travel cost between every pair of locations entered by the user. This information is stored in a structure called the distance matrix.

When you enter a new location, OptaWeb Vehicle Routing calculates the travel cost between the new location and every other location that has been entered so far, and stores the travel cost in the distance matrix. The travel cost calculation is performed by the GraphHopper routing engine.

The back end module implements the following additional supporting functionality:

  • Persistence
  • WebSocket connection for the front end
  • Data set loading, export, and import

To learn more about the back end code architecture, see Appendix A, Back end architecture.

The next sections describe how to configure and run the back end in development mode.

7.2.1. Running the OptaWeb Vehicle Routing back end module using the Spring Boot Maven plugin

You can use the Spring Boot plug-in to run the OptaWeb Vehicle Routing back end module in development mode.

Prerequisites

Procedure

  1. Change directory to optaweb-vehicle-routing-distribution-7.39.0.Final-redhat-00005/sources/optaweb-vehicle-routing-backend.
  2. To run the back end in development mode, enter the following command:

    mvn spring-boot:run

7.2.2. Running the OptaWeb Vehicle Routing back end module from IntelliJ IDEA

You can use the IntelliJ IDEA to run the OptaWeb Vehicle Routing back end module to make it easier to develop your project.

Procedure

  1. In IntelliJ IDEA, enter org.optaweb.vehiclerouting.OptaWebVehicleRoutingApplication. This creates a run configuration that you will edit in the next step.

    1. Open the OptaWebVehicleRoutingApplication class in the Editor window.
    2. Click the green symbol in the editor window gutter and select Run OptaWebVehicleRoutingApplication. The run fails because the working directory is set to the root of the project where the back end module directory is expected.

      Note

      See the Run Applications page on the IntelliJ IDEA web site to learn more about running applications in IntelliJ IDEA.

  2. Select Run→Edit Configurations and then select Spring Boot→OptaWebVehicleRoutingApplication.
  3. Set Program arguments to --spring.profiles.active=local to activate the Spring profile called local. This directs the application to use configurations in the application-local.properties file.
  4. Change Working directory to the back end module (optaweb-vehicle-routing-backend).
  5. Set On Update action to Hot swap classes and update trigger file if failed. This enables you to use the Update action to quickly restart the application.

    For more information, see Spring and Spring Boot in IntelliJ IDEA 2018.1.

7.2.3. Spring Boot automatic restart

Automatic restart is provided by Spring Boot DevTools. When you run the OptaWeb Vehicle Routing back end with the Spring Boot Maven plug-in, the application automatically restarts whenever files on the classpath change. Automatic restart scans files on the classpath, so you only need to recompile your changes to trigger application restart. No IDE configuration is needed.

If your IDE has a compile-on-save feature (for example Eclipse or NetBeans), you just need to save the files that have changed since the last compilation.

IntelliJ IDEA saves changes automatically and you need to select either Build[Recompile], which recompiles the file in the active tab, or Build[Build Project] which recompiles all changes. For more information, see Compile and build applications with IntelliJ IDEA.

7.2.4. Setting OptaWeb Vehicle Routing back end module configuration properties

There are several ways that you can set OptaWeb Vehicle Routing back end module configuration properties. The methods in this section are useful if you are running OptaWeb Vehicle Routing locally.

Prerequisites

Procedure

  1. Set configuration properties in the application.properties file:
  2. Change directory to rhpam-7.39.0.Final-redhat-00005-optaweb-vehicle-routing/sources/optaweb-vehicle-routing-backend/src/main/resources.
  3. Open the application.properties file in a text editor.
  4. Edit or add properties and then save the file.

    • Use a command line argument when running the packaged application. In the following example, <PROPERTY> is the name of a property and <VALUE> is the value of that property:

      java -jar optaweb-vehicle-routing-backend.jar --app.<PROPERTY>=<VALUE>
    • Use an environment variable when running the application with spring-boot:run:

      <PROPERTY>=<VALUE> ./mvnw spring-boot:run
      Note

      This method requires relaxed binding which only works if the property is defined using @ConfigurationProperties.

It is not possible to set properties by specifying -D when running the application using the Spring Boot Maven plugin (./mvnw spring-boot:run -D<PROPERTY). Any system properties to be set by the plugin to the forked Java process in which the application runs must be specified in the pom.xml file using the systemPropertiesVariables attribute. For information about this attribute, see Using System Properties on the Spring web site.

You can learn more about configuring a Spring Boot application on the Spring Boot Externalized Configuration page.

Tip

Use src/main/resources/application-local.properties to store your personal configuration without affecting the Git working tree.

For a complete list of OptaWeb Vehicle Routing configuration properties, see Appendix B, OptaWeb Vehicle Routing back end configuration properties.

For a complete list of application properties available in Spring Boot, see the Common Application Properties page on the Spring web site.

7.2.5. OptaWeb Vehicle Routing backend logging

OptaWeb Vehicle Routing uses the SLF4J API and Logback as the logging framework. The Spring environment enables you to configure most logging aspects, including levels, patterns, and log files, in the same way as other configuration properties. The most common ways to set logging properties are by editing the application.properties file or using arguments such as <PROPERTY>=<VALUE> where <PROPERTY> is the name of a property and <VALUE> is the value of that property. See the Spring Boot Logging documentation for more information.

The following examples are properties that you can use to control logging level of some parts of the application:

  • logging.level.org.optaweb.vehiclerouting=debug: Enables the debug level for the back end code
  • logging.level.org.optaplanner.core=warn: Reduces Red Hat Business Optimizer logging
  • logging.level.org.springframework.web.socket=trace: Accesses more details when investigating problems with WebSocket connection

7.3. Working with the OptaWeb Vehicle Routing front end module

The front end project was bootstrapped with Create React App. Create React App provides a number of scripts and dependencies that help with development and with building the application for production.

Prerequisites

Procedure

  1. On Fedora, enter the following command to set up the development environment:

    sudo dnf install npm

    See Downloading and installing Node.js and npm for more information about installing npm.

  2. Change directory to optaweb-vehicle-routing-distribution-7.39.0.Final-redhat-00005/sources/optaweb-vehicle-routing-frontend.
  3. Install npm dependencies:

    npm install

    Unlike Maven, the npm package manager installs dependencies in node_modules under the project directory and does that only when you execute npm install. Whenever the dependencies listed in package.json change, for example when you pull changes to the master branch, you must execute npm install before you run the development server.

  4. Enter the following command to run the development server:

    npm start
  5. If it does not open automatically, open http://localhost:3000/ in a web browser.

    By default, the npm start command attempts to open this URL in your default browser.

    Note

    If you do not want the npm start command to open a new browser tab each time you run it, export the BROWSER=none environment variable. You can use .env.local file to make this preference permanent. To do that, enter the following command:

    echo BROWSER=none >> .env.local

    The browser refreshes the page whenever you make changes in the front end source code. The development server process running in the terminal picks up the changes as well and prints compilation and lint errors to the console.

  6. Enter the following command to run tests:

    npm test
  7. Change the value of the REACT_APP_BACKEND_URL environment variable to specify the location of the back end project to be used by npm when you execute npm start or npm run build, for example:

    REACT_APP_BACKEND_URL=http://10.0.0.123:8081
    Note

    Environment variables are hard coded inside the JavaScript bundle during the npm build process, so you must specify the back end location before you build and deploy the front end.

    To learn more about the React environment variables, see Adding Custom Environment Variables.

  8. To build the front end, enter one of the following commands:

    ./mvnw install
    mvn install