Skip to content

feat: Spring Boot 4 + Spring AI 2.0 upgrade - #23

Open
adityamparikh wants to merge 7 commits into
apache:mainfrom
adityamparikh:sb4
Open

feat: Spring Boot 4 + Spring AI 2.0 upgrade#23
adityamparikh wants to merge 7 commits into
apache:mainfrom
adityamparikh:sb4

Conversation

@adityamparikh

@adityamparikh adityamparikh commented Dec 13, 2025

Copy link
Copy Markdown
Contributor

Upgrades the Solr MCP server to Spring Boot 4.1.1 and Spring AI 2.0.1.

This PR is scoped to the Spring Boot 4 / Spring AI 2.0 upgrade only, rebased onto current main (a84033b). Changes that had accumulated on the sb4 branch but are unrelated to the upgrade (CI Solr-version-matrix tweaks, Solr 10 /admin/metrics test skips, the docker-image-tag-suffix helper superseded by #139, and cosmetic refactors) have been intentionally excluded.

Both are current GA releases on Maven Central (verified against maven-metadata.xml), so no milestone repositories are required.

Breaking configuration change: OTLP export moves from gRPC on port 4317 to HTTP on 4318, with a separate full URL per signal. OTEL_TRACES_URL changes meaning — it was a base endpoint and is now a complete path ending in /v1/traces. A value carried over from a pre-SB4 deployment will not error; traces simply stop arriving. OTEL_METRICS_URL and OTEL_LOGS_URL are new. See docs/observability.md.

Highlights

  • Jackson 3: tools.jackson.databind replaces com.fasterxml.jackson.databind (annotations stay in com.fasterxml.jackson.annotation); the MCP SDK uses mcp-json-jackson3. JacksonException replaces IOException/JsonProcessingException; JsonNode.properties()/asString() replace fields()/asText().
  • MCP annotations: package moved org.springaicommunity.mcp.annotationorg.springframework.ai.mcp.annotation (now part of Spring AI core).
  • Modular starters: spring-boot-starter-web-webmvc + -json; explicit spring-ai-autoconfigure-mcp-server-common (no longer transitive after Spring AI 2.0.0-M7); modular test starters.
  • Observability: spring-boot-starter-opentelemetry (SB4 idiomatic) for traces, metrics, and OTLP log export, replacing the manual OTel BOM + micrometer-tracing-bridge-otel approach; spring-boot-starter-aspectj for @Observed; OTel logback appender installed programmatically via InstallOpenTelemetryAppender; management.opentelemetry.* OTLP properties.
  • Testcontainers 2.x module/package renames.
  • JSpecify is built into Spring Boot 4, so the explicit dependency is dropped.
  • GraalVM native: AOT NullAway exclusions, JUnit-platform build-time init, DefaultMetaProvider + Solr API model reflection hints, per-profile AOT docs; dependency-resolution alignment for opentelemetry-proto and opentelemetry-api-incubator against the SB 4.1.0 BOM.
  • mcp-server-security 0.0.6 → 0.1.14 — see below.

mcp-server-security upgrade

0.0.6 is built against the Spring Boot 3 line: its POM declares spring-core 6.2.9 and spring-security-{web,config,core,oauth2-*} 6.5.2, and it predates mcp-core 2.x entirely. This branch ships Spring Framework 7.0.8 and Spring Security 7.1.0 via the Spring Boot 4.1.0 BOM, so the 0.0.6 bytecode was running against a Security major it was never compiled for.

0.1.14 is the current release of the same library on the Boot 4 line: spring-core 7.0.8, spring-security-* 7.1.0, mcp-core 2.0.0 — matching exactly what Spring Boot 4.1.0 and Spring AI 2.0.0 put on the classpath. The upgrade is a version-catalog change only; the McpServerOAuth2Configurer API used in HttpSecurityConfiguration is unchanged.

Coverage caveat, flagged for reviewers: no automated test in this repo exercises McpServerOAuth2Configurer on any version. It is wired only when OAUTH2_ISSUER_URI is set (HttpSecurityConfiguration#secured), and DockerImageHttpIntegrationTest deliberately runs without an issuer since it has no IdP. That gap is pre-existing and is not introduced by this PR, but it does mean the OAuth2 wiring path is covered by neither the old nor the new version here. Worth closing separately.

Rebase notes

Conflicts against current main were resolved to keep both sides rather than picking a winner:

File Resolution
build.gradle.kts Kept both NullAway blocks — main's compileTestJava disable (#179) and this branch's compileAot{,Test}Java disable. Different tasks.
SolrConfig.java Kept main's java.net.URI (new URL validation) plus tools.jackson.databind.ObjectMapper; dropped the Jackson 2 import.
SearchService.java, CollectionService.java Kept main's org.jspecify.annotations.Nullable plus the relocated org.springframework.ai.mcp.annotation.*.
SolrNativeHints.java Spring AI 2.x DefaultMetaProvider coordinate registered; the legacy springaicommunity name kept as a defensive no-op.

Two breaks surfaced only on build/test, not as textual conflicts:

  1. Missing static imports. main still uses import static org.junit.jupiter.api.Assertions.*, which this branch had expanded to explicit imports. Git merged the explicit list, so assertions main added since the fork point (feat(search): append remediation hints to common Solr query errors #166 assertThrows, feat(indexing): report indexed field names in tool responses #165 assertFalse) had no import. Added the two rather than reintroducing the wildcard.
  2. SolrNativeHintsTest failure. The test added on main via fix(native): register DefaultMetaProvider reflection hint to unbreak nativeTest #172 asserts a hint for org.springaicommunity.mcp.context.DefaultMetaProvider. Spring AI 2.x relocated that class into Spring AI core, and registerTypeIfPresent silently no-ops for a class absent from the classpath — so the legacy coordinate registers nothing here and the assertion failed. The test now pins the coordinate Spring AI 2.x actually ships.

Upstream work landed since the fork point was verified to survive the rebase: all new package-info.java files, #166's search remediation hints, and #165's indexed-field reporting. The service-file diffs versus main are now import migrations only.

Verification

All on JDK 25 (GraalVM 25.0.2 for the native path):

Command Result
./gradlew build 372 tests, 0 failures, 0 errors, 7 skipped
./gradlew nativeTest -Pnative 227 tests, 0 failures
./gradlew dockerIntegrationTest 49 tests, 0 failures (all three Docker classes, fresh Jib image)

References

🤖 Generated with Claude Code

@adityamparikh
adityamparikh marked this pull request as draft December 16, 2025 22:10
@adityamparikh

Copy link
Copy Markdown
Contributor Author

Currently using Milestone version of Spring AI 2.0. Will make it ready for review once Spring AI 2.0 is GA.

@epugh

epugh commented Jan 6, 2026

Copy link
Copy Markdown
Contributor

Thanks for the update on this one... We will merge when we get an official Spring AI 2.0 release!

@epugh epugh changed the title feat: Spring Boot 4 upgrade feat: Spring Boot 4 + Spring AI 2.0 upgrade Jan 6, 2026
epugh pushed a commit that referenced this pull request Mar 9, 2026
* feat: implement observability with OpenTelemetry and Micrometer, add logging configuration, and enable tracing with annotation support

* test(observability): implement distributed tracing tests for Spring Boot 3.5

Add comprehensive distributed tracing test suite using SimpleTracer from
micrometer-tracing-test library. This is the Spring Boot 3-native approach
for testing observability without requiring external infrastructure.

Key changes:
- Add DistributedTracingTest with 6 passing tests for @observed methods
- Add OpenTelemetryTestConfiguration providing SimpleTracer as @primary bean
- Add OtlpExportIntegrationTest (disabled due to Jetty dependency issue)
- Add LgtmAssertions and TraceAssertions utility classes
- Add micrometer-tracing-bridge-otel to bridge Observation API to OpenTelemetry
- Add spring-boot-starter-aop for @observed annotation support
- Add test dependencies: micrometer-tracing-test, awaitility, Jetty modules

Test results:
- DistributedTracingTest: 6/6 tests passing
- Spans successfully captured from @observed annotations
- Build: SUCCESS (219 tests passing, 0 failures)

Spring Boot 3.5 uses Micrometer Observation → Micrometer Tracing → OpenTelemetry
bridge, which differs from Spring Boot 4's direct OpenTelemetry integration.

Adapted from PR #23 (Spring Boot 4 implementation) with modifications for
Spring Boot 3.5 architecture and APIs.

---------

Signed-off-by: adityamparikh <aditya.m.parikh@gmail.com>
Co-authored-by: Claude Opus 4.5 <noreply@anthropic.com>
@adityamparikh

Copy link
Copy Markdown
Contributor Author

Re-triggering CI now that ci.yml has landed on main (#117).

@epugh

epugh commented May 2, 2026

Copy link
Copy Markdown
Contributor

Looks like you have some conflicts.. I think you need to update from main to pick up the new ci stuff?

@adityamparikh

Copy link
Copy Markdown
Contributor Author

Let's get 1.0 out.
This can be next minor version update.

adityamparikh and others added 5 commits August 19, 2026 07:35
Migrate the Solr MCP server from Spring Boot 3.5.x / Spring AI 1.1.x to
Spring Boot 4.1.0 and Spring AI 2.0.0 GA.

Highlights:
- Jackson 3: tools.jackson.databind replaces com.fasterxml.jackson.databind
  (annotations stay in com.fasterxml.jackson.annotation); the MCP SDK uses the
  mcp-json-jackson3 module. JacksonException replaces IOException/
  JsonProcessingException; JsonNode.properties()/asString() replace
  fields()/asText().
- MCP annotations: package moved from org.springaicommunity.mcp.annotation to
  org.springframework.ai.mcp.annotation (now part of Spring AI core).
- Modular starters: spring-boot-starter-web -> -webmvc + -json; explicit
  spring-ai-autoconfigure-mcp-server-common (no longer pulled transitively
  after Spring AI 2.0.0-M7); modular test starters (actuator / opentelemetry /
  webmvc).
- Observability: spring-boot-starter-opentelemetry (SB4 idiomatic) for traces,
  metrics, and OTLP log export, replacing the manual OTel BOM +
  micrometer-tracing-bridge-otel approach; spring-boot-starter-aspectj for
  @observed; OpenTelemetry logback appender installed programmatically via
  InstallOpenTelemetryAppender; management.opentelemetry.* OTLP properties.
- Testcontainers 2.x module/package renames.
- JSpecify is built into Spring Boot 4, so the explicit dependency is dropped.
- GraalVM native: AOT NullAway exclusions for generated sources, JUnit-platform
  build-time init, DefaultMetaProvider + Solr API model reflection hints, and
  per-profile AOT documentation; dependency-resolution alignment for
  opentelemetry-proto and opentelemetry-api-incubator against the Spring Boot
  4.1.0 BOM.

Both Spring Boot 4.1.0 and Spring AI 2.0.0 are GA on Maven Central, so no
milestone repositories are required.

Scope is limited to the Spring Boot 4 / Spring AI 2.0 upgrade and its required
changes; unrelated CI, Solr-version-matrix, and Solr 10 metrics changes are
intentionally excluded.

Signed-off-by: adityamparikh <aditya.m.parikh@gmail.com>
Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
… JSON test to Jackson 3

Resolving PR #23 (sb4 -> main) onto current main surfaced two build breaks
that the conflict resolution had to fix:

1. SBOM completeness gate failed. `generateBinaryLicense` compares the
   CycloneDX SBOM against the shipped `productionRuntimeClasspath`, but
   `cyclonedxBom` was never configured for it. Spring Boot's
   `CycloneDxPluginAction` only auto-configures the cyclonedx plugin version it
   recognizes (3.x for Spring Boot 4.1.0); we stay pinned to 2.4.1 because
   cyclonedx 3.x fails at configuration time on Gradle 9.4.1 (variant-mutation
   conflict on `:cyclonedxDirectBom`). With 2.4.1 unrecognized, the task fell
   back to plugin defaults: it wrote `build/reports/bom.json` (not
   `application.cdx.json`) and scanned the wrong configuration set (stale
   Jackson 2, none of the Spring Boot 4 modular jars), so the gate reported
   ~30 bundled deps "absent from the SBOM". Configure the task explicitly:
   `outputName = "application.cdx"` and
   `includeConfigs = [productionRuntimeClasspath]`.

2. `JsonResponseParserContentTypesTest` (added on main via #90) imported the
   Jackson 2 `com.fasterxml.jackson.databind.ObjectMapper`, but SB4 migrated
   `JsonResponseParser` to Jackson 3. Use `tools.jackson.databind.json.JsonMapper`
   (the project's Jackson 3 mapper-construction pattern) instead.

Update the AGENTS.md SBOM Architecture note to match the explicit wiring.
`./gradlew build` is green.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Signed-off-by: adityamparikh <aditya.m.parikh@gmail.com>
The lgtm service published Grafana on "3000:3000" (all interfaces) while
setting GF_AUTH_ANONYMOUS_ORG_ROLE=Admin, so any host that could reach the
developer's machine had unauthenticated admin access to the observability
stack - no credentials, no prompt.

Verified against the running container:
- Old config: anonymous POST /api/folders -> HTTP 200, folder created.
- New config: same request      -> HTTP 403 "folders:create" denied.
- Grafana answers on 127.0.0.1:3000 but the LAN address refuses the
  connection.

Defaults are now loopback-only and read-only. Both are overridable for the
cases that genuinely need them, so the previous behaviour stays available
but has to be asked for:

  GF_ANON_ROLE=Admin  docker compose up -d lgtm   # editable dashboards
  GRAFANA_BIND=0.0.0.0 docker compose up -d lgtm  # expose on a trusted LAN

The OTLP receivers (4317/4318) are bound the same way via OTLP_BIND. The
application posts telemetry to http://localhost:4318 by default, so the
documented workflow is unaffected.

Reported by a CodeRabbit review of #23.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Signed-off-by: Aditya Parikh <aditya.m.parikh@gmail.com>
The lgtm service tracked grafana/otel-lgtm:latest, so a rebuild could pull a
different observability stack without any change to this repo. Pin 0.30.0
(current release as of 2026-07-31).

Verified against the pinned image rather than assumed:
- Provisioned Grafana datasources are Loki, Prometheus (default), Pyroscope
  and Tempo. There is no Mimir datasource, and the image ships a prometheus
  binary and prometheus.yaml with no mimir equivalent.
- OTLP ingestion works end to end on this tag: POST /v1/metrics returned 200
  and Prometheus then answered probe_counter_total{service_name=
  "solr-mcp-probe"} = 7.

So the docs were sending readers to a datasource that does not exist -
"Select Mimir as the datasource" could not be followed. Corrected across
compose.yaml and dev-docs/Observability.md, and added Pyroscope, which the
stack provides but the docs never mentioned. The architecture diagram was
redrawn (Prometheus is wider than Mimir) and all rows re-aligned to 81
columns.

The LGTM table keeps its "M is for Mimir" row - that is what the acronym
stands for - but now says the image actually ships Prometheus.

Reported by a CodeRabbit review of #23.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Signed-off-by: Aditya Parikh <aditya.m.parikh@gmail.com>
Rebasing the Spring Boot 4 / Spring AI 2.0 branch onto current main
applied cleanly at the textual level but left three test-side breaks
that only compiling and running the suite surfaces.

1. `SearchServiceIntegrationTest` and `IndexingServiceIntegrationTest`
   failed to compile. Main still uses the wildcard
   `import static org.junit.jupiter.api.Assertions.*`, which this branch
   had expanded to explicit imports. Git merged the explicit list, so the
   assertions main added since the fork point (apache#166 `assertThrows`, apache#165
   `assertFalse`) had no import. Add the two missing static imports rather
   than reintroducing the wildcard.

2. `SolrNativeHintsTest.registersDefaultMetaProviderConstructorHint`
   (added on main via apache#172) asserts a hint for
   `org.springaicommunity.mcp.context.DefaultMetaProvider`. Spring AI 2.x
   relocated that class to
   `org.springframework.ai.mcp.annotation.context.DefaultMetaProvider`,
   which the Registrar already registers. Because `registerTypeIfPresent`
   silently no-ops for a class that is absent from the classpath, the
   legacy coordinate registers nothing here and the assertion failed. Point
   the test at the coordinate that Spring AI 2.x actually ships; the
   legacy registration stays in the Registrar defensively.

`./gradlew build` is green on JDK 25: 372 tests, 0 failures, 0 errors,
7 skipped.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Signed-off-by: Aditya Parikh <aditya.m.parikh@gmail.com>
@adityamparikh

Copy link
Copy Markdown
Contributor Author

Rebased onto main (a84033b) and now green: 372 tests, 0 failures, 7 skipped on Spring Boot 4.1.0 + Spring AI 2.0.0 GA.

I have not force-pushed this PR's branch. Its head is adityamparikh:sb4, which is the long-lived integration branch — 9 local branches track it (chore/bump-*-sb4, feat/enable-virtual-threads-sb4, sb4-extras, …) and rewriting it would strand all of them. The rebased result is on adityamparikh:sb4-rebased-20260819 instead; say the word and I'll either retarget this PR's head to it or fast-forward sb4 deliberately.

Four conflicts, all from the Spring AI 2.0 relocation meeting upstream's jspecify work:

  • CollectionService/SearchService: took the org.springframework.ai.mcp.annotation.* imports and kept org.jspecify.annotations.Nullable — the merged bodies use @Nullable throughout.
  • SolrConfig: dropped the Jackson 2 ObjectMapper import (Jackson 3's tools.jackson.databind supersedes it) but kept java.net.URI, which fix: correct indexing, collection-name and service defects #176's path-normalisation fix needs.
  • build.gradle.kts: kept both Error Prone blocks — upstream's compileTestJava NullAway disable and this branch's AOT-sources disable are independent.
  • SolrNativeHints: kept both the SolrJ EnvUtils resource patterns and the DefaultMetaProvider registrations.

Two things the rebase broke semantically — both merged cleanly and failed only under javac/JUnit, so they are worth naming:

  1. This branch had expanded the wildcard Assertions.* static import into an explicit list; upstream then added tests using assertThrows (feat(search): append remediation hints to common Solr query errors #166) and assertFalse, which were not in that list. Compile failure.
  2. SolrNativeHintsTest (new upstream) asserts the DefaultMetaProvider hint under its pre-2.x name org.springaicommunity.mcp.context.DefaultMetaProvider. Spring AI 2.x relocated it to org.springframework.ai.mcp.annotation.context. Because the registration uses registerTypeIfPresent — a no-op when the class is absent — the old name passes vacuously on 1.x and fails outright here. The assertion now names the class actually on this classpath. Worth flagging to reviewers: that test is weaker than it looks on main today.

Still parked behind the 1.0 release per the earlier discussion; this is just to keep it merge-ready.

@adityamparikh

Copy link
Copy Markdown
Contributor Author

Updated: sb4 now points at the rebased, green state (e01c7da) — this PR shows it directly, so the temporary sb4-rebased-20260819 branch is redundant.

The previous sb4 tip (cb0d94e) is preserved on adityamparikh:backup-sb4-pre-rebase-20260819 if anything needs recovering. Branches that were tracking the old sb4 (chore/bump-*-sb4, feat/enable-virtual-threads-sb4, sb4-extras, …) will need rebasing onto the new tip.

…line

0.0.6 is built against the Spring Boot 3 line: its POM declares
spring-core 6.2.9 and spring-security-{web,config,core,oauth2-*} 6.5.2,
and it predates mcp-core 2.x entirely. This branch ships Spring Framework
7.0.8 and Spring Security 7.1.0 via the Spring Boot 4.1.0 BOM, so the
0.0.6 bytecode was running against a Security major it never saw.

0.1.14 is the current release of the same library on the Boot 4 line:
spring-core 7.0.8, spring-security-* 7.1.0, mcp-core 2.0.0 — matching
exactly what Spring Boot 4.1.0 and Spring AI 2.0.0 put on the classpath.
The upgrade is a version-catalog change only; McpServerOAuth2Configurer's
API in HttpSecurityConfiguration is unchanged.

Note on verification: no automated test in this repo exercises
McpServerOAuth2Configurer on any version. It is wired only when
OAUTH2_ISSUER_URI is set (HttpSecurityConfiguration#secured), and
DockerImageHttpIntegrationTest deliberately runs without an issuer since
it has no IdP. That coverage gap is pre-existing and worth closing
separately.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Signed-off-by: Aditya Parikh <aditya.m.parikh@gmail.com>
Addresses review findings on this PR.

Versions: 4.1.0 -> 4.1.1 and 2.0.0 -> 2.0.1, both verified as current against
maven-metadata.xml rather than a search index. The PR described 4.1.0/2.0.0 as
"the latest GA releases", which was true when written.

Observability docs were the substantive problem. This PR moves OTLP export from
gRPC on 4317 to HTTP on 4318 with a separate full URL per signal, which silently
redefines OTEL_TRACES_URL: it used to be a base endpoint and is now a complete
path ending in /v1/traces. docs/observability.md -- the user-facing guide README
links to -- still documented the removed otel.exporter.otlp.* properties and told
readers to export a :4317 base URL. Following it after this merged would not
error; traces would just stop arriving.

- docs/observability.md: real property names, corrected production example, a
  variable table, and an explicit upgrade warning about the changed semantics
- dev-docs/Observability.md: added here, so it now states its relationship to the
  user-facing guide instead of silently competing with it; defaults filled in for
  the three OTLP variables
- README.md: names all four OTEL variables
- AGENTS.md: version references, and the OTEL variables added to Key Configuration

Also removed a broken image reference in dev-docs/Observability.md
(images/grafana-traces.png does not exist in the repo); the prose that follows
already describes the trace breakdown in full.

build.gradle.kts: documented why spring-boot-starter-mongodb is excluded from
the Spring AI docker-compose module, and linked the CycloneDX 2.4.1 pin to apache#186
so it gets revisited rather than becoming permanent.

Verified: ./gradlew build green, 372 tests / 0 failures (matching main's count),
and nativeTest green at 227 passing / 0 failed -- unchanged by the version bump.

Signed-off-by: Aditya Parikh <aditya.m.parikh@gmail.com>
@adityamparikh

Copy link
Copy Markdown
Contributor Author

Pushed 6364bd3 addressing review findings.

Versions bumped

4.1.0 → 4.1.1 and 2.0.0 → 2.0.1, both checked against maven-metadata.xml directly (the
Maven Central search index returns stale, unsorted results for these coordinates). The PR
description called 4.1.0/2.0.0 "the latest GA releases" — true when written, no longer.
Description updated to match.

The substantive finding: observability docs would have broken users

This PR moves OTLP export from gRPC on 4317 to HTTP on 4318, with a separate full URL per
signal. That silently redefines OTEL_TRACES_URL — it used to be a base endpoint, and is now a
complete path ending in /v1/traces.

docs/observability.md — the user-facing guide README links to — was untouched by this PR and
still documented the removed otel.exporter.otlp.* properties plus:

export OTEL_TRACES_URL=https://otel-collector.example.com:4317

Following that after this merged would not error. Traces would just stop arriving, which is
the worst way for a telemetry config to fail.

Fixed:

  • docs/observability.md — real property names, corrected production example, a variable table,
    and an explicit callout that the semantics changed for anyone upgrading
  • dev-docs/Observability.md — this PR adds it, so it now states its relationship to the
    user-facing guide rather than silently competing with it; the three OTLP defaults are filled in
    instead of "(auto-configured)"
  • README.md — names all four OTEL variables
  • AGENTS.md — version references, plus the OTEL variables in Key Configuration

Also worth flagging as breaking in the release notes, not just the docs: anyone with
OTEL_TRACES_URL already set in a deployment is affected.

Smaller items

  • Broken image removed. dev-docs/Observability.md referenced images/grafana-traces.png,
    which does not exist anywhere in the repo — a broken-image icon on GitHub, introduced by this
    PR. The prose following it already describes the trace breakdown span by span, so it stands
    alone. Caught by a link check, not by reading.
  • The mongodb exclude is now explained. It sat uncommented in a file where the cyclonedx pin
    above it gets fourteen lines of rationale — exactly the kind of thing someone deletes while
    tidying, and being developmentOnly it would break local bootRun without CI noticing.
  • CycloneDX pin now has a tracker (build: revisit the CycloneDX 2.4.1 pin once the Gradle 9.4.1 variant conflict is fixed #186) linked from both build.gradle.kts and AGENTS.md,
    with a checklist for verifying the SBOM still lands where generateBinaryLicense expects it.

Verification

  • ./gradlew build — green, 372 tests / 0 failures, matching main's count exactly
  • ./gradlew nativeTest -Pnative — green, 227 passing / 0 failed, unchanged by the bump

Merge-order note

This PR and #175 both rewrite the same line in JsonResponseParser.toNamedList — this one changes
fields().forEachRemaining(...) to properties().forEach(...) for Jackson 3, #175 threads a node
path through it for the empty-facet fix. They compose (the properties() call plus the path
argument), but it is a guaranteed conflict. #175 is small and ready, so merging it first makes
this the cheaper rebase.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants