This page installs the Vidocq CLI, scaffolds a REST application, builds it with plain Maven, and serves a first endpoint — every command below is tested end-to-end against the released 0.2.x artifacts on Maven Central. If you prefer not to use the CLI, jump to the manual annex.

Prerequisites

  • Java 25 (Temurin recommended) — check with java -version

  • Maven 3.9+ — check with mvn -version

With SDKMAN!: sdk install java 25-tem && sdk install maven.

Step 1 — Install the CLI

curl -fsSL https://vidocq.dev/install.sh | sh

On Windows (PowerShell):

irm https://vidocq.dev/install.ps1 | iex

The script downloads the latest released CLI from Maven Central into ~/.vidocq/cli and puts a vidocq launcher on your PATH. Verify:

$ vidocq version
Vidocq CLI 0.2.1
No installer needed? Download vidocq-runtime-cli-<version>-cli.zip from Maven Central, unzip it anywhere, and add its bin/ directory to your PATH.

Step 2 — Scaffold a project

vidocq create --name todo --group-id com.acme --extension cassini-rest
cd todo

--extension cassini-rest (short: -x) enables Jakarta REST — it transitively brings the Chappe HTTP server, CDI (Vauban) and JSON-B (Champollion). The generated project is a standard JPMS Maven project:

todo/
  pom.xml                      (1)
  src/main/java/
    module-info.java           (2)
    com/acme/todo/TodoApp.java (3)
  src/main/resources/
    vidocq.properties          (4)
1 Inherits io.vidocq.runtime:vidocq-runtime-parent:0.2.0 and wires the vidocq-runtime-maven-plugin so mvn package produces a runnable distribution.
2 Module descriptor, pre-filled with the requires/opens a REST app needs.
3 The entry point — boots the runtime with VidocqBootstrap.
4 MicroProfile-style configuration (vidocq.http.port=8080, …).
Run vidocq extension list --available to see all first-party extensions, and vidocq help create for the options (--package, --parent-version, …).

Step 3 — Write your first resource

Create src/main/java/com/acme/todo/HelloResource.java:

package com.acme.todo;

import jakarta.enterprise.context.ApplicationScoped;
import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;
import jakarta.ws.rs.Produces;
import jakarta.ws.rs.core.MediaType;

@Path("/hello")
@ApplicationScoped
public class HelloResource {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String hello() {
        return "Hello from Vidocq!";
    }
}

No further wiring: the Cassini annotation processor generates the dispatch adapter at compile time — no runtime reflection.

Step 4 — Build and run

mvn package
sh target/todo-0.2.0/bin/todo.sh

mvn package compiles, runs the code generators, and assembles a standalone distribution under target/todo-0.2.0/ (launchers in bin/, module path in lib/). In another terminal:

$ curl http://localhost:8080/hello
Hello from Vidocq!

The runtime boots in well under a second — the log line to look for:

INFOS: Vidocq - Started in 90.940 ms (process running for 135 ms)

Step 5 — Dev mode

mvn vidocq:dev

Dev mode launches the application on its module path and watches your sources. It uses the vidocq.mainModule / vidocq.mainClass properties already set in the generated pom.

vidocq dev and vidocq start (the CLI commands, as opposed to the Maven goal) boot the runtime from the CLI’s own module path and therefore do not see the extensions declared in your pom. Prefer mvn vidocq:dev and the packaged launcher for extension-based apps.

Step 6 — Add extensions as you grow

vidocq extension list --available
vidocq extension add knock-health
mvn package

extension add edits your pom.xml with the correct coordinates. See Usage for the per-extension configuration keys, and the examples tour for a full REST + persistence application (Mansart Data + H2).

Step 7 — Package for production

vidocq build jlink    # self-contained runtime image (no local java needed)
vidocq build docker   # container image

See Usage for jlink/jpackage/Docker options and AOT notes.

Annex — Without the CLI

The CLI is a convenience, not a requirement. The project above is plain Maven — here is the complete, copy-pasteable equivalent.

pom.xml:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <parent>
        <groupId>io.vidocq.runtime</groupId>
        <artifactId>vidocq-runtime-parent</artifactId>
        <version>0.2.0</version>
        <relativePath/>
    </parent>

    <groupId>com.acme</groupId>
    <artifactId>todo</artifactId>
    <name>todo</name>

    <properties>
        <vidocq.mainModule>com.acme.todo</vidocq.mainModule>
        <vidocq.mainClass>com.acme.todo.TodoApp</vidocq.mainClass>
    </properties>

    <dependencies>
        <dependency>
            <groupId>io.vidocq.runtime</groupId>
            <artifactId>vidocq-runtime-core</artifactId>
            <version>0.2.0</version>
        </dependency>
        <dependency>
            <groupId>io.vidocq.runtime.extensions.jakartaee.core</groupId>
            <artifactId>vidocq-runtime-cassini-rest-extension</artifactId>
            <version>0.2.0</version>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>io.vidocq.runtime</groupId>
                <artifactId>vidocq-runtime-maven-plugin</artifactId>
                <configuration>
                    <jvmArgs>-Dfile.encoding=UTF-8</jvmArgs>
                </configuration>
                <executions>
                    <execution>
                        <goals>
                            <goal>package</goal>
                        </goals>
                        <configuration>
                            <mainClass>${vidocq.mainModule}/${vidocq.mainClass}</mainClass>
                        </configuration>
                    </execution>
                </executions>
            </plugin>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <configuration>
                    <annotationProcessorPaths combine.children="append">
                        <path>
                            <groupId>io.vidocq.runtime.extensions.jakartaee.core</groupId>
                            <artifactId>vidocq-runtime-cassini-rest-extension-codegen</artifactId>
                            <version>0.2.0</version>
                            <type>pom</type>
                        </path>
                    </annotationProcessorPaths>
                </configuration>
            </plugin>
        </plugins>
    </build>
</project>
Dependency versions are pinned on purpose: the released parent’s dependencyManagement uses ${project.version}, so an app relying on it must inherit the parent’s version. The two vidocq-runtime-maven-plugin configuration blocks work around known 0.2.0 issues (fixed in the next release).

src/main/java/module-info.java:

module com.acme.todo {
    // APT-generated $$CassiniAdapter classes import @Generated (SOURCE retention).
    requires static java.compiler;

    requires jakarta.cdi;
    requires jakarta.inject;
    requires jakarta.ws.rs;
    requires jakarta.json.bind;

    requires io.vidocq.runtime.core;
    requires io.vidocq.runtime.extensions.jakartaee.core.cassini;
    requires io.vidocq.cassini.api;

    // JAX-RS and JSON-B reflect on resource classes and payload types.
    opens com.acme.todo;
}

This opens works because the resources live in the same module as the main class. In a multi-module application (e.g. hexagonal, resources in their own Java module), the module system only lets a module open packages it owns: the opens must move into the module that contains the classes, and the runtime module scans it with <scanDependencies>. See Usage — Multi-module applications.

src/main/java/com/acme/todo/TodoApp.java:

package com.acme.todo;

import io.vidocq.runtime.core.VidocqBootstrap;

public final class TodoApp {

    public static void main(String[] args) {
        VidocqBootstrap.create()
                .configure()
                .start()
                .awaitShutdown();
    }
}

src/main/resources/vidocq.properties:

# Vidocq application configuration
vidocq.http.port=8080

Then add the HelloResource from Step 3 and continue from Step 4 (mvn package) — the flow is identical.

Next steps