DEV Community

KevinTen
KevinTen

Posted on

Capa-Java: Why Sidecar Isn't Always the Answer for Hybrid Cloud Java

Capa-Java: Why Sidecar Isn't Always the Answer for Hybrid Cloud Java

Honestly, I've been doing Java backend development for over a decade, and when I first heard about "hybrid cloud architecture," I'll admit I was pretty skeptical. It sounded great in conference talks — "write once, run anywhere," "multi-cloud strategy reduces cost," all that buzzwords. But when you actually sit down to write the code? Man, it's a mess. Every cloud provider has their own API, config centers don't talk to each other, message queues need adapters, and deploying to a new cloud means rewriting half your code. Sound familiar?

Today I want to talk about an open source project I've been using in production for three years now — Capa-Java, a multi-runtime SDK for hybrid cloud built on the Mecha architecture. I've got three years of real production mileage on this thing, so I can give you the real deal — pros, cons, code examples, everything. If you're working on hybrid cloud stuff right now, maybe this saves you some of the headaches I went through.

What Is Capa-Java, And What Problem Does It Solve?

Let me start simple. Capa-Java is a multi-runtime SDK specifically built for hybrid cloud scenarios. The core idea is "Unified API, decoupled infrastructure".

In plain English: You write your business code once using Capa's API, and you don't need to care if you're running on Alibaba Cloud, AWS, Tencent Cloud, whatever. Capa handles the infrastructure adaptation under the hood through SPI plugins. Change cloud providers? You don't touch your business logic — just swap the plugin and you're done.

Sounds familiar, right? This isn't exactly a new idea. Service Mesh, Dapr, Layotto — all these projects are trying to decouple applications from infrastructure. So what's different about Capa compared to Dapr?

I couldn't really see the difference at first either, but after using it for a while, it clicked:

  • Dapr/Layotto go with the Sidecar pattern — your app talks to a local sidecar over the network
  • Capa-Java puts everything right in the SDK — in-process calls, no extra network hops

That's really it. If you're into the Sidecar approach, Dapr is great. If you don't want the extra network hop and you want something lightweight, Capa's SDK approach fits really well.

Code Example: Let's See How It Actually Works

Enough talking — let's look at some actual code. It's honestly way simpler than you might think.

Here's how you make an RPC call. Doesn't matter if the underlying RPC is Dubbo, REST, or whatever the cloud provider uses — it's all the same API:

// Build the RPC client once — your whole app only needs one instance
CapaRpcClient client = new CapaRpcClientBuilder()
    .build();

// Invoke the remote method — automatically adapts to the underlying cloud platform
Mono<String> result = client.invokeMethod(
    "order-service",  // Target service ID
    "createOrder",     // Method name
    orderRequest,      // Request payload
    HttpExtension.POST,
    null,
    TypeRef.STRING
);

// Get the response
String response = result.block();
System.out.println(response);
Enter fullscreen mode Exit fullscreen mode

Pretty straightforward, right? Now what about configuration? Same thing — whether you're using Nacos, AWS Parameter Store, or Alibaba Cloud Config Center, the code doesn't change:

// Subscribe to configuration changes — automatically adapts to the underlying config center
ConfigurationClient client = new ConfigurationClientBuilder()
    .build();

// Get the current configuration
Mono<Configuration> config = client.getConfiguration("app.config");
config.subscribe(cfg -> {
    System.out.println("Config updated: " + cfg.getValue("timeout"));
});
Enter fullscreen mode Exit fullscreen mode

See the pattern? Unified API across all infrastructure providers. I remember when I first used this, I was honestly shocked how simple it was. All that complexity just disappears from your business code.

Pub/Sub works the same way with a consistent API:

// Create the Pub/Sub client
PubSubClient pubSubClient = new PubSubClientBuilder()
    .build();

// Publish a message
pubSubClient.publishMessage(
    "order-events",  // Topic name
    new PubSubMessage().setText("order created")
).subscribe();

// Subscribe to messages
pubSubClient.subscribe(
    "order-events",
    message -> {
        System.out.println("Received: " + message.getText());
        return AckStatus.SUCCESS;
    }
);
Enter fullscreen mode Exit fullscreen mode

That's it. Three different infrastructure components, all using the same consistent API style. You don't have to learn a new API for every new cloud provider. Your muscle memory just works.

Three Years In: My Honest Takeaway

Okay, I've talked about the good stuff — now let's get real. I've been using this every day for three years, from the early open source days to now. I know the good, the bad, and the ugly.

The Good: It Actually Solves Real Problems

1. "Write Once, Run Anywhere" — It Actually Works

I'm not kidding here. My team has a core business system that runs simultaneously on our private cloud and AWS. The business code is exactly the same — we don't change a single line. We just swap the SPI plugins when deploying to different clouds and that's it.

Before Capa, deploying to a new cloud used to take us 3-5 days of code changes. Now it takes literally minutes. That's not a "nice to have" — that's a game-changer for productivity.

2. No Network Overhead — Performance Is Great

Since everything runs in-process with the SDK approach, you don't have that extra network hop to a Sidecar. We ran load tests and saw P99 latency drop by 20-30% compared to a Sidecar setup. For latency-sensitive applications, that's a big deal.

3. Java Ecosystem Friendly — Low Intrusion

If you're on the Java stack, especially with Spring Boot, getting started with Capa is stupid simple. Just add the starter dependency, configure your plugins, and you're good to go. You don't need to refactor your entire existing architecture. The intrusion is really low. Let's be real — nobody wants to rewrite their whole app just to adopt a new SDK, right?

4. SPI Plugin System Is Actually Flexible

Capa makes every cloud provider adaptation an SPI plugin. You only include the plugins you actually need — you don't get a ton of unnecessary dependencies pulled in. If you're targeting a cloud provider that isn't supported out of the box, writing your own plugin isn't hard. The interfaces are really well-defined.

The Bad: It's Not For Everyone, And That's Okay

So here's the thing — I learned this the hard way: No tool solves every problem. Capa has its flaws, and you need to know about them before you jump in.

1. The Ecosystem Isn't As Mature As Dapr

Let's be honest. Dapr is a CNCF project backed by Microsoft. It has a huge community and supports a ton of components out of the box. Capa is a community-driven open source project with a small core team. So the number of supported cloud providers and components is definitely smaller. The major ones (AWS, Alibaba Cloud, Tencent Cloud) all work great, but if you need something really niche, you'll probably have to write the adapter yourself.

2. The Documentation Is A Bit Light

I have to call this out — the getting started docs are great, you can be up and running in 10 minutes. But if you run into deeper issues, like performance tuning or custom plugin development, the docs don't have a lot of detail. You end up having to read the source code. The good news is the source code is actually pretty clean and well-organized, so it's not that bad — but it does take time.

3. Chinese-First Community — English Resources Are Scarce

Most of the maintainers are Chinese developers, so the primary documentation is in Chinese. The English docs exist but they don't get updated as often. If you're on an international team, that could be a problem. But if you're based in China or your team doesn't mind reading Chinese docs, it's totally fine.

4. SDK Pattern Means You Manage Versions Per App

This is just a fundamental trade-off between SDK and Sidecar. With Sidecar, you can upgrade once everywhere. With SDK, every application has to upgrade its own dependency. That's more work, but again — it's the trade-off you make for no network hop. Worth it for many teams, but not for everyone.

Who Should Use This? Who Should Skip It?

After three years of using this in production, I've got pretty clear rules of thumb for whether Capa is a good fit for you:

Go for it if:

  • You actually need hybrid/multi-cloud deployment — same code running on multiple clouds
  • You care about latency and want to avoid extra network hops
  • You're on the Java stack and don't want to deal with the operational complexity of Sidecar
  • You're a smaller team without the bandwidth to maintain a whole Sidecar infrastructure

Probably skip it if:

  • You're only running on one cloud — you don't need this abstraction at all
  • You're already all-in on Dapr/Sidecar and it's working for you — no reason to switch
  • You need a huge ecosystem of pre-built components — Dapr has you covered there
  • You're not on Java — Capa is primarily Java-focused, other language support is limited

Some Architecture Thoughts I Picked Up Along The Way

One of the things I appreciate about Capa is its design philosophy. There are a few ideas here that've really stuck with me after using it for three years.

1. Mecha Architecture: An Evolution From Service Mesh

Capa's Mecha architecture is basically an evolution of the Service Mesh idea. Service Mesh pulls capabilities out into a Sidecar, Mecha pulls capabilities down into the SDK. There's no right or wrong here — it's just different choices for different scenarios.

What I find interesting is that this idea actually lines up pretty well with what's happening in AI right now with Mixture of Experts (MoE) — split capabilities into separate components, load what you need, don't load what you don't. Keep it clean.

2. Standard API + SPI Plugins: A Timeless Combination

This design pattern has been around forever, but it's still one of the best. The standard API keeps your business code stable, the SPI plugins give you extensibility. No matter how the underlying infrastructure changes, your business code doesn't need to move.

I've come to believe that good architecture isn't about being able to handle every possible change up front. It's about isolating the change points — when something changes, only that something changes. Everything else stays the same. Capa nails this.

3. Perfect Is The Enemy Of Good

Can Capa really abstract away 100% of the differences between cloud providers? No, of course not. Different cloud providers have different capabilities, and that's just reality. But here's what Capa does do — it abstracts away 80% of the common stuff that you would've had to write yourself. That 80% saves you 80% of your time. The remaining 20% was always going to be cloud-specific anyway.

That's just good pragmatism. You don't need theoretical perfection. You need something that solves most people's most common problems. Capa does that.

Wrapping Up: My Advice For Anyone Considering This

Honestly, after three years, I'm still really grateful for this project. It solved a real problem my team was having and saved us countless hours of work.

If you're currently drowning in hybrid cloud adapter code, and you're on the Java stack, you should definitely check Capa-Java out. I think it'll help you. Here's where to find it:

Before you dive in though, let me leave you with a couple of pieces of advice I wish someone had told me three years ago:

  1. Do you actually need hybrid cloud? So many companies go "multi-cloud strategy" because it sounds good in board meetings, but they don't actually need it. Don't add complexity to your architecture just for the sake of it. If you're only running on one cloud, you don't need this.

  2. SDK vs Sidecar — pick based on your team size. Big team with dedicated ops people? Sidecar probably makes sense. Smaller team that wants to keep things simple and lightweight? Go SDK. That's really it. No need to overcomplicate the decision.

  3. Don't pick technology for the cool factor. Capa is great, but it's not the right choice for every situation. Be honest about your team's capabilities and your actual requirements.

I know hybrid cloud can be a real pain — I've been there. Hopefully this honest review helps you make a better decision than I did when I started.

What about you? Have you tried Capa-Java? Or are you still struggling with hybrid cloud adaptation madness? What's your go-to approach — SDK or Sidecar? I'd love to hear your experiences in the comments.

Top comments (0)