← Back to all projects

LEARN QUARKUS KUBERNETES NATIVE

In the era of Cloud Native and Serverless, the traditional Java Virtual Machine (JVM) faced a crisis. Its write once, run anywhere philosophy relied on heavy dynamic loading, JIT compilation, and huge memory footprints—attributes that lead to slow startups and high costs in pay-per-use environments like AWS Lambda or high-density Kubernetes clusters.

Learn Quarkus: From Zero to Kubernetes-Native Master

Goal: Deeply understand Quarkus—the “Supersonic Subatomic Java” framework. You will master the shift from traditional runtime-heavy Java to build-time optimized, Kubernetes-native applications. You’ll learn how GraalVM, ahead-of-time (AOT) compilation, and the Quarkus extension model work together to produce binaries that start in milliseconds and consume kilobytes of memory instead of megabytes.


Why Quarkus Matters

In the era of Cloud Native and Serverless, the traditional Java Virtual Machine (JVM) faced a crisis. Its “write once, run anywhere” philosophy relied on heavy dynamic loading, JIT compilation, and huge memory footprints—attributes that lead to slow startups and high costs in pay-per-use environments like AWS Lambda or high-density Kubernetes clusters.

Quarkus was created by Red Hat to fix this. By moving as much work as possible to the build phase, Quarkus eliminates the overhead of classpath scanning and dynamic proxy generation at runtime.

The Shift: Traditional vs. Quarkus

Traditional JVM Boot:

[Start] -> [Load Classes] -> [Scan Annotations] -> [Build Metadata] -> [Start Framework] -> [App Ready]
           ^--- Takes Seconds/Minutes and hundreds of MBs ---^

Quarkus Boot (Native):

[Start] -> [Pre-initialized Framework State] -> [App Ready]
           ^--- Takes Milliseconds and 10-20MB ---^

Core Concept Analysis

1. The Build-Time Boot (The Secret Sauce)

Quarkus performs “Augmentation” during the build. It resolves all dependency injection, parses configuration, and prepares the wiring before the application starts.

Build Time (Maven/Gradle)
┌─────────────────────────────────┐
│ 1. Scan Annotations             │
│ 2. Resolve Config               │
│ 3. Generate Proxies             │
│ 4. Initialize Frameworks        │
└────────────────┬────────────────┘
                 ▼
          Static Metadata
                 ▼
        Runtime Execution
┌─────────────────────────────────┐
│ 1. Load Pre-baked State         │
│ 2. Open Ports                   │
└─────────────────────────────────┘

2. GraalVM & Native Executables

While Quarkus runs great on the JVM (HotSpot), its true power is unlocked via GraalVM Native Image. This tool takes the pre-analyzed Java code and compiles it into a standalone OS-specific binary.

Java Bytecode (.class)
       │
       ▼
GraalVM AOT Compiler
 (Static Analysis)  <-- Quarkus provides "hints" to make this work
       │
       ▼
Native Machine Code (Binary)
(No JVM needed at runtime!)

3. Kubernetes-Native Extensions

Quarkus isn’t just fast; it’s designed for the Kubernetes environment. It automatically generates Dockerfiles, Kubernetes manifests, and supports features like Health Checks, Metrics, and ConfigMaps out of the box.


Concept Summary Table

Concept Cluster What You Need to Internalize
Build-Time Augmentation The framework does 90% of its work before the JAR is even created.
AOT Compilation Ahead-of-Time compilation translates Java to machine code, losing dynamic flexibility for extreme speed.
Dev Mode (Inner Loop) Quarkus provides near-instant “Hot Reload” that even works for configuration and database changes.
Reactive vs. Imperative Quarkus uses Mutiny to bridge the gap between blocking code and non-blocking event loops.
Extensions Model How Quarkus “teaches” traditional libraries (like Hibernate) to work in a native environment.

Deep Dive Reading by Concept

Foundation

Concept Book & Chapter
Quarkus Philosophy “Quarkus Cookbook” by Alex Soto & Jason Porter — Ch. 1: “Introduction to Quarkus”
Native Compilation “Understanding Quarkus” by Antonio Goncalves — Ch. 2: “Native Executables”

Cloud Native & Kubernetes

Concept Book & Chapter
K8s Integration “Quarkus: The Definitive Guide” by Ken Finnigan — Ch. 8: “Deploying to Kubernetes”
Observability “Quarkus Cookbook” by Alex Soto — Ch. 11: “Observability”

Essential Reading Order

  1. Foundation (Week 1):
    • Quarkus Cookbook Ch. 1-2 (The Basics & Dev Mode)
    • Understanding Quarkus Ch. 2 (GraalVM details)
  2. Data & Logic (Week 2):
    • Quarkus Cookbook Ch. 4 (Hibernate & Panache)
    • Quarkus Cookbook Ch. 7 (Reactive Programming with Mutiny)

Project 1: The Instant-Feedback Dev Loop (Hello Quarkus)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin, Scala
  • Coolness Level: Level 2: Practical but Forgettable
  • Business Potential: 1. The “Resume Gold”
  • Difficulty: Level 1: Beginner
  • Knowledge Area: Web Development / Developer Experience
  • Software or Tool: Quarkus Dev Mode, Maven/Gradle
  • Main Book: “Quarkus Cookbook” by Alex Soto & Jason Porter

What you’ll build: A simple RESTful API where you’ll experience Quarkus’s “Dev Mode.” You will change code, add new endpoints, and modify properties, seeing the results instantly without ever restarting the process.

Why it teaches Quarkus: It introduces the core developer experience. You’ll understand that Quarkus isn’t just about speed at runtime, but speed during development. You’ll learn how Quarkus handles the “Inner Loop” of development.

Core challenges you’ll face:

  • Understanding Dev Mode vs. JVM Mode → maps to How Quarkus monitors files
  • Adding dependencies dynamically → maps to Quarkus extension management
  • RESTEasy Reactive basics → maps to JAX-RS annotations

Key Concepts:

  • Hot Reload: “Quarkus Cookbook” Ch. 2 - Alex Soto
  • Quarkus Extensions: Quarkus Official Guide (extensions)

Difficulty: Beginner Time estimate: 1-2 hours Prerequisites: Basic Java knowledge, Maven or Gradle installed.


Real World Outcome

You will have a running REST API that you can modify in real-time. You’ll see the logs show “Hot replace total time: 0.Xs” whenever you hit a key.

Example Output:

$ ./mvnw quarkus:dev
...
Listening for transport dt_socket at address: 5005
QUARKUS 3.x.x started in 1.234s. Listening on: http://localhost:8080

# Now change a string in your Java file and refresh the browser
[INFO] Quarkus hot replace completed in 0.345s

The Core Question You’re Answering

“Why did Java developers accept 30-second restart times for 20 years, and how does Quarkus break that cycle?”

Before you write any code, sit with this question. Traditional Java frameworks re-scan everything on every start. Quarkus keeps the framework “warm” and only swaps the bits you changed.


Concepts You Must Understand First

Stop and research these before coding:

  1. JAX-RS (Jakarta RESTful Web Services)
    • What is @Path, @GET, and @Produces?
    • How does a resource class relate to an HTTP endpoint?
    • Book Reference: “Java EE 8 Recipe” Ch. 11 - Josh Juneau
  2. Quarkus Dev Mode
    • What happens when you press ‘r’ in the terminal?
    • How does Quarkus detect file changes?
    • Book Reference: “Quarkus Cookbook” Ch. 2 - Alex Soto

Questions to Guide Your Design

Before implementing, think through these:

  1. Resource Lifecycle
    • Are JAX-RS resources singletons by default in Quarkus?
    • How do you inject a service into a resource?
  2. Continuous Testing
    • Did you know Quarkus can run tests in the background as you code? How do you enable it?

Thinking Exercise

The Reflection Trap

Traditional frameworks use Reflection to find your annotations. This is slow. Quarkus avoids this at runtime.

@Path("/hello")
public class GreetingResource {
    @GET
    public String hello() { return "Hello!"; }
}

Questions while coding:

  • How would YOU find this class without scanning the whole classpath at runtime?
  • What if you could record the “location” of this class during build time?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is Quarkus Dev Mode, and how does it differ from JRebel or Spring Boot DevTools?”
  2. “Explain the ‘Inner Loop’ of development and why it matters.”
  3. “What is the default port for Quarkus Dev Mode’s debug window?”
  4. “How do you add an extension to a Quarkus project via the CLI?”
  5. “Does Quarkus restart the JVM during a hot reload?”

Hints in Layers

Hint 1: Initializing Use code.quarkus.io or the Quarkus CLI to bootstrap your project with quarkus-resteasy-reactive.

Hint 2: Running Use ./mvnw quarkus:dev. Don’t use java -jar.

Hint 3: Live Coding Open your resource file. Change the return string. Save. Refresh your browser immediately. Notice the log output.

Hint 4: Debugging Attach your IDE debugger to port 5005. It’s already waiting for you.


Books That Will Help

Topic Book Chapter
JAX-RS Basics “Java EE 8 Recipe” Ch. 11
Quarkus Dev Mode “Quarkus Cookbook” Ch. 2

Project 2: The Reactive Data Layer (PostgreSQL & Panache)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin
  • Coolness Level: Level 3: Genuinely Clever
  • Business Potential: 3. The “Service & Support” Model
  • Difficulty: Level 2: Intermediate
  • Knowledge Area: Databases / Persistence
  • Software or Tool: Hibernate Panache, PostgreSQL, Dev Services
  • Main Book: “Quarkus Cookbook” by Alex Soto & Jason Porter

What you’ll build: A “Task Manager” API that persists data to PostgreSQL using Hibernate Reactive with Panache. You will use “Dev Services,” meaning Quarkus will automatically start a Docker container for Postgres for you.

Why it teaches Quarkus: You’ll learn about Dev Services (Quarkus managing infrastructure) and Panache (a simplified layer over Hibernate). You’ll also encounter the Reactive side of Quarkus, understanding how to write non-blocking database code.

Core challenges you’ll face:

  • Working with Mutiny (Uni/Multi) → maps to Reactive programming patterns
  • Dev Services for Database → maps to Zero-config database setup
  • Active Record vs. Repository Pattern → maps to Panache design choices

Key Concepts:

  • Hibernate Reactive: “Quarkus Cookbook” Ch. 4 - Alex Soto
  • Mutiny (Reactive Streams): Mutiny Official Documentation

Difficulty: Intermediate Time estimate: 4-6 hours Prerequisites: Docker installed (for Dev Services), Project 1 completed.


Real World Outcome

You’ll have a running application that interacts with a database without you ever writing a connection string or starting a DB server manually.

Example Output:

# Quarkus starts Postgres in Docker automatically!
$ ./mvnw quarkus:dev
...
[INFO] Dev Services for PostgreSQL started.
...
$ curl -X POST -H "Content-Type: application/json" -d '{"title":"Learn Quarkus"}' http://localhost:8080/tasks
{"id":1, "title":"Learn Quarkus", "completed":false}

The Core Question You’re Answering

“How can we make database interaction non-blocking without making the code unreadable?”

Hibernate Reactive allows the event loop to handle other requests while waiting for the database, but it introduces Uni<T>. You need to understand why this is better than standard JDBC in a high-concurrency environment.


Concepts You Must Understand First

Stop and research these before coding:

  1. Active Record Pattern
    • How does it differ from the Repository pattern?
    • Why does Panache promote it?
    • Book Reference: “Patterns of Enterprise Application Architecture” - Martin Fowler
  2. Reactive Streams (Mutiny)
    • What is a Uni? What is a Multi?
    • What is the difference between “Subscribing” and just “Returning” a type?

Questions to Guide Your Design

Before implementing, think through these:

  1. Transaction Management
    • How do you handle transactions in a reactive environment? (Hint: @WithTransaction)
  2. Schema Generation
    • Should you let Quarkus generate your schema in production? (Hint: Flyway/Liquibase)

Thinking Exercise

The Blocking Thread Pool vs. The Event Loop

In standard Java (Spring/JEE), every request gets a thread. If that thread waits for DB, it’s “blocked.”

Request 1 -> [Thread A] -> [Wait for DB] -> (Blocked)
Request 2 -> [Thread B] -> [Wait for DB] -> (Blocked)

In Reactive Quarkus:

Request 1 -> [Event Loop] -> [Ask DB] -> [Next Request!]
DB Responds -> [Event Loop] -> [Resume Request 1]

Questions while coding:

  • If you use Thread.sleep() in a Reactive resource, what happens to the whole server?
  • Why is it dangerous to call a blocking library inside a Uni chain?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What are Quarkus Dev Services?”
  2. “Explain the difference between Hibernate ORM and Hibernate Reactive.”
  3. “What is Panache and how does it simplify persistence in Java?”
  4. “Why would you choose the Active Record pattern over the Repository pattern?”
  5. “What is Mutiny and why does Quarkus use it instead of RxJava or Project Reactor?”

Hints in Layers

Hint 1: Extension Add quarkus-hibernate-reactive-panache and quarkus-reactive-pg-client.

Hint 2: The Entity Extend PanacheEntity. You don’t need to define IDs or getters/setters (Quarkus generates them!).

Hint 3: The Resource Your methods should return Uni<List<Task>> or Uni<Response>. Use .chain() to link operations.

Hint 4: Dev Services As long as Docker is running, you don’t need to configure application.properties. Quarkus finds it!


Books That Will Help

Topic Book Chapter
Persistence Patterns “Patterns of Enterprise Application Architecture” Active Record
Hibernate Panache “Quarkus Cookbook” Ch. 4
Reactive Mutiny “Quarkus: The Definitive Guide” Ch. 6

Project 3: The Native Binary Factory (GraalVM)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: N/A (Focus on GraalVM)
  • Coolness Level: Level 5: Pure Magic (Super Cool)
  • Business Potential: 5. The “Industry Disruptor”
  • Difficulty: Level 3: Advanced
  • Knowledge Area: Compilation / Performance Engineering
  • Software or Tool: GraalVM, Mandrel, Docker
  • Main Book: “Understanding Quarkus” by Antonio Goncalves

What you’ll build: You will take your Task Manager from Project 2 and compile it into a Native Executable. You will then measure the memory usage (RSS) and startup time, comparing it against the JVM version.

Why it teaches Quarkus: This is the “Subatomic” part of Quarkus. You’ll understand the constraints of AOT compilation (no dynamic reflection, closed-world assumption) and why Quarkus extensions are necessary to bridge existing Java libraries to GraalVM.

Core challenges you’ll face:

  • Closed-World Assumption → maps to Why you can’t load classes at runtime
  • Native Build Resources → maps to High CPU/RAM requirements during build
  • Reflection Hints → maps to How Quarkus tells GraalVM about reflection

Key Concepts:

  • Ahead-of-Time (AOT) Compilation: “Understanding Quarkus” Ch. 2
  • SubstrateVM: GraalVM Documentation

Difficulty: Advanced (Build process is complex) Time estimate: 2-4 hours (depending on your machine’s speed) Prerequisites: Project 2 completed, GraalVM installed OR Docker (for containerized build).


Real World Outcome

You’ll have a single, self-contained binary file (around 30-50MB) that starts in less than 50ms and uses only ~20MB of RAM.

Example Output:

# Build the native image (this takes a few minutes)
$ ./mvnw package -Dnative

# Run the binary
$ ./target/task-manager-1.0.0-SNAPSHOT-runner

QUARKUS started in 0.018s. Listening on: http://localhost:8080

# Check memory
$ ps -o rss,command -p $(pgrep task-manager)
  RSS COMMAND
21456 ./target/task-manager-1.0.0-SNAPSHOT-runner

The Core Question You’re Answering

“Why is native compilation so hard for Java, and how does Quarkus make it look easy?”

Java was built for dynamic environments. AOT requires everything to be known at build time. Quarkus uses its build-time augmentation to feed GraalVM exactly what it needs to know.


Concepts You Must Understand First

Stop and research these before coding:

  1. Static vs. Dynamic Analysis
    • Why can’t GraalVM handle Class.forName(someVariable) easily?
    • What is the “Closed World” assumption?
  2. RSS (Resident Set Size)
    • Why is RSS a better measure than Heap size for cloud billing?

Questions to Guide Your Design

Before implementing, think through these:

  1. Build Environment
    • Should you build native images on your local Mac/Windows or in a Linux container?
    • How do you handle OS-specific dependencies?
  2. Testing Native Images
    • How do you ensure the native binary behaves exactly like the JVM version? (Hint: @QuarkusIntegrationTest)

Thinking Exercise

The Reflection Paradox

In a native binary, there is no JVM to interpret strings as class names.

// Traditional Java
String className = "com.myapp.MyService";
Class<?> clazz = Class.forName(className); // This works in JVM

In Native Image, MyService might have been stripped by the compiler because it didn’t see any static references to it!

Questions while coding:

  • How does Quarkus know that your Panache Entity needs to be preserved even if no one calls its constructor directly?
  • What happens to System.getProperty() calls at native runtime?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “Explain the ‘Closed World Assumption’ in GraalVM.”
  2. “Why does a native binary start faster than a JVM JAR?”
  3. “What are the trade-offs of using native executables (AOT) vs JVM (JIT)?”
  4. “How does Quarkus help GraalVM with reflection and dynamic proxies?”
  5. “What is Mandrel and how does it relate to GraalVM?”

Hints in Layers

Hint 1: Build command Use -Dnative. If you don’t have GraalVM installed, use -Dquarkus.native.container-build=true (requires Docker).

Hint 2: Memory The build process is extremely memory-intensive. You might need to give Docker 8GB+ of RAM.

Hint 3: Errors If you get “Reflection not allowed” errors, it usually means a library you’re using isn’t “Quarkus-ready.” Use a Quarkus extension instead!

Hint 4: Profiling Compare the output of time ./target/...-runner vs time java -jar target/...-runner.jar.


Books That Will Help

Topic Book Chapter
Native Image “Understanding Quarkus” Ch. 2
GraalVM Internals “GraalVM Web Docs” Reference Manual

Project 4: The Configurable Cloud Service (MicroProfile Config)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin
  • Coolness Level: Level 1: Pure Corporate Snoozefest
  • Business Potential: 3. The “Service & Support” Model
  • Difficulty: Level 1: Beginner
  • Knowledge Area: Configuration / Cloud Architecture
  • Software or Tool: MicroProfile Config, Kubernetes ConfigMaps
  • Main Book: “Quarkus: The Definitive Guide” by Ken Finnigan

What you’ll build: A service that changes its behavior based on profiles (dev, test, prod) and external environment variables. You will implement a custom ConfigSource and learn how to override properties using Kubernetes ConfigMaps without rebuilding the image.

Why it teaches Quarkus: You’ll learn the Unified Configuration model. Quarkus merges configuration from application.properties, environment variables, and external sources at build-time AND runtime. You’ll learn which properties are “Fixed” (build-time) and which are “Overridable” (runtime).

Core challenges you’ll face:

  • Build-time vs Runtime Config → maps to Immutable vs Mutable settings
  • Profile Expression Syntax → maps to %prod.db.url
  • External Configuration → maps to ConfigMaps and Secrets integration

Key Concepts:

  • MicroProfile Config: Quarkus Documentation
  • Config Mapping: “Quarkus Cookbook” Ch. 3

Difficulty: Beginner Time estimate: 2-3 hours Prerequisites: Project 1 completed.


Real World Outcome

A service where you can change the “Maintenance Mode” status or “API Key” by simply changing an environment variable, without ever touching the code.

Example Output:

$ ./mvnw quarkus:dev -Dgreeting.message="Hello from CLI"
# The app now shows "Hello from CLI"

# On Kubernetes:
# kubectl create configmap my-config --from-literal=greeting.message="Hello K8s"
# The app (running in Pod) automatically picks up "Hello K8s"

The Core Question You’re Answering

“How do we keep the SAME binary across all environments while changing its behavior?”

In the Cloud Native world, the binary is immutable. Rebuilding for “production” is a sin. You must master how to inject values at the last possible second.


Concepts You Must Understand First

Stop and research these before coding:

  1. The 12-Factor App (Config)
    • Why should config be stored in the environment?
  2. MicroProfile Config API
    • @ConfigProperty vs ConfigProvider.getConfig().

Questions to Guide Your Design

Before implementing, think through these:

  1. Security
    • Where do you store database passwords? (ConfigMap vs Secret).
    • How does Quarkus handle encrypted properties?
  2. Validation
    • How do you ensure the app fails fast if a required configuration is missing? (Hint: @ConfigMapping with validation).

Thinking Exercise

The Config Hierarchy

Quarkus looks for config in many places. If a property is defined in both application.properties and an Environment Variable, which one wins?

Scenario:

  • application.properties: app.color=blue
  • export APP_COLOR=red
  • java -Dapp.color=green -jar app.jar

Questions while coding:

  • Which color will the app show?
  • Why is it important that “Environment Variables” usually override “Properties files”?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is the difference between build-time and runtime configuration in Quarkus?”
  2. “How do you define environment-specific properties in Quarkus?”
  3. “Explain the priority order of MicroProfile Config sources.”
  4. “What is a Quarkus profile and how do you activate it?”
  5. “How do you inject a configuration object instead of individual properties?”

Hints in Layers

Hint 1: Injection Use @ConfigProperty(name = "my.prop") String val;.

Hint 2: Profiles In application.properties, use %dev.my.prop=foo and %prod.my.prop=bar.

Hint 3: Mapping Use @ConfigMapping to group properties into a nice Java Interface. It’s much cleaner!

Hint 4: Env Vars Remember that my.prop becomes MY_PROP or QUARKUS_MY_PROP in environment variables.


Books That Will Help

Topic Book Chapter
Cloud Config “The 12-Factor App” III. Config
Quarkus Config “Quarkus Cookbook” Ch. 3

Project 5: The Resilient Service Mesh (Fault Tolerance)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin
  • Coolness Level: Level 3: Genuinely Clever
  • Business Potential: 4. The “Open Core” Infrastructure
  • Difficulty: Level 2: Intermediate
  • Knowledge Area: Distributed Systems / Reliability
  • Software or Tool: MicroProfile Fault Tolerance, SmallRye Fault Tolerance
  • Main Book: “Quarkus Cookbook” by Alex Soto & Jason Porter

What you’ll build: A service that calls an unreliable external API. You will implement Circuit Breakers, Timeouts, Retries, and Fallbacks to ensure your application remains stable even when its dependencies are failing.

Why it teaches Quarkus: In a Kubernetes cluster, network failures are inevitable. You’ll learn how Quarkus integrates the MicroProfile Fault Tolerance spec to handle these failures declaratively with annotations, and how it works seamlessly with both imperative and reactive code.

Core challenges you’ll face:

  • Tuning Circuit Breaker thresholds → maps to Managing error states
  • Handling Fallbacks → maps to Providing a degraded user experience
  • Async Fault Tolerance → maps to Combining @Asynchronous with @Retry

Key Concepts:

  • Circuit Breaker Pattern: Release It! by Michael Nygard
  • MicroProfile Fault Tolerance: Quarkus Guide (fault-tolerance)

Difficulty: Intermediate Time estimate: 3-5 hours Prerequisites: Project 1 completed.


Real World Outcome

A robust API that doesn’t hang when a downstream service is slow, but instead returns a cached or default value and “trips” the circuit to prevent further damage.

Example Output:

# External service is down
$ curl http://localhost:8080/weather
# Response is instant! (Fallback)
{"city":"Unknown", "temp": 0.0, "status":"Service Temporarily Unavailable"}

# In Logs:
[WARN] Circuit Breaker opened for weather-service

The Core Question You’re Answering

“How do we prevent a single slow service from bringing down the entire cluster?”

This is the cascading failure problem. If Service A waits for Service B, and Service B is slow, Service A’s threads fill up. You must learn to ‘fail fast’.


Concepts You Must Understand First

Stop and research these before coding:

  1. The Circuit Breaker Pattern
    • States: Closed, Open, Half-Open.
    • Why do we need Half-Open?
  2. Bulkhead Pattern
    • How does isolating resources (threads) prevent failure propagation?

Questions to Guide Your Design

Before implementing, think through these:

  1. Retry Strategy
    • Is it safe to retry a POST request? (Hint: Idempotency).
    • How many retries are too many?
  2. Metrics
    • How do you know if your circuit is open in production? (Hint: MicroProfile Metrics integration).

Thinking Exercise

The Fallback Logic

When a fallback is triggered, you have a choice:

  1. Return an error code (424 Failed Dependency).
  2. Return a default value.
  3. Return data from a local cache.

Questions while coding:

  • Which one is best for a Product Catalog?
  • Which one is best for a Payment Gateway?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is the difference between a Retry and a Fallback?”
  2. “Explain the three states of a Circuit Breaker.”
  3. “Why is it important to define Timeouts for every external call?”
  4. “How do @Bulkhead protect your application?”
  5. “What happens if a Fallback method throws an exception?”

Hints in Layers

Hint 1: Annotations Use @Retry, @Timeout, @CircuitBreaker, and @Fallback.

Hint 2: Fallback Method The fallback method must have the same signature (parameters and return type) as the original method.

Hint 3: Jitter When using @Retry, use jitter to prevent a ‘thundering herd’ of clients all retrying at the exact same millisecond.

Hint 4: Testing Use a tool like WireMock or a simple Quarkus resource with Thread.sleep() to simulate failures.


Books That Will Help

Topic Book Chapter
Resilience Patterns “Release It!” Ch. 5 (Stability Patterns)
MP Fault Tolerance “Quarkus Cookbook” Ch. 8

Project 6: Event-Driven Microservices (Kafka & Strimzi)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin
  • Coolness Level: Level 4: Hardcore Tech Flex
  • Business Potential: 4. The “Open Core” Infrastructure
  • Difficulty: Level 3: Advanced
  • Knowledge Area: Messaging / Event-Driven Design
  • Software or Tool: Apache Kafka, SmallRye Reactive Messaging, Dev Services
  • Main Book: “Quarkus: The Definitive Guide” by Ken Finnigan

What you’ll build: A system where one microservice (Orders) emits events to a Kafka topic, and another service (Inventory) consumes those events to update its state. You’ll use SmallRye Reactive Messaging to handle the stream of data.

Why it teaches Quarkus: You’ll master the Channel abstraction. Quarkus lets you decouple your business logic from the underlying broker (Kafka, RabbitMQ, AMQP). You’ll also see Dev Services in action again, as Quarkus will spin up a Kafka cluster (via Redpanda or Testcontainers) for you automatically.

Core challenges you’ll face:

  • Backpressure → maps to Handling faster producers than consumers
  • Serialization/Deserialization → maps to Avro or JSON schema management
  • Message Acknowledgment → maps to Ensuring at-least-once delivery

Key Concepts:

  • Reactive Messaging: SmallRye Documentation
  • Event-Driven Architecture: “Designing Data-Intensive Applications” by Martin Kleppmann

Difficulty: Advanced Time estimate: 6-8 hours Prerequisites: Project 2 (Reactive) completed.


Real World Outcome

An asynchronously coupled system that can handle huge bursts of traffic without the Order service ever waiting for the Inventory service.

Example Output:

# Order Service Logs
[INFO] Order #123 sent to 'orders' topic

# Inventory Service Logs (running in another terminal)
[INFO] Received Order #123. Reducing inventory for SKU 'ABC'

The Core Question You’re Answering

“How do we scale services independently when they need to talk to each other?”

Synchronous HTTP calls create a ‘distributed monolith’. Event-driven design with Kafka allows services to be truly independent and resilient to each other’s downtime.


Concepts You Must Understand First

Stop and research these before coding:

  1. Kafka Topics & Partitions
    • How does Kafka ensure message order?
    • What is a Consumer Group?
  2. Backpressure
    • What happens when a producer is 10x faster than a consumer?

Questions to Guide Your Design

Before implementing, think through these:

  1. Payload Format
    • Should you use JSON or Avro? (Hint: Avro is better for schema evolution).
    • How do you share the DTO (Data Transfer Object) between services?
  2. Acknowledgment
    • Should you acknowledge messages automatically or manually?

Thinking Exercise

The Dual Write Problem

You need to save an Order to the DB AND send an event to Kafka. What if the DB save succeeds but Kafka fails?

Questions while coding:

  • How does the Outbox Pattern solve this?
  • Can Quarkus help with the Outbox pattern? (Hint: Debezium extension).

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is SmallRye Reactive Messaging?”
  2. “Explain the concept of an @Incoming and @Outgoing channel.”
  3. “How do you handle backpressure in a Quarkus Kafka application?”
  4. “What is the role of Emitter in Reactive Messaging?”
  5. “How do Dev Services for Kafka work?”

Hints in Layers

Hint 1: Extension Add quarkus-smallrye-reactive-messaging-kafka.

Hint 2: Channels Use @Outgoing("orders-out") on a method that returns a Multi or uses an Emitter.

Hint 3: Mapping Map your channels to actual Kafka topics in application.properties using mp.messaging.outgoing.orders-out.topic=orders.

Hint 4: Testing Use @QuarkusTestResource(KafkaCompanionResource.class) for advanced Kafka testing.


Books That Will Help

Topic Book Chapter
Event Streams “Designing Data-Intensive Applications” Ch. 11
Quarkus Kafka “Quarkus Cookbook” Ch. 9

Project 7: The Serverless Function (Quarkus Funqy)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin
  • Coolness Level: Level 4: Hardcore Tech Flex
  • Business Potential: 2. The “Micro-SaaS / Pro Tool”
  • Difficulty: Level 2: Intermediate
  • Knowledge Area: Serverless / FaaS
  • Software or Tool: Quarkus Funqy, AWS Lambda, Knative
  • Main Book: “Quarkus Cookbook” by Alex Soto & Jason Porter

What you’ll build: A serverless function (e.g., an Image Resizer or a Calculator) that can be deployed to multiple cloud providers without changing the code. You will use Quarkus Funqy to write the business logic once and deploy it as an AWS Lambda.

Why it teaches Quarkus: You’ll see the power of Native Startup in a serverless context. Traditional Java Lambda functions suffer from “Cold Starts” (seconds of delay). Quarkus Native Lambda functions start in milliseconds. You’ll also learn about the Funqy portable API.

Core challenges you’ll face:

  • Portable Functions → maps to Abstracting cloud provider details
  • AWS Lambda Packaging → maps to SAM or CDK integration
  • Cold Start Measurement → maps to Benchmarking native vs JVM in the cloud

Key Concepts:

  • FaaS (Function as a Service): Knative / AWS Lambda docs
  • Quarkus Funqy: Quarkus Guide (funqy)

Difficulty: Intermediate Time estimate: 3-5 hours Prerequisites: Project 3 (Native) completed, AWS account (optional but recommended).


Real World Outcome

A function that costs $0 when not in use and wakes up instantly to process a request the moment it arrives.

Example Outcome:

# Invoke Lambda locally using SAM
$ sam local invoke MyFunction --event event.json

# Logs show:
START RequestId: ... Version: $LATEST
QUARKUS Funqy function executed in 12ms
END RequestId: ...

The Core Question You’re Answering

“Can Java finally be a first-class citizen in the Serverless world?”

Historically, Java was too slow for FaaS. With Quarkus Native, Java is now as fast (or faster) than Node.js and Python for startups, while retaining the power of the Java ecosystem.


Concepts You Must Understand First

Stop and research these before coding:

  1. The ‘Cold Start’ Problem
    • Why do FaaS providers spin down containers?
    • How does memory allocation affect CPU performance in AWS Lambda?
  2. Custom Runtimes
    • How does a native binary run on AWS Lambda? (Hint: provided runtime).

Questions to Guide Your Design

Before implementing, think through these:

  1. Statelessness
    • Can you store data in a global variable in a serverless function?
  2. Connectivity
    • How do you handle database connections in a function that might scale to 1000 instances in a second? (Hint: Connection pooling pitfalls).

Thinking Exercise

The Portable Function

Compare these two ways to write a function:

  1. public void handleRequest(S3Event event, Context context) (AWS Specific)
  2. @Funq public String process(MyData data) (Quarkus Funqy)

Questions while coding:

  • Why would you choose Funqy over the native AWS SDK?
  • What happens if you need to access the raw S3 event in Funqy?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is Quarkus Funqy?”
  2. “Why is native compilation critical for Serverless Java?”
  3. “How do you handle CloudEvents in Quarkus?”
  4. “Compare Quarkus Lambda vs standard AWS Java Lambda.”
  5. “What are the limitations of running Java as a native binary in Lambda?”

Hints in Layers

Hint 1: Extension Add quarkus-funqy-http (for local dev) and quarkus-funqy-amazon-lambda.

Hint 2: Function Definition Just use the @Funq annotation on a method. No interfaces needed!

Hint 3: Packaging When building for AWS, Quarkus generates a function.zip in your target folder.

Hint 4: Local Dev Run mvn quarkus:dev. You can test your function via HTTP locally even if it’s meant for Lambda!


Books That Will Help

Topic Book Chapter
Serverless Patterns “Cloud Native Patterns” Ch. 7
Quarkus Funqy “Quarkus Cookbook” Ch. 12

Project 8: Security with OIDC (Keycloak)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Kotlin
  • Coolness Level: Level 3: Genuinely Clever
  • Business Potential: 3. The “Service & Support” Model
  • Difficulty: Level 2: Intermediate
  • Knowledge Area: Security / Identity Management
  • Software or Tool: Keycloak, OIDC, Dev Services
  • Main Book: “Quarkus Cookbook” by Alex Soto & Jason Porter

What you’ll build: A secure API where endpoints are protected by Role-Based Access Control (RBAC). You will use Keycloak as the Identity Provider and learn how to configure Quarkus to validate JWT tokens.

Why it teaches Quarkus: You’ll learn how Quarkus simplifies Security via extensions. Instead of writing boilerplate security code, you’ll use annotations like @RolesAllowed. You’ll also use Dev Services for Keycloak, which automatically starts a Keycloak container and configures a realm for you.

Core challenges you’ll face:

  • JWT Validation → maps to Understanding public keys and issuers
  • Role Mapping → maps to Bridging Identity Provider roles to Java roles
  • Security Scopes → maps to Protecting specific HTTP methods

Key Concepts:

  • OpenID Connect (OIDC): OIDC Official Specs
  • JWT (JSON Web Tokens): jwt.io

Difficulty: Intermediate Time estimate: 4-6 hours Prerequisites: Project 1 completed, Docker installed.


Real World Outcome

A system where GET /tasks is public, but POST /tasks requires a valid token with the admin role.

Example Output:

# Attempting to post without token
$ curl -X POST http://localhost:8080/tasks
# HTTP 401 Unauthorized

# Posting with token
$ curl -X POST -H "Authorization: Bearer <TOKEN>" http://localhost:8080/tasks
# HTTP 201 Created

The Core Question You’re Answering

“How do we secure microservices without every service having its own user database?”

OIDC and JWT allow for ‘Stateless Security’. The service doesn’t need to call a database to verify a user; it only needs to verify the cryptographic signature of the token.


Concepts You Must Understand First

Stop and research these before coding:

  1. OAuth2 vs OIDC
    • What is the difference between an Access Token and an ID Token?
  2. Bearer Authentication
    • How is the token passed in the HTTP header?

Questions to Guide Your Design

Before implementing, think through these:

  1. Token Propagation
    • If Service A calls Service B, how do you pass the user’s identity along?
  2. Local Security
    • How do you test security during development without a real Keycloak server? (Hint: Quarkus Dev Services).

Thinking Exercise

The Token Verification

When Quarkus receives a JWT, it checks:

  1. Is the signature valid? (Uses Public Key).
  2. Is the iss (issuer) correct?
  3. Is the exp (expiry) in the future?

Questions while coding:

  • Why doesn’t the service need to ‘talk’ to Keycloak for every request?
  • What happens if the Keycloak server goes offline but the service is still running?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is Quarkus OIDC?”
  2. “Explain RBAC and how to implement it in Quarkus.”
  3. “How do you handle security in a native executable?”
  4. “What is the role of Dev Services for Keycloak?”
  5. “How do you inject the SecurityIdentity in a Quarkus resource?”

Hints in Layers

Hint 1: Extension Add quarkus-oidc.

Hint 2: Configuration In application.properties, you usually need quarkus.oidc.auth-server-url. With Dev Services, this is automatic!

Hint 3: Annotations Use @Authenticated or @RolesAllowed("admin") on your methods.

Hint 4: Tokens Use the Keycloak admin console (on the port shown in Quarkus logs) to create a user and get a token for testing.


Books That Will Help

Topic Book Chapter
OAuth2/OIDC “OAuth 2 in Action” Ch. 2-3
Quarkus Security “Quarkus Cookbook” Ch. 10

Project 9: The Kubernetes Operator (Quarkus SDK)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: Go (The standard for Operators)
  • Coolness Level: Level 5: Pure Magic (Super Cool)
  • Business Potential: 5. The “Industry Disruptor”
  • Difficulty: Level 4: Expert
  • Knowledge Area: Kubernetes / Cloud Automation
  • Software or Tool: Java Operator SDK, Kubernetes, CRDs
  • Main Book: “Kubernetes Operators” by Jason Dobies and Joshua Wood

What you’ll build: A Kubernetes Operator written in Java that manages a custom resource (e.g., a “MySQLDatabase” resource). Your operator will watch for new resources and automatically provision the underlying infrastructure in the cluster.

Why it teaches Quarkus: You’ll learn how Quarkus is used to build Infrastructure. Native compilation is a game-changer for Operators because they run as small pods that need to start fast and use very little memory. You’ll use the Quarkus Operator SDK.

Core challenges you’ll face:

  • The Reconciliation Loop → maps to Maintaining the ‘Desired State’
  • Watching Cluster Events → maps to Kubernetes API client interaction
  • CRD (Custom Resource Definition) Generation → maps to Defining your own K8s objects

Key Concepts:

  • Control Loop: Kubernetes Docs
  • Operator Pattern: “Kubernetes Operators” by O’Reilly

Difficulty: Expert Time estimate: 1-2 weeks Prerequisites: Project 4 (Config) completed, deep understanding of Kubernetes.


Real World Outcome

You will be able to run kubectl apply -f my-db.yaml and see your Java program automatically create deployments, services, and secrets.

Example Output:

$ kubectl apply -f mysql-task.yaml
mysql-task.example.com/my-db created

# Your operator logs:
[INFO] Noticed new MySQLDatabase resource 'my-db'
[INFO] Provisioning Pods and Services for 'my-db'...
[INFO] Reconciliation successful.

The Core Question You’re Answering

“How do we automate the management of complex stateful applications in Kubernetes?”

The Operator pattern allows you to encode human operational knowledge (backups, scaling, recovery) into software.


Concepts You Must Understand First

Stop and research these before coding:

  1. Desired State vs Current State
    • How does Kubernetes keep things running?
  2. Informer & Reflector
    • How does the K8s client watch for changes efficiently?

Questions to Guide Your Design

Before implementing, think through these:

  1. Idempotency
    • If your reconciliation loop runs twice, will it create two databases? (It shouldn’t!).
  2. Native Performance
    • Why is memory footprint critical for an operator that might be running in 100 different namespaces?

Thinking Exercise

The Control Loop

The operator doesn’t just run once. It’s a loop: Observe -> Diff -> Act

Questions while coding:

  • What happens if the user manually deletes a Service created by the operator?
  • How does the operator detect that the Service is missing and recreate it?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What is a Kubernetes Operator?”
  2. “Why use Java for Operators instead of Go?”
  3. “Explain the Reconciliation process.”
  4. “What is a CRD?”
  5. “How does the Quarkus Operator SDK simplify development?”

Hints in Layers

Hint 1: Extension Add quarkus-operator-sdk.

Hint 2: Reconciler Implement the Reconciler<MyCustomResource> interface. The reconcile method is where the magic happens.

Hint 3: Client Use the Fabric8 Kubernetes Client (injected automatically) to talk to the K8s API.

Hint 4: Testing Use minikube or kind to run a local cluster for testing.


Books That Will Help

Topic Book Chapter
Operator Design “Kubernetes Operators” Ch. 3-4
K8s Client “Fabric8 Documentation” Core API

Project 10: The Custom Extension (Quarkus Extension Dev)

  • File: LEARN_QUARKUS_KUBERNETES_NATIVE.md
  • Main Programming Language: Java
  • Alternative Programming Languages: N/A
  • Coolness Level: Level 5: Pure Magic (Super Cool)
  • Business Potential: 5. The “Industry Disruptor”
  • Difficulty: Level 5: Master
  • Knowledge Area: Framework Engineering / Metaprogramming
  • Software or Tool: Quarkus Extension Creator
  • Main Book: “Quarkus Cookbook” by Alex Soto (Appendix)

What you’ll build: You will build a Quarkus Extension for a third-party library (e.g., a simple custom logging library or a niche API client). You will split the code into a Deployment module (build-time logic) and a Runtime module.

Why it teaches Quarkus: This is the “God Mode” project. You will finally understand how Quarkus actually works. You’ll learn about Build Steps, Bytecode Recording, and how Quarkus “tricks” libraries into being native-ready.

Core challenges you’ll face:

  • Splitting Build vs Runtime → maps to Understanding what can happen at build-time
  • Recording Bytecode → maps to The ‘Recorder’ pattern in Quarkus
  • Providing Native Hints → maps to Explicitly telling GraalVM about reflection

Key Concepts:

  • Build Steps: Quarkus Extension Guide
  • Bytecode Enhancement: ASM / Gizmo (libraries Quarkus uses)

Difficulty: Master Time estimate: 2-4 weeks Prerequisites: All previous projects completed.


Real World Outcome

You will have a library that other Quarkus developers can add to their pom.xml. When they build their app, your extension will automatically configure itself and produce no runtime overhead.

Example Output:

# In the user's project
$ ./mvnw quarkus:dev
...
[INFO] MyCustomExtension initialized at build-time!
[INFO] Generated 14 build steps.

The Core Question You’re Answering

“How does Quarkus remove the overhead of my favorite library?”

Most libraries use reflection to find config at startup. You will write code that finds that config at build-time and generates the static code to initialize the library instantly.


Concepts You Must Understand First

Stop and research these before coding:

  1. Quarkus Bootstrap
    • How does Quarkus find extensions on the classpath?
  2. Gizmo
    • How do you generate Java bytecode without writing .java files?

Questions to Guide Your Design

Before implementing, think through these:

  1. Build Time vs Runtime
    • What data can you “capture” at build time and pass to the runtime recorder?
  2. Native Stability
    • Does the library you’re extending use Unsafe? How will you handle that in GraalVM?

Thinking Exercise

The Recorder Pattern

Quarkus allows you to “record” method calls at build-time and “replay” them at runtime.

// At BUILD TIME:
recorder.setupMyLibrary(configValue);

Questions while coding:

  • How does Quarkus save the state of configValue into the binary?
  • Why is this faster than reading a config file at runtime?

The Interview Questions They’ll Ask

Prepare to answer these:

  1. “What are the two main modules of a Quarkus extension?”
  2. “What is a @BuildStep?”
  3. “Explain the role of a Recorder.”
  4. “How do extensions help with GraalVM native image compatibility?”
  5. “What is the difference between a synthetic bean and a regular bean?”

Hints in Layers

Hint 1: Scaffolding Use mvn io.quarkus:quarkus-maven-plugin:create-extension.

Hint 2: Deployment Module This is where your @BuildStep methods go. This code NEVER runs in production.

Hint 3: Runtime Module This is where your library logic and @Recorder classes live.

Hint 4: Debugging Debugging build steps is hard! Use System.out.println during the build and look at the Maven output.


Books That Will Help

Topic Book Chapter
Extension Basics “Quarkus Official Docs” Writing Extensions
Framework Internals “Quarkus Source Code” io.quarkus.deployment

Project Comparison Table

Project Difficulty Time Depth of Understanding Fun Factor
1. Hello Quarkus Level 1 2h ⭐️ 😄
2. Reactive Data Level 2 6h ⭐️⭐️ 😄😄
3. Native Binary Level 3 4h ⭐️⭐️⭐️⭐️ 🤩🤩
4. Cloud Config Level 1 3h ⭐️⭐️ 😄
5. Fault Tolerance Level 2 4h ⭐️⭐️⭐️ 😄😄
6. Kafka Events Level 3 8h ⭐️⭐️⭐️⭐️ 🤩🤩
7. Serverless Level 2 4h ⭐️⭐️⭐️ 🤩
8. OIDC Security Level 2 6h ⭐️⭐️⭐️ 😄😄
9. K8s Operator Level 4 2w ⭐️⭐️⭐️⭐️⭐️ 🤩🤩🤩
10. Custom Extension Level 5 3w ⭐️⭐️⭐️⭐️⭐️ 🤯🤯🤯

Recommendation

If you are a Java developer new to Quarkus: Start with Project 1 and 2. The dev mode and Panache will immediately show you the productivity gains.

If you are interested in Kubernetes: Focus on Project 3, 4, and 9. Understanding how native binaries save money in a cluster is the “killer app” for Quarkus.

If you want to be a framework architect: Project 10 is the ultimate goal. Once you can write an extension, you truly understand the “Supersonic Subatomic” magic.


Final Overall Project: The Subatomic E-Commerce Mesh

What you’ll build: A complete, mini e-commerce platform consisting of:

  1. Catalog Service: Native binary, PostgreSQL (Project 2 & 3).
  2. Order Service: Event-driven (Kafka), Reactive (Project 6).
  3. Auth Service: Keycloak OIDC (Project 8).
  4. Price Function: Serverless (Project 7) for dynamic pricing.
  5. Operator: A custom K8s Operator to deploy the whole stack (Project 9).

This project integrates every concept. You will deploy it to a local Kubernetes cluster (Kind/Minikube), monitor it with Prometheus (Metrics), and see how a full Java stack can run on less than 500MB of total cluster RAM.


Summary

This learning path covers Quarkus through 10 hands-on projects. Here’s the complete list:

# Project Name Main Language Difficulty Time Estimate
1 The Instant-Feedback Dev Loop Java Beginner 1-2 hours
2 The Reactive Data Layer Java Intermediate 4-6 hours
3 The Native Binary Factory Java Advanced 2-4 hours
4 The Configurable Cloud Service Java Beginner 2-3 hours
5 The Resilient Service Mesh Java Intermediate 3-5 hours
6 Event-Driven Microservices Java Advanced 6-8 hours
7 The Serverless Function Java Intermediate 3-5 hours
8 Security with OIDC (Keycloak) Java Intermediate 4-6 hours
9 The Kubernetes Operator Java Expert 1-2 weeks
10 The Custom Extension Java Master 2-4 weeks

For beginners: Start with projects #1, #2, #4 For intermediate: Jump to projects #3, #5, #7, #8 For advanced: Focus on projects #6, #9, #10

Expected Outcomes

After completing these projects, you will:

  • Master the Quarkus “Build-time boot” philosophy and how it differs from traditional Java.
  • Be able to compile complex Java applications into high-performance native binaries via GraalVM.
  • Understand how to build reactive, non-blocking systems using Mutiny and Panache.
  • Expertly secure and configure microservices for a Kubernetes environment.
  • Gain the “Master” level skill of extending the framework itself to optimize any library.

You’ll have built 10 working projects that demonstrate deep understanding of Quarkus from first principles.