Skip to content

Getting Started

Prerequisites

  • Java 21 or later and Spring Boot 4.1.

  • An agent you can run. Spring AI ACP Harness Client (SAAHC) does not package agent binaries. For the compiled adapters:

    • Goose: the goose CLI on the PATH, or GOOSE_CLI_PATH pointing at it. Verified against goose 1.57.0.
    • Codex: Node.js with npx. The adapter runs npx -y @agentclientprotocol/codex-acp@2.5.0, so the first start downloads it. CODEX_ACP_CLI_PATH names a local codex-acp to run instead.
    • OpenCode: the opencode CLI on the PATH, or OPENCODE_CLI_PATH. Verified against opencode 2.2.4.
    • Registry agents: nothing pre-installed; the agent is downloaded and checksum-verified. Agents distributed through npm or PyPI need npx or uvx.
  • Model credentials, either already configured in the agent itself (for example goose configure or codex login) or given to SAAHC through spring.ai.acp.harness.provider (see Models and Providers).

Add the dependency

Releases are on Maven Central. Add one runtime starter:

<dependencies>
    <dependency>
        <groupId>org.springaicommunity</groupId>
        <artifactId>spring-ai-acp-harness-client-boot-starter-goose</artifactId>
        <version>0.7.0</version>
    </dependency>
</dependencies>
repositories {
    mavenCentral()
}

dependencies {
    implementation("org.springaicommunity:spring-ai-acp-harness-client-boot-starter-goose:0.7.0")
}

Replace -goose with -codex, -opencode or -registry for another agent. No @Enable… annotation or bean definition is needed.

Configure

src/main/resources/application.yaml
spring:
  ai:
    acp:
      harness:
        runtime: goose                  # optional while goose is the only adapter on the classpath
        workspace: ${AGENT_WORKSPACE:./workspace}   # the agent's working directory; must exist
        timeout: 5m                     # longest a single turn may take

The workspace is the agent's working directory (its ACP session cwd). It is also where the agent looks for AGENTS.md and where skills are installed, so most of this guide comes back to it. A relative path is resolved against the JVM's working directory; left unset, the JVM's working directory itself is used. It must be an existing directory.

Send a prompt

@SpringBootApplication
public class ReviewApplication {

    public static void main(String[] args) {
        SpringApplication.run(ReviewApplication.class, args);
    }

    @Bean
    ApplicationRunner demo(AcpHarnessClient acpHarnessClient) {
        return args -> System.out.println(
                acpHarnessClient.prompt("Summarize what is in this directory").call().content());
    }
}

AcpHarnessClient is a thread-safe singleton. The agent process is started on the first prompt, not at context refresh: an application whose agent is misconfigured still starts, and reports the problem the first time it is used. The process is stopped when the context closes.

Tip

The repository's samples/smoke-app has all three adapters and the registry on its classpath. After ./mvnw install in the SAAHC checkout, run it against each agent in turn:

./mvnw -pl samples/smoke-app spring-boot:run
./mvnw -pl samples/smoke-app spring-boot:run -Dspring-boot.run.arguments=--spring.ai.acp.harness.runtime=codex
./mvnw -pl samples/smoke-app spring-boot:run -Dspring-boot.run.arguments=--spring.ai.acp.harness.runtime=opencode
./mvnw -pl samples/smoke-app spring-boot:run -Dspring-boot.run.arguments=--spring.ai.acp.harness.runtime=gemini