All notable changes to the Rust-Java REST Framework will be documented in this file.
The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.
4.0.0 - 2026-07-17
- Added build-time startup, route, direct JSON writer, and JDBC record mapper generation in a
separate
codegenclassifier. - Added explicit application descriptors, runtime profile plans, dependency health probes, and compile-verified standalone examples.
- Added English and Turkish configuration, operations, troubleshooting, and declarative development guides.
- Made generated default package names safe when an artifact segment is a Java keyword.
- Kept runtime and core-runtime artifacts free of annotation processor and sample classes.
- Replaced handwritten startup indexes and repeated framework wiring with generated artifacts.
- Tightened route validation, component construction, low-allocation parameter binding, and native idle-memory configuration.
- Removed obsolete
FastMapV2,CleanerUtils,MemoryOptimizedConfig, manualStartupIndexGenerator, andRestApplication.sleepForever()compatibility APIs. - Removed duplicate allocation-based primitive parser helpers and the old native trim property alias.
- Java handlers, services, records, REST annotations, business rules, and native ABI
24/7/6remain unchanged. - Applications using a removed compatibility helper must migrate using the table in the README.
3.4.1 - 2026-07-16
- Refreshed the packaged Windows and Linux native runtime from a clean
rust-springsource revision. - Advanced the aligned Dubbo native contract from ABI
6to ABI7; REST ABI24and Redis ABI6are unchanged. - Added stale idle Dubbo connection expiry and liveness validation to the shared native runtime.
- Updated native provenance, SHA-256 validation, and release workflow gates for the
24/7/6ABI line.
- REST annotations, handler signatures, DTO serialization, runtime profiles, and response APIs are unchanged.
- Applications that use native Dubbo must upgrade
rust-java-restandjava-rust-dubbotogether.
- Added
RestApplication.run(...),runStandard(...), and async launcher overloads for explicit named modules without exposing the advanced builder in normal application entry points.
- Reduced the bundled sample entry point to one module-selection call while keeping handler and
resource composition explicit in
ReactorRustHyperModule. - Registered the nested feature sample records with DSL-JSON code generation so the documented
feature endpoints return JSON instead of a missing-serializer
500response. - Kept the existing builder API source-compatible for custom ports, containers, tests, and unusual lifecycle wiring.
- Native REST, Dubbo, and Redis ABI versions are unchanged; this is a Java API and documentation release.
3.2.5 - 2026-07-03
- Refreshed packaged Windows and Linux native resources for the current REST, Redis cache, and Dubbo companion library line.
- Documented the supported version set:
rust-java-rest:3.2.5,java-rust-cache:0.2.1, andjava-rust-dubbo:0.2.0. - Clarified that Dubbo native response handles require the current native resource package and must not be published over an older Maven version.
3.2.2 - 2026-06-07
- Made
JsonProducerResponseandDirectJsonResponseheader maps lazy. Default no-extra-header producer/direct JSON responses no longer allocate aLinkedHashMapbefore encoding the standard JSON content type; mutablegetHeaders().put(...)behavior is preserved. - Added
JsonBufferWriter.fieldStringAsciiPrefixInt(...)andJsonBufferWriter.stringAsciiPrefixInt(...)so hot direct/producer JSON loops can write predictable prefix-plus-int strings without caller-sideStringconcatenation. - Added direct
JsonBodyProducerresponse support. Hot producer routes can now returnJsonBodyProducerdirectly for default200 OKJSON, avoiding the per-requestJsonProducerResponsewrapper allocation.JsonProducerResponseremains the API for custom status codes and custom headers. - Added opt-in async
JsonBodyProducerdirect query-int support. Routes returningCompletionStage<JsonBodyProducer>orCompletionStage<JsonProducerResponse>can now use@DirectQueryIntscalar invocation without building query/header strings for that hot scalar. - Extended direct scalar
intbinding toRawResponse handler(int value)for read-model/cache routes that already return serialized bytes or native cached payload ids. - Changed async response frame buffers to heap-backed by default via
reactor.rust.async.direct-buffer.enabled=false. Direct async buffers remain available as an explicit RSS/p99-gated optimization instead of a low-RSS default. - Added short rebuild-gate evidence for the heap-backed async default: minimal
micro-restc256/c512 ended with60.285 MiBcgroup current,52.625 MiBcgroup anon, and0.008 MiBdirect-buffer attribution. Async producer routes reduced some c512 overload rows, but remain opt-in and route-local. - Added optional OpenJ9 startup preset
openj9-micro-rss-jitthreads1.options. It keeps JIT enabled and adds-XcompilationThreads1for services where javacore evidence shows JIT compiler thread surface is part of the anonymous memory budget. It is an A/B preset, not a default. - Added explicit route workload metadata with
@RouteWorkload. Heavy JSON routes can now declare a workload class and named budget such asheavy-json-directorheavy-json-producer; startup route diagnostics expose the workload and budget for each route. - Promoted
micro-rest-plusfrom a benchmark-only recipe to a runtime profile. It inheritsmicro-restsizing and applies measured route-budget defaults for heavy JSON routes without increasing global JNI queue, worker, or connection limits. - Added optional production gate
reactor.optimizer.fail-on-heavy-json-object-graph. When enabled, routes markedHEAVY_JSONfail startup if they still use a legacy/exact object-graph serialization path instead of direct writer,JsonProducerResponse,RawResponse, or native static response. - Tightened the heavy JSON production gate so direct query/path primitive bindings no longer hide a DTO object-graph response. Direct scalar binding removes parameter parsing overhead only; heavy JSON routes still need producer/direct/raw/native response paths to pass the gate.
- Added route diagnostics and startup metric visibility for heavy JSON object-graph routes.
/diagnostics/routesnow exposesheavy_json_object_graphat summary and route level, and Prometheus metrics includereactor_route_plan_heavy_json_object_graph. - Added
@BenchmarkOnlyRoutefor sample/benchmark comparison routes. Benchmark-only routes stay visible in diagnostics, but production route summaries and production gates separate them throughbenchmark_only,benchmark_legacy, andbenchmark_heavy_json_object_graph. The optionalreactor.optimizer.fail-on-benchmark-only-routes=truegate can reject them in real production services. - Replaced stale benchmark/memory helper overrides that still carried the rejected
128/125direct-heavy route recipe with the newmicro-rest-plusprofile budget source. - Split the bundled heavy DTO benchmark route into two explicit paths:
/api/v1/heavy/dtonow returns the same DTO-shaped JSON throughJsonProducerResponse, avoiding per-requestHeavyResponse -> HeavyItem -> HeavyMetadataobject graph allocation on the hot path./api/v1/heavy/dto/legacykeeps the real Java DTO graph + DSL-JSON path for apples-to-apples regression comparison.
- Added
dynamic-producer-jsonas the recommended benchmark endpoint class for hot dynamic JSON. The olderdynamic-dto-jsonclass now points to the legacy DTO graph path. - Updated JIT-cap gate defaults to measure the recommended dynamic producer path by default while still allowing explicit legacy DTO graph testing.
- Added targeted c256/c512 repeat-3 benchmark evidence for the split:
dynamic-producer-jsonimproves useful200throughput by1.50xat c256 and1.83xat c512 versus legacydynamic-dto-json, with RSS staying in the same broad band. - Tuned the sample optimized DTO-shaped route admission to
maxConcurrent=128,queueTimeoutMs=125after a c256/c512 repeat-3 matrix. Compared with the previous80/125setting, c512 useful200 RPSimproved from3064.78to4120.37and average503%dropped from13.89%to1.46%. - Ran the full dynamic gate with the selected
128/125recipe acrossdynamic-producer-json, legacydynamic-dto-json,direct-json-writer, andraw-jsonat c256/c512/c1000, repeat3. The optimized producer path stayed ahead of the legacy DTO graph on useful200 RPS:1.58xat c256,1.31xat c512, and2.06xat c1000. c512 still showed one overload outlier, so the recipe remains measured guidance rather than a universal default. - Added optional plan-level benchmark pre-warm and extended the route-admission matrix runner to support mixed endpoint sets with per-class aggregate output. This exposed that single-route admission tuning overfit the sample producer route.
- Moved the bundled
GET /api/v1/candidates/directsample route toRawResponse.registeredJson(...) + @NativeStaticRoute. This route is intentionally immutable and now demonstrates the correct Rust-served path for hot bodyless/static JSON instead of spending JNI capacity on a precomputed payload. - Removed the remaining DTO graph build from the benchmark native-cache miss path. The bundled
heavy cache sample now generates miss payload bytes through the direct heavy JSON writer before
registering them in the native cache; the legacy DTO graph remains only on
/api/v1/heavy/dto/legacyfor explicit comparison. - Re-ran the
micro-restsmall-direct repeat-3 gate after the native static change. Metrics showedreactor_native_jni_queue_full_total=0and only the metrics scrape entering JNI; remaining c512503came fromreactor_native_http_connections_rejected_total, not JNI queue pressure. - Re-ran the mixed c256/c512 clean-index matrix after the native static change. The rejected priority JNI lane remains opt-in only; native static improves the small static route without adding a global queue or extra priority worker.
- Rejected broad heavy-route fixes that traded one bottleneck for another:
get.api.v1.heavy=128/125lowered direct-heavy c512503but regressed RPS/p99 across the mixed matrix;jni.workers=2, queue=256helped producer/dynamic routes but hurt raw/small paths and did not fix direct-heavy. The accepted recipe is route-local and explicit: direct-heavymaxConcurrent=80,queueTimeoutMs=150for services that prefer fewer503over maximum RPS. - Updated the sample
dynamic-producer-jsonroute recipe from128/125to96/125after the mixed c512 matrix. Under the mixed plan,96/125produced3860.72useful200 RPS,192.91msp99,3.42%503, and75.77 MiBRSS, beating128/125on useful RPS, p99, and RSS. - Revalidated the updated
micro-rest-plusprofile at c512 with the mixed dynamic endpoint set:dynamic-producer-jsonproduced3703.11useful200 RPS,198.30msp99, and4.29%503. RSS after was higher in this run, so docs now keep route-admission tuning separate from pod memory sizing proof. - Ran the current full dynamic gate with
96/125,PlanPreWarm, c256/c512/c1000, repeat3. The producer route improved c512 versus the earlier128/125full gate: useful200 RPS3311.67 -> 3774.52, p99261.50ms -> 190.73ms, and503%15.92% -> 4.31%. c256 and c1000 throughput decreased, which is accepted for the memory-firstmicro-rest-plusrecipe. - Documentation now distinguishes production package contents from bundled sample/benchmark
artifacts more explicitly. The existing
3.2.1package already excludes sample/benchmark classes from the normal jar,core-runtime, sources, and javadocs. - Benchmark documentation now recommends the minimal production app as the default RSS attribution target. The bundled sample app remains the correct target only for bundled demo-route behavior.
- Removed the legacy request-count native trim branch from Java handler entry points. Native memory release is no longer attached to arbitrary user requests.
- Added optional
reactor.rust.native-trim.*idle policy. It runs from a daemon thread only after native request activity is stable and active connections/requests are below the configured thresholds, withreactor_native_trim_*metrics for attempts, skips, success, errors, and last duration. - Changed the background idle trim path to call ABI
21NativeBridge.releaseNativeMemoryRetaining(...), so memory-first services can keep a tiny response-buffer warm floor (retain-smalldefault2) while reclaiming larger pools and optionally trimming the platform allocator. The manual/diagnostics/native/trimendpoint remains a full diagnostic trim. - Rebuilt Windows DLL and Linux SO native resources for ABI
21, and added a Java native ABI smoke test so stale bundled binaries fail early. - Extended
linux_smaps_breakdown.ps1to capture/metricsper phase and include native idle trim attempts/skips/success/duration in the summary CSV and markdown report. - Added
idle_trim_ab_gate.ps1for trim off/on A/B validation across repeat runs. The current minimalmicro-restc64/c256/c512 repeat-3 gate showed final cgroup anon improvement-14.484 MiB, but average p99 regression+15.68%; idle trim remains explicit and disabled by default. - Reran a focused retained-floor soft-trim A/B on minimal
micro-rest, c64/c512, repeat2: final cgroup anon improved by-14.607 MiB, average p99 regressed by+10.88%, and max p99 regressed by+81.08%on one raw c64 run. The production decision remains conservative opt-in, not a default profile behavior. - Added
native_trim_policy_matrix.ps1and measured retain-small2/8/16with allocator trim on/off. Allocator trim off did not reclaim meaningful anon memory;retain-small=16with allocator trim on is now the opt-in starting point because the focused matrix showed about-15.367 MiBfinal cgroup anon with lower p99 risk than smaller floors. - Completed the full retained-trim A/B gate for
retain-small=16, minimalmicro-rest, c64/c256/c512, repeat3: final cgroup anon-14.768 MiB, final cgroup current-17.263 MiB, average p99+4.89%, max p99+27.37%, max503delta+3.021pp. - Completed the conservative production-timing soak with
30s/60s/10s, final idle95s, repeat1: final cgroup anon-20.844 MiB, final current-20.687 MiB, trim fired once in final idle. This remains low-traffic/idle-service evidence, not a throughput default. - Extended
linux_smaps_breakdown.ps1with-FinalIdleSnapshotSecondsfor same-container long idle soak snapshots. A c512 5-minute/30-minute soak showed trim-on anon stayed flat after reclaim (27.258 MiB -> 27.273 MiB), while trim-off stayed high (44.836 MiB -> 44.836 MiB). - Added
-JvmXsssupport tolinux_smaps_breakdown.ps1and introducedxss_anon_matrix.ps1for stack-size A/B evidence across256k/192k/160k/128kwithout duplicate JVM-Xssflags. - Updated the minimal production benchmark image to generate
META-INF/reactor/components.idxandMETA-INF/reactor/routes.idxduring Docker build. The minimal image now mirrors the strict low-RSS production expectation instead of emitting the classpath-scan fallback warning. - Completed the current indexed minimal
micro-restc512 stack matrix. No stack/OOM/native-thread failure or 500 was observed. Lowering-Xssdid not improve final anon in the clean-index run (256k=43.512 MiB,192k=46.113 MiB,160k=50.211 MiB,128k=49.082 MiB), so the default remains256k; smaller values remain service-specific experiments. - Tested
micro-restJNI queue capacity512as a focusedsmall-directoptimization while keeping one JNI worker andmax-connections=512. The focused indexed minimal-app c256/c512 repeat-3 matrix showed c256503dropping from19.720%to0%, and c512503from8.635%to0.607%. Full clean-index endpoint matrix rejected it as the globalmicro-restdefault: direct-heavy, producer-heavy, dynamic-producer, and raw-heavy regressed on RPS/p99/503. The default remainsreactor.rust.jni.queue-capacity=128; queue512is documented only as an explicit small/direct JSON tuning recipe. - Added opt-in route-local JNI queue admission (
@JniQueueAdmission/reactor.rust.jni-admission.*) backed by a bounded priority JNI lane. The bundledsmall-directsample keeps it disabled by default because the full clean-index gate reduced503but did not pass as a generalmicro-restdefault.@RouteAdmissionremains the right tool for heavy or slow route work. - Release documentation now states the package immutability rule: do not overwrite a published Maven version; cut a new patch version if packaged bytes must change.
- Added optional OpenJ9 JIT code-cache cap evidence flow through
openj9-micro-rss-jitcap.options,linux_smaps_breakdown.ps1, andcontainer_benchmark.ps1. - Added
jitcap_gate.ps1to comparemicro-restagainst JIT-cappedmicro-restwith explicit RSS and p99 pass/fail criteria. - Extended Linux smaps evidence collection with optional post-measurement OpenJ9 javacore capture.
- Documented the full local JIT-cap gate result:
-Xcodecachetotal8mreduced minimal production cgroup RSS by5.952 MiB, but failed default candidacy due p99 regressions on mixed endpoint workload, especially the legacy dynamic DTO graph at c256/c512. - Added
micro-dubbosupport tolinux_smaps_breakdown.ps1, using static discovery defaults so the minimal production app can isolate the Dubbo-enabled runtime surface without requiring ZooKeeper. - Added
anon_evidence_gate.ps1, a single evidence entrypoint that runs minimalmicro-rest,micro-rest-plus,micro-dubbo, conservative trim off/on A/B, and OpenJ9 javacore/native evidence, then writes final attribution, peak memory, load signal, and all smaps rows to one report folder. - Added native
reactor_native_http_user_requests_totaland Javahttp_user_requests_total./health,/metrics,/metrics/*, and/diagnostics/*no longer reset the idle native trim window. This prevents Kubernetes probes, Prometheus scrapes, and benchmark diagnostics from keeping an otherwise idle pod inskipped_not_idle. - Changed idle native trim scheduling so
skipped_not_idleandskipped_activeretry at the next idle boundary instead of blindly waiting the fullinterval-ms. Conservative production settings still avoid request-path trim, but warmed RSS can now be reclaimed sooner after a burst. - Rebuilt Windows DLL and Linux SO resources after the native user-request metric change.
- Documentation now describes anon attribution as a production decision gate: use heap, JIT/code, class metadata, direct buffer, Rust-accounted pools, thread stack budget, and residual anon fields to choose the next code target instead of lowering heap or changing defaults blindly.
3.2.1 - 2026-06-04
- Maven package version bumped to
3.2.1. - Production-like benchmark images can now use
-FrameworkArtifactMode core-runtime, sorust-java-rest-*-core-runtime.jaris used instead of frameworktarget/classes. jvm_baseline_rss_matrix.ps1now forwards the framework artifact mode, keeping repeated JVM/RSS checks aligned with production classpath rules.- Published sources and javadocs now exclude framework sample, benchmark, and Dubbo sample packages.
- Runtime profile defaults no longer override keys explicitly configured in
rust-spring.properties; JVM system properties and environment variables still have highest priority. - README, benchmark docs, and production runtime docs now document the production artifact rule:
use the normal dependency or
core-runtime; do not use thesampleclassifier in production.
- Prevented sample/example classes and sample startup indexes from leaking into production-like consumer RSS measurements.
- Added regression coverage for explicit property values overriding runtime profile defaults.
mvn -q testmvn -q -DskipTests package- Jar policy check: main jar,
core-runtime, and sources jar contain no sample/benchmark packages and no sample startup index. - Native-static Dubbo consumer smoke RSS check with
-FrameworkArtifactMode core-runtime. - A/B smoke check for
core-runtimeversus frameworktarget/classesbenchmark classpath.
- Latest native-static Dubbo consumer smoke,
cpu1, idle5s:core-runtime: ready RSS57.27 MiB, after first RPC RSS58.28 MiB, Docker memory ready30.00 MiB, image build context5.01 MB.classes: ready RSS58.75 MiB, after first RPC RSS59.88 MiB, Docker memory ready31.48 MiB, image build context9.99 MB.
- This is a packaging and measurement-correctness patch, not a broad JVM RSS breakthrough. RSS can stay close because unloaded classes do not always become live RSS.
3.2.0 - 2026-06-03
- Added startup phase diagnostics via
/diagnostics/startupand Prometheus gauges. - Added optional
META-INF/reactor/components.idxsupport to bypass component classpath scanning. - Added optional
META-INF/reactor/routes.idxvalidation as a startup production gate. - Added native DLL/SO extraction cache keyed by ABI, platform, and SHA-256.
- Added
fast-startandready-low-latencyruntime profiles. - Added readiness prewarm hooks for handler descriptors, DSL-JSON writer state, and direct writer lookup.
- Added OpenJ9/Semeru startup tuning docs and a startup benchmark runner.
- Added tests for startup timeline metrics/JSON, startup index parsing, and index generation.
- Added optional OpenJ9 CRIU/Semeru InstantOn checkpoint hook and Docker Desktop image flow.
- Added
ready_since_restore_msstartup diagnostics for CRIU-restored containers. - Added WSL/Linux InstantOn benchmark script for normal vs restored container startup comparison.
- Added
@RouteAdmissionfor route-level native admission control before the JNI worker queue. - Added route admission matrix benchmark runner and memory proof runner.
- Added
JsonProducerResponseandJsonBodyProducerfor heavy dynamic JSON without building Java DTO list graphs. - Added direct primitive query/path binding expansion for hot numeric parameters.
- Added user-facing REST cookbook with GET, GET-by-id, POST, PUT, PATCH, and DELETE examples.
- Added richer profile/RSS decision guidance for
micro-rest,micro-dubbo,low-rss,balanced-dubbo,throughput,fast-start, andready-low-latency. - Added lean production artifact behavior: the default jar excludes sample/benchmark classes and sample code is attached as a separate classifier.
- Route index validation now detects both missing routes and unexpected runtime routes.
- Native extraction cache now verifies cached file content by SHA-256, not only by file size.
- Classpath component scanning loads candidate classes without static initialization.
- Native ABI is now
20; use the DLL/SO from this package. - Maven package version bumped to
3.2.0. - README and release notes now avoid broad "always faster" or "always 50 MiB" claims and describe workload-specific profile decisions.
- Heavy producer sample route now uses measured route admission defaults
maxConcurrent=80,queueTimeoutMs=150. RawResponse,JsonProducerResponse, andFileResponsecache encoded headers to avoid repeated UTF-8/header encoding work on hot response paths.
mvn -q testmvn -q -DskipTests package- Full repeat benchmark:
micro-rest-plus, endpoint classessmall-json-legacy,small-json-direct,dynamic-dto-json,producer-json,direct-json-writer,raw-json,native-cache-json,file-static, concurrency64/256/512/1000, repeat3. - Idle/soak memory proof with mixed small/raw/heavy/cache/export endpoints.
- Route admission full matrix for producer JSON at c256/c512 with
64/80/96/128concurrency limits and75/125/150 msqueue timeouts.
- At c512, small JSON averaged
9153 RPS,115.83 msp99, and68.75 MiBsampled RSS versus Spring Boot3459 RPS,368.60 msp99, and314.33 MiBsampled RSS. - At c512, raw/precomputed JSON averaged
9659 RPS,114.80 msp99, and68.56 MiBsampled RSS versus Spring Boot3875 RPS,623.98 msp99, and274.13 MiBsampled RSS. - At c512, dynamic DTO JSON averaged
3338 RPS,309.68 msp99, and67.82 MiBsampled RSS versus Spring Boot1524 RPS,776.47 msp99, and309.98 MiBsampled RSS. Dynamic DTO remains supported, but the Java object graph cost is still real. - Memory proof baseline was
66.11 MiB, peak was91.35 MiB, and final idle RSS was75.59 MiB. - For heavy dynamic JSON and high concurrency, release guidance is to use route admission and at
least
128 MiBpod headroom unless a service-specific soak test proves lower memory is safe.
3.1.0 - 2026-06-01
- Clarified user-facing documentation with use-case driven API choices, runtime profile guidance, low-RSS tuning recipes, and softer release notes language.
- Added a response path playbook for Small JSON, Raw/precomputed JSON, Native cache JSON, Direct JSON writer, and Dynamic DTO selection.
- Promoted the measured
3.1.0-rc5feature set to stable3.1.0. - Maven package version bumped to
3.1.0.
- Stable for pilot and production adoption where route-level tuning, bounded overload behavior, and low-RSS profile selection are treated as part of deployment.
- Best fit remains small JSON, raw/precomputed JSON, direct/Rust JSON writer, native static/cache, and file response paths.
- Dynamic Java DTO graphs remain supported, but should be measured and tuned on hot routes when RSS or p99 latency is a hard requirement.
- Added
@NativeStaticRoutefor immutableRawResponse.registered*routes. Rust can now serve explicitly static/native responses without invoking the Java handler or JNI queue per request. - Added
reactor.rust.file-stream.chunk-bytesfor boundedFileResponsestream tuning. The native runtime reports the active value through Prometheus metrics and memory diagnostics. - Added
@NativeStaticFileRoutefor immutableFileResponseroutes. The handler is invoked once during startup; runtime requests are streamed directly by Rust without entering the Java handler. - Added native static file observability through
reactor_native_static_file_response_bytesandstatic_responses.file_bytesin diagnostics. - Added
reactor.rust.static-file.inline-max-bytes. Immutable@NativeStaticFileRoutefiles at or below this threshold are loaded into native memory once and served without disk I/O. - Added
reactor.rust.static-file.max-concurrent-streamsbulkhead for disk-backed native static file streams. Overload returns503and increments native stream rejection metrics instead of allowing unbounded disk/file-descriptor fanout. - Added
file-stream-largebenchmark class and/api/v1/export/file-largesample endpoint for 8 MiB file-stream bulkhead measurement. - Added
-FrameworkJavaOptsAppendto the container benchmark script so profile overrides can be measured without editing the benchmark harness.
- Native ABI bumped to
19; Windows DLL and Linux SO must match this Java build. - Maven package version bumped to
3.1.0-rc5. - Increased low-RSS HTTP connection headroom from
512to1024so c512 benchmark gates do not fail from admission-limit jitter. - Increased benchmark-only ultra-low-rss HTTP connection headroom from
512to640. - Changed the default native
FileResponsestream chunk from the small response buffer size to64 KiB; throughput profile can raise it while micro/low-RSS profiles keep it bounded. @NativeStaticFileRoutenow caches file length and parsed response headers at startup, removing per-request filemetadata()and encoded-header parsing from the static file hot path.
mvn -q testcargo testcargo build --releaseon Windowscargo build --releaseon Linux via WSL- Container benchmark
container_20260531_051255: low-RSS profile, CPU2, Rust-Java memory96m, Spring Boot memory512m, endpoint classesraw-json,file-static, concurrency64/256/512, repeat3, randomized order. - Memory proof
memory_proof_low-rss_20260531_052414:heavy/rawandexport/staticwith post-load idle snapshots and native trim checks. - Admission headroom check
container_20260531_053510:export_static_registeredat c512 withmax-connections=1024,0connection rejections,0response backpressure, and05xx. - Native static file route check
container_20260531_060646:export_file_streamat c512 produced1553 RPS,1.08sp99,0connection rejections,0response backpressure,05xx, and only startup/diagnostic JNI activity (reactor_native_jni_requests_total=1for the endpoint metrics snapshot). - Native static file inline check
container_20260531_063622: low-RSS c512 withreactor.rust.static-file.inline-max-bytes=524288produced1926 RPS,944.03msp99,0connection rejections,0response backpressure,05xx, andreactor_native_static_file_inline_bytes=302608. - Static file stream bulkhead smoke: inline disabled,
reactor.rust.static-file.max-concurrent-streams=1,/api/v1/export/filereturned200,reactor_native_static_file_stream_limit=1,reactor_native_static_file_stream_started_total=1, and diagnostics exposedstream_limit. - Current full benchmark
current_full_20260531_090441: low-RSS profile, CPU2, Rust-Java memory96m, Spring Boot memory512m, concurrency64/256/512/1000, repeat1, randomized order. - Large file stream matrix
stream_matrix_{32,64,128,256}_20260531_085157: 8 MiB file, inline disabled, stream limits32/64/128/256, concurrency256/512/1000.
- At c512,
candidatesreached4.87xSpring Boot RPS with125.69msp99 and80.46 MiBmax sampled container memory. - At c512,
echo_parse_businessreached4.39xSpring Boot RPS with98.38msp99 and90.04 MiBmax sampled container memory. - At c512,
heavy100_rawreached2.00xSpring Boot RPS with142.44msp99 and91.22 MiBmax sampled container memory. - At c512,
heavy100_native_cachereached14970 RPSwith102.03msp99 on the Rust-Java path. - Large file stream results favor
32or64max concurrent streams for low-RSS services; higher limits increase p99/RSS and should be reserved for dedicated download profiles.
- Split container benchmark endpoint classes into
dynamic-dto-json,direct-json-writer,rust-json-writer,raw-json,native-cache-json, andfile-staticso optimized paths are not mixed into one heavy JSON number. - Added
-EndpointClassesbenchmark filter for targeted repeated runs. - Added
balancedcontainer benchmark runtime profile betweenlow-rssandthroughput. - Added direct primitive route bindings for query/path
doubleandshort, matching the existingint,long, andbooleanfast paths. - Added
DirectJsonWriterRegistryandDirectJsonWriterProviderso generated/manual DTO writers can bypass DSL-JSON and write directly into the responseByteBuffer. - Added
reactor.rust.json.direct-writer-enabledproperty.
- Native ABI bumped to
13; Windows DLL and Linux SO must match this Java release. JsonBufferWriternow supports double values.- Route diagnostics now expose the new direct primitive strategy types.
mvn -q testcargo testcargo build --releaseon Windowscargo build --releaseon Linux via WSL- Container benchmark
container_20260530_154237: low-RSS profile, CPU2, Rust-Java memory128m, Spring Boot memory512m, concurrency64/256/512/1000, repeat3, randomized order. - Profile comparison gates:
container_20260530_165249forbalancedc=1000 andcontainer_20260530_172402forthroughputc=1000.
- At concurrency
1000, average Rust-Java RPS ratios were3.07xforcandidates,3.76xforecho,4.01xforheavy100 raw, and1.51xforheavy100 dynamic DTO. - Rust-Java max sampled container memory stayed around
95-98 MiBfor the comparable c=1000 endpoints, while Spring Boot was around295-313 MiB. file-staticis not yet a high-concurrency throughput winner in the low-RSS profile; it needs separate stream/sendfile tuning before being used as a throughput claim.
3.0.0 - 2026-03-17
- MethodMetadata Cache - Pre-computed annotation metadata at startup (~200ns → ~5ns)
- FastMapV2 - Robin-Hood hashing for O(1) parameter lookup (was O(n))
- Zero-Copy Header Encoding - Direct byte encoding in Rust (no String allocation)
- ThreadLocal Buffer Pools - Zero-allocation parameter parsing
| Endpoint | Before | After | Improvement |
|---|---|---|---|
| GET /health | 8-12ms | 5-8ms | 33-40% faster |
| POST /order/create | 8-15ms | 6-11ms | 25-35% faster |
| Concurrent 10 req | 8-15ms | 4-6ms | 50% faster |
MethodMetadata.java- Pre-computed method parameter metadata cacheFastMapV2.java- Robin-Hood hashing implementation for O(1) lookupParamInfoclass - Cached parameter information (type, name, defaultValue)ParamTypeenum - Parameter type classification (PATH_VARIABLE, REQUEST_PARAM, etc.)- Pre-allocated error byte arrays in DslJsonService for fast error responses
writeErrorToBuffer()method in DslJsonService
encode_headers_zero_copy()- Zero-copy header encoding to Vecencode_path_params_zero_copy()- Zero-copy path parameter encoding- Thread-local buffer pools for header and path encoding
- Pre-calculated buffer sizes to avoid borrow checker issues
Dockerfile.ultra- Ultra-low memory container (149MB image, 28MB runtime)- Multi-stage build with Rust 1.85 and JDK 21
- jlink minimal JRE (~25MB)
- Ultra-low memory JVM options (4-24MB heap)
- Integrated MethodMetadata cache for zero-overhead annotation lookup
- Replaced HashMap with ThreadLocal FastMapV2 pools
- Added
parseParamsFast()andparseHeadersFast()methods - Added
resolveArgumentsFast()with pre-computed parameter info - Added lazy debug logging (only when
-Dhandler.debug=true)
- Added pre-allocated ERROR_PREFIX and ERROR_SUFFIX byte arrays
- Added
writeErrorToBuffer()for fast error responses - Added
escapeJson()helper for JSON string escaping - Removed verbose initialization logging
- Changed header encoding from String to Vec (zero-copy)
- Fixed borrow checker issues in buffer size calculation
- Removed unused imports (AtomicPtr, HashMap)
- Fixed doc comments on thread_local! macro
| Metric | v2.0.0 | v3.0.0 |
|---|---|---|
| Per-request allocation | ~2KB | ~0 bytes |
| Container memory | 27-35 MB | 26-29 MB |
| JRE size | 35 MB | ~25 MB |
Added 2 new project rules:
-
Rule #17: Docker Image & JRE Ultra Low Size
- Docker Image target: < 150 MB
- JRE target: < 30 MB (via jlink)
- Runtime memory: < 50 MB
-
Rule #18: Test Strategy - Docker vs Local
- Load/Benchmark/Stress tests → Docker Container
- Functional/Unit tests → Local (mvn test)
# Rust (Cargo.toml)
rayon = "1.10" # Parallel iterator and thread pool
radix_trie = "0.2" # Radix trie for route matching
smallvec = "1.13" # Stack-allocated small vectors# Build ultra-low memory image
docker build -t rust-java-rest:ultra -f src/main/resources/container/Dockerfile.ultra .
# Run with 50MB memory limit
docker run -d -p 8080:8080 --memory=50m --name rust-java rust-java-rest:ultraNone. All v2.0.0 code is compatible with v3.0.0.
2.0.0 - 2026-03-12
- Zero-overhead Dependency Injection container
@Component,@Service,@Repository,@Configurationannotations@Beanmethods for bean production@Autowiredfor dependency injection@PostConstructand@PreDestroylifecycle callbacks@Primaryand@Qualifierfor bean selection- O(1) bean lookup with ConcurrentHashMap
- Bean lookup: ~0.4 microseconds
- Memory overhead: ~50-100 bytes/bean
- Zero runtime reflection
1.0.0 - 2026-03-01
- Initial release
- Rust Hyper HTTP server with JNI
- Spring Boot-like annotations (@GetMapping, @PostMapping, etc.)
- DSL-JSON 2.0.2 integration
- Parameter annotations (@PathVariable, @RequestParam, @HeaderParam, @RequestBody)
- ResponseEntity support
- WebSocket support (/ws/echo, /ws/chat/{roomId})
- Docker images (74MB minimal)
- ~27 MB memory (vs Spring Boot ~94 MB)
- 3,257 RPS (vs Spring Boot ~1,150 RPS)
- 33 ms latency (vs Spring Boot ~144 ms)