Quarkus Roq Data

Quarkus Roq Data is a Quarkus extension that register JSON/YAML files as CDI beans, and available from Qute templates, in a type-safe way in your project.

Roq Data is already included as part of the Roq Static Site Generator extension io.quarkiverse.roq:quarkus-roq, Follow Standalone installation section to use it standalone.

Data Mapping

You can add JSON or YAML files to your project’s site/_data directory.

The data file can use .json, .yml, or .yaml extensions.
mountain.json
{
    "name": "Lhotse",
    "elevation": 8516
}

To use the data in your Java code, you have two options:

1. Use a Java class mapping.

Mountain.java
import io.quarkiverse.roq.data.runtime.annotations.DataMapping;

@DataMapping("mountain") (1)
public record Mountain(String name, Integer elevation) {}
1 The filename of the data file without the extension.

Then inject the Mountain record into a resource class.

Resource.java
import jakarta.inject.Inject;
import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;

@Path("/site")
public class Resource {

    @Inject
    Mountain mountain;

    @GET
    public String getMountain() {
        return mountain.toString();
    }
}

Access the resource using the following URL: http://localhost:8080/site. The output should be Quarkus Site - Quarkus Site generated by Roq.

2. Use JsonObject dynamic mapping

It is also possible to directly access the data without having a class mapping. In this case you can inject a named io.vertx.core.json.JsonObject in your code:

Resource.java
import jakarta.inject.Inject;
import jakarta.inject.Named;import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;

@Path("/site")
public class Resource {

    @Inject
    @Named("mountain") (1)
    JsonObject mountain;

    @GET
    public String getMountain() {
        return mountain.toString();
    }
}
1 The filename of the data file without the extension.

Mapping data file as a array

If your data file root element is an array.

mountains.json
[
    {
        "name": "Lhotse",
        "elevation": 8516
    },
    {
        "name": "Everest",
        "elevation": 8849
    }
]

You also have two options to map it.

1. Use a parent Java class mapping.

You could create a parent record as shown below:

Mountains.java
import java.util.List;
import io.quarkiverse.roq.data.runtime.annotations.DataMapping;

@DataMapping(value = "mountains", parentArray = true) (1)
public record Mountains(List<Mountain> list) { (2)

}
1 The parentArray attribute is set to true to indicate that the root element of the data file is an array.
2 The class aimed to map the data file must have a constructor that accepts a single parameter of type List<T>, where T is the type of the elements in the array.
The class annotated with @DataMapping(parentArray=true) must have a constructor that accepts a single parameter of type List<T>, where T is the type of the elements in the array.

With the above configuration, the Mountains record will have a list of Mountain records and can be injected via CDI.

2. Use JsonArray dynamic mapping

It is also possible to directly access the data without having a class mapping. In this case you can inject a named io.vertx.core.json.JsonArray in your code:

Resource.java
import jakarta.inject.Inject;
import jakarta.inject.Named;import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;

@Path("/site")
public class Resource {

    @Inject
    @Named("mountains") (1)
    JsonArray mountains;

    @GET
    public String getMountains() {
        return mountains.toString();
    }
}
1 The filename of the data file without the extension.

From a Qute template

Since generated data beans are named, it is possible to access them from any Qute template:

{#for mountain in cdi:mountains}
  <li>{mountains.name}: {mountains.elevation}</li> (1)
{/for}
1 A Value Resolver already exists for JsonObject allowing you to directly access attributes.
For type-safety, use a @DataMapping bean instead and access it using the Qute cdi namespace.

Standalone installation

It is included as part of the Roq Static Site Generator extension io.quarkiverse.roq:quarkus-roq. You can also use it standalone.

If you want to use this extension standalone, you need to add the io.quarkiverse.roq:quarkus-roq-data extension first to your build file.

For instance, with Maven, add the following dependency to your POM file:

<dependency>
    <groupId>io.quarkiverse.roq</groupId>
    <artifactId>quarkus-roq-data</artifactId>
    <version>0.0.8</version>
</dependency>

Extension Configuration Reference

Configuration property fixed at build time - All other configuration properties are overridable at runtime

Configuration property

Type

Default

The location of the Roq data files relative to the quarkus.roq.dir.

Environment variable: QUARKUS_ROQ_DATA_DIR

string

_data

Whether to enforce the use of a bean for each data file.
With this option enabled, when a record is annotated with DataMapping, a bean will be created and populated with the data from the file.

Environment variable: QUARKUS_ROQ_DATA_ENFORCE_BEAN

boolean

false