From spring
Implement Spring Cloud distributed-system building blocks for ConfigData integration, refresh-aware configuration, service discovery, load-balanced downstream calls, and circuit-breaker boundaries. Use this skill when implementing Spring Cloud distributed-system building blocks such as ConfigData integration, refresh-aware configuration, service discovery, load-balanced downstream calls, circuit-breaker boundaries, and release-train-aligned dependency management.
npx claudepluginhub ririnto/sinon --plugin springThis skill uses the workspace's default tool permissions.
Use this skill when implementing Spring Cloud distributed-system building blocks such as ConfigData integration, refresh-aware configuration, service discovery, load-balanced downstream calls, circuit-breaker boundaries, and release-train-aligned dependency management.
Mandates invoking relevant skills via tools before any response in coding sessions. Covers access, priorities, and adaptations for Claude Code, Copilot CLI, Gemini CLI.
Share bugs, ideas, or general feedback.
Use this skill when implementing Spring Cloud distributed-system building blocks such as ConfigData integration, refresh-aware configuration, service discovery, load-balanced downstream calls, circuit-breaker boundaries, and release-train-aligned dependency management.
The current Boot 4.x Spring Cloud release-train line is 2025.1.1 (Oakwood). Spring Cloud 2025.0.2 is a parallel Boot 3.5.x line, not a newer replacement, so the common path in this skill stays anchored to 2025.1.1 unless the project is intentionally on the 3.5.x generation.
Use spring-cloud for release-train-aligned distributed application wiring, external configuration through ConfigData, refresh-aware configuration, service discovery, load-balanced downstream calls, and resilience patterns.
spring-cloud-data-flow for SCDF stream and task orchestration.| Surface | Start here when | Open a reference when |
|---|---|---|
| ConfigData client | the service needs externalized configuration through ConfigData | Vault-backed config is the real blocker in references/cloud-vault-config.md or Kubernetes-backed config is the blocker in references/kubernetes-config.md |
| Refresh-aware configuration | one bean must rebind after refresh | distributed refresh propagation is the blocker in references/bus-refresh.md |
| Service discovery and load-balanced clients | one service calls another by logical service id | Kubernetes-backed discovery is the blocker in references/kubernetes-discovery.md or declarative clients are clearer in references/openfeign-clients.md |
| Circuit-breaker boundary | one remote call needs resilience | gateway routing is the real boundary in references/gateway-routing.md |
| Contract verification | provider-consumer compatibility is the real job | open references/contract-testing.md |
| Stream binders | the service actually publishes to or consumes from a broker | open references/stream-binders.md |
| Function catalog | the task is specifically about function beans or composition | open references/function-catalog.md |
The ordinary Spring Cloud job is:
Import the Spring Cloud BOM once and keep Spring Cloud modules versionless underneath it.
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>2025.1.1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
| Need | Starter or artifact |
|---|---|
| ConfigData client import | spring-cloud-starter-config |
| Service discovery client | the discovery implementation starter used by the platform |
Load-balanced RestClient or RestTemplate | spring-cloud-starter-loadbalancer |
| Circuit-breaker boundary with Resilience4j | spring-cloud-starter-circuitbreaker-resilience4j |
| Edge routing | add the Gateway starter from references/gateway-routing.md |
| Declarative HTTP clients | add the OpenFeign starter from references/openfeign-clients.md |
| Broker-backed event transport | add the binder starter from references/stream-binders.md |
| Distributed refresh propagation | add the Bus transport starter from references/bus-refresh.md |
| Contract verification | add the contract plugin and test support from references/contract-testing.md |
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-circuitbreaker-resilience4j</artifactId>
</dependency>
</dependencies>
Keep the discovery implementation starter, Gateway starter, OpenFeign starter, and bus or binder transports out of the common path unless the service truly needs them.
./mvnw test -Dtest=InventoryGatewayIntegrationTests
./gradlew test --tests InventoryGatewayIntegrationTests
Requires spring-cloud-starter-config.
spring:
application:
name: catalog-service
config:
import: optional:configserver:http://localhost:8888
Use optional: only when startup may continue without the config server. If startup must stop when remote config is unavailable, keep the import explicit and use fail-fast semantics in the backend-specific branch.
@RefreshScope
@Component
@ConfigurationProperties("catalog")
class CatalogProperties {
private String region;
public String getRegion() {
return this.region;
}
public void setRegion(String region) {
this.region = region;
}
}
Use @RefreshScope only for beans that must rebind after a config refresh rather than for ordinary immutable wiring.
Requires the discovery implementation starter used by the platform.
@SpringBootApplication
@EnableDiscoveryClient
class CatalogApplication {
}
Discovery can auto-configure when a supported implementation is on the classpath, but explicit enablement is still useful when the distributed boundary must stay obvious in shared code.
Requires spring-cloud-starter-loadbalancer.
@Configuration
class ClientConfiguration {
@Bean
@LoadBalanced
RestClient.Builder restClientBuilder() {
return RestClient.builder();
}
}
Use the logical service id as the remote target boundary and let the load balancer resolve concrete instances at runtime.
spring:
cloud:
compatibility-verifier:
enabled: true
Keep compatibility verification enabled unless the platform has a deliberate reason to override the release-train check.
Requires spring-cloud-starter-circuitbreaker-resilience4j.
@Bean
Customizer<ReactiveResilience4JCircuitBreakerFactory> defaultCustomizer() {
return factory -> factory.configureDefault(id -> new Resilience4JConfigBuilder(id).circuitBreakerConfig(CircuitBreakerConfig.ofDefaults()).build());
}
Put retries or circuit breakers only around genuine remote call boundaries. Do not treat resilience as a global default for local method calls.
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>2025.1.1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
</dependencies>
spring:
application:
name: catalog-service
config:
import: optional:configserver:http://localhost:8888
@SpringBootApplication
@EnableDiscoveryClient
class CatalogApplication {
}
@Configuration
class ClientConfiguration {
@Bean
@LoadBalanced
RestClient.Builder restClientBuilder() {
return RestClient.builder();
}
}
@Service
class InventoryGateway {
private final RestClient restClient;
InventoryGateway(RestClient.Builder builder) {
this.restClient = builder.baseUrl("http://inventory-service").build();
}
ItemDto find(String sku) {
return this.restClient.get().uri("/api/items/{sku}", sku).retrieve().body(ItemDto.class);
}
}
@SpringBootTest
class InventoryGatewayIntegrationTests {
@Autowired
InventoryGateway gateway;
@Test
void logicalServiceIdCallReturnsItem() {
ItemDto item = gateway.find("sku-1");
assertAll(
() -> assertNotNull(item),
() -> assertEquals("sku-1", item.sku())
);
}
}
spring.application.name and discovery ids)catalog-service
inventory-service
spring.config.import)optional:configserver:http://localhost:8888
vault://secret/catalog
kubernetes:
lb://catalog-service
http://inventory-service
Use these only when the task moves beyond the ordinary config, refresh, discovery, and downstream-client path.
RestClient code.