Asynchronous Programming and Promise Patterns in Backend Systems
This article introduces the concepts of synchronous versus asynchronous calls, explains the challenges of RPC services in large-scale systems, and provides detailed guidance on using polling, callbacks, futures, and CompletableFuture in Java to implement efficient, non‑blocking backend architectures with practical code examples.
In large, complex backend systems, services often rely on synchronous RPC calls that block CPU resources, leading to performance bottlenecks. Adopting asynchronous programming allows the CPU to be fully utilized by decoupling request handling from response processing.
1. Synchronous vs Asynchronous
Synchronous calls wait for the callee to finish before returning control, while asynchronous calls return immediately and let the caller retrieve results later via polling or callbacks.
2. Asynchronous RPC
Asynchronous RPC enables the client and server to handle I/O using non‑blocking mechanisms, reducing the number of threads needed for high throughput.
Polling
The caller repeatedly checks if a Future is done:
Future<Void> f = callee.asyncCall(param);
while (true) {
if (f.isDone()) break;
// do other work or sleep
}Callback
The callee invokes a user‑provided callback once the operation completes:
callee.asyncCall(param, new AsyncHandler<Response<Message>>() {
@Override
public void handleResponse(Response<Message> response) {
// process response
}
});3. Promise‑style APIs
Promises (e.g., CompletableFuture or Guava's ListenableFuture) represent a value that will be available later and can be composed without nesting callbacks.
Creating a Promise
CompletableFuture<String> asyncCall(String msg) {
CompletableFuture<String> promise = new CompletableFuture<>();
try {
callee.asyncCall(msg, new Callback<String>() {
public void onSuccess(String r) { promise.complete(r); }
public void onFail(Throwable t) { promise.completeExceptionally(t); }
});
} catch (Throwable e) { promise.completeExceptionally(e); }
return promise;
}Composing Promises
Serial composition using thenCompose:
CompletableFuture<Result4> promise4 = rpc1.call(input)
.thenCompose(r1 -> rpc2.call(r1))
.thenCompose(r2 -> rpc3.call(r2))
.thenCompose(r3 -> rpc4.call(r3));Parallel composition using allOf (or Guava's Futures.allAsList):
List<CompletableFuture<Result>> futures = List.of(f1, f2, f3);
CompletableFuture<Void> all = CompletableFuture.allOf(futures.toArray(new CompletableFuture[0]));Error Handling
Common error handling with exceptionally (or Guava's Futures.catching):
ListenableFuture<Integer> fetch = ...;
ListenableFuture<Integer> safe = Futures.catching(
fetch, FetchException.class,
e -> 0,
MoreExecutors.directExecutor());Or with CompletableFuture:
CompletableFuture<Integer> safe = fetch.exceptionally(e -> 0);Recovery and Timeout
Retry logic can be expressed by re‑dispatching the command when a recoverable exception occurs, using an AtomicInteger to track remaining attempts.
if (cause instanceof RecoverableException && leftTries.getAndDecrement() > 0) {
CompletableFuture<V> next = loadbalance.selectHandler().dispatch(new Command<V>(...));
return next.handle((v, err) -> err).thenCompose(err -> fallback.apply(next, err));
}Timeouts are handled by the standard Future.get(timeout, TimeUnit) method, optionally cancelling the pending operation.
try {
Result r = promise.get(1, TimeUnit.SECONDS);
} catch (TimeoutException e) {
promise.cancel(false);
}4. Practical Recommendations
Callbacks should be lightweight and non‑blocking; heavy work must be offloaded to dedicated executors to avoid stalling internal I/O threads. Use thenAcceptAsync with a custom executor for such cases.
Overall, asynchronous programming with Promise‑style APIs simplifies complex service orchestration, improves resource utilization, and provides clearer error handling compared to traditional callback‑heavy designs.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
JD Tech
Official JD technology sharing platform. All the cutting‑edge JD tech, innovative insights, and open‑source solutions you’re looking for, all in one place.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
