Spring Boot vs Quarkus at 1 GiB with swap disabled
A short follow-up to the 768 MiB Spring Boot vs Quarkus experiment.
Question
What changes when the same constrained-JVM experiment gets approximately 1 GiB of RAM and no swap?
Setup
I stopped the existing VM, changed its configured memory to 1 GiB, started it again, and disabled swap with sudo swapoff -a. The guest reported 955 MiB of RAM and Swap: 0B.
Spring Boot 4.1.1 and Quarkus 3.39.4 used Eclipse Temurin 25.0.4.1+1, the same JVM flags including -Xmx80m, separate file-backed H2 databases, the same deterministic fixture, and the same startup order. The paired workload sent ten requests to each application, followed by manually recorded checkpoints at the same nominal stages as the 768 MiB run. The final snapshot was taken 13 minutes 47 seconds after the post-workload snapshot; checkpoint names describe nominal stages rather than exact sampling deadlines.
Results
| Checkpoint | Spring RSS | Quarkus RSS |
|---|---|---|
| Ready, pre-request | 233.1 MiB | 169.6 MiB |
| After one request | 234.8 MiB | 170.5 MiB |
| Post-workload | 235.4 MiB | 171.9 MiB |
| Intermediate | 239.7 MiB | 178.4 MiB |
| Nominal 5-minute checkpoint | 240.0 MiB | 179.6 MiB |
| Final, nominal 10-minute checkpoint | 240.4 MiB | 181.2 MiB |
Process RSS (MiB)
Swap was disabled throughout this run; both applications recorded zero process swap at every checkpoint. At the final checkpoint, Spring RSS was 240.4 MiB and Quarkus RSS was 181.2 MiB.
Comparison with 768 MiB
The 768 MiB experiment used the same applications, JVM flags, startup order, fixture, and workload, with 256 MiB of configured swap. The final checkpoints compare as follows:
| Configuration | Spring RSS | Spring swap | Quarkus RSS | Quarkus swap |
|---|---|---|---|---|
| 768 MiB, swap enabled | 202.3 MiB | 34.3 MiB | 175.7 MiB | 0.0 MiB |
| 1 GiB, swap disabled | 240.4 MiB | 0.0 MiB | 181.2 MiB | 0.0 MiB |
Spring's final RSS was 38.1 MiB higher in the 1 GiB run; Quarkus's was 5.5 MiB higher. In the 768 MiB run, Spring's RSS declined while process swap increased. This pattern is consistent with paging contributing to its lower resident footprint. RSS alone therefore does not establish lower overall memory demand in that run.
The capture parser's legacy heap fields contain generation-specific values rather than total JVM heap usage, so they are excluded from this comparison.
What this suggests
Quarkus had a smaller resident footprint at every sampled checkpoint in both configurations. At 1 GiB, the final gap was 59.2 MiB: Spring used 240.4 MiB RSS and Quarkus used 181.2 MiB. The ordering persisted when swap was unavailable.
Both applications completed all ten deliberate workload requests with HTTP 200 and remained active with zero recorded restarts. StatLite's final summary showed successful latest polls and zero consecutive poll failures for all three targets. This demonstrates successful operation during these short, lightly loaded observations.
Zero process swap in the 1 GiB run follows from disabling swap. Because both RAM and swap configuration changed, the comparison cannot isolate the effect of extra RAM or establish that extra RAM alone prevented swapping. Each configuration was observed once, Spring started first on the shared host, and neither run establishes long-term stability, throughput, or an independent minimum memory requirement for either application.
Evidence
The curated 1 GiB follow-up record contains the checkpoint data, workload, polling summary, and direct comparison with the 768 MiB run. Monitoring was provided by StatLite.