This is an automated email from the ASF dual-hosted git repository.

jamesbognar pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/juneau.git

commit d8e855681b0444b8cb6a6ba783a1e67bcbbe687e
Author: James Bognar <[email protected]>
AuthorDate: Fri May 8 10:30:10 2026 -0400

    refactor(inject): TODO-15 phase-3 batch 3 — drop vestigial casts, migrate 
transient stores
    
    Two complementary cleanups in `RestContext.java` and `RestOpContext.java`. 
Build
    + unit tests + jetty-ftest verified green.
    
    (1) Vestigial `(BasicBeanStore) bs` casts dropped — 16 in `RestContext` 
(lines
    494, 515, 584, 676, 753, 768, 914, 937, 957, 987, 1008, 1029, 1064, 1110, 
1125)
    and 1 in `RestOpContext` (line 437). Each was a leftover from before the
    cascade-builder migration widened the utility-class `create(...)` factories
    (`FileFinder`, `EncoderSet`, `MethodExecStore`, `ParserSet`, 
`SerializerSet`,
    `ThrownStore`, `RestOperations`, `RestChildren`, `ResponseProcessorList`,
    `RestOpArgList`) to accept `WritableBeanStore`, and before
    `BeanCreator.of(Class, BeanStore)` was added. The casts were no-ops on the
    legacy `BasicBeanStore` instance — and they would have started failing once 
any
    caller passed a `BasicBeanStore2` through. Drop now to unblock that next 
step.
    
    (2) Five transient internal-bean-store sites migrated from
    `BasicBeanStore.of((BasicBeanStore) beanStore())` to
    `new BasicBeanStore2(beanStore())`:
    
    * `RestOpContext.java:216` — `beanContext` lambda
    * `RestOpContext.java:546` — `jsonSchemaGenerator` lambda
    * `RestOpContext.java:664` — `partParser` lambda
    * `RestOpContext.java:680` — `partSerializer` lambda
    * `RestContext.java:2670` — `findRestOperationArgs`
    
    Each site builds a one-shot child store, adds 2 beans, and calls
    `createBeanFromMethod(...)` for `@RestInject` discovery. The result never 
escapes
    the method, so flipping the implementation is purely internal — no field or
    public-API changes.
    
    NOT migrated (see TODO-15 §"Residual casts in `RestContext` / 
`RestOpContext`"
    item 4 for the full reasoning):
    
    * `RestContext.java:348` — 
`BasicBeanStore.create().overridingParent(...).type(...).impl(...)` — fluent
      Builder chain needs an equivalent on the v2 side first.
    * `RestContext.java:1206` — per-resource store exposed via public
      `RestContext.getBeanStore()`; `RestSession.java:240` and 
`VarResolver.java:260`
      still downcast that result to legacy `BasicBeanStore` to call the legacy
      `BasicBeanStore.of(...)` static. Migrating them requires field/return-type
      widening or porting `of(...)` to v2.
    * `RestOpContext.java:1097` — registers the bean store under 
`BasicBeanStore.class`
      so user-facing `@RestPostCall void hook(BasicBeanStore bs)` parameter 
resolution
      keeps working. Cannot migrate without breaking that user contract until 
the
      legacy class is removed in Phase 4.
    
    Net effect: 16 vestigial casts gone, 5 transient stores on v2. The remaining
    4 legacy-API sites in 
`RestContext`/`RestOpContext`/`RestSession`/`VarResolver`
    are documented and gated by Phase 4 cutover.
    
    TODO-15 plan updated with batch-3 entry and revised residual table.
    
    Co-authored-by: Cursor <[email protected]>
---
 .../java/org/apache/juneau/rest/RestContext.java   | 39 +++++++++++++---------
 .../java/org/apache/juneau/rest/RestOpContext.java | 11 +++---
 todo/TODO-15-replace-basicbeanstore-with-v2.md     | 23 ++++++++-----
 3 files changed, 43 insertions(+), 30 deletions(-)

diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
index c6fb104835..698777119f 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContext.java
@@ -17,6 +17,7 @@
 package org.apache.juneau.rest;
 
 import org.apache.juneau.commons.http.MediaType;
+import org.apache.juneau.commons.inject.BasicBeanStore2;
 import org.apache.juneau.commons.inject.WritableBeanStore;
 
 import static jakarta.servlet.http.HttpServletResponse.*;
@@ -490,7 +491,7 @@ public class RestContext extends Context {
                                        RequestSwaggerVar.class, 
SerializedRequestAttrVar.class, ServletInitParamVar.class,
                                        SwaggerVar.class, UrlVar.class, 
UrlEncodeVar.class, HtmlWidgetVar.class
                                ).addDefault())
-                               .bean(FileFinder.class, 
FileFinder.create((BasicBeanStore) bs).cp(resourceClass(), null, true).build())
+                               .bean(FileFinder.class, 
FileFinder.create(bs).cp(resourceClass(), null, true).build())
                                .build()
                );
                bs.createBeanFromMethod(VarResolver.class, resource().get(), x 
-> isRestInjectMethod(x, PROP_bootstrapVarResolver)).ifPresent(v::set);
@@ -511,7 +512,7 @@ public class RestContext extends Context {
                // bean store's entries deque and are returned by 
bs.getBean(CallLogger.class) before falling
                // through to this memoizer's default supplier (which is what 
the @Rest(callLogger) chain
                // produces).  The memoizer therefore only needs to produce the 
framework default.
-               var creator = BeanCreator.of(CallLogger.class, (BasicBeanStore) 
bs).type(BasicCallLogger.class);
+               var creator = BeanCreator.of(CallLogger.class, 
bs).type(BasicCallLogger.class);
                bs.getBeanType(CallLogger.class).ifPresent(creator::type);
                // @Rest(callLogger=X) — most-derived non-Void wins.
                // getRestAnnotationsForProperty(...) yields parent-to-child 
order (rstream reversal); reduce-last
@@ -580,7 +581,7 @@ public class RestContext extends Context {
                        bs.addBean(Enablement.class, resolvedDebugDefault);
                else if (bs.getBean(Enablement.class).isEmpty())
                        bs.addBean(Enablement.class, isDebug() ? 
Enablement.ALWAYS : Enablement.NEVER);
-               var creator = BeanCreator.of(DebugEnablement.class, 
(BasicBeanStore) bs).type(BasicDebugEnablement.class);
+               var creator = BeanCreator.of(DebugEnablement.class, 
bs).type(BasicDebugEnablement.class);
                bs.getBeanType(DebugEnablement.class).ifPresent(creator::type);
                // @Rest(debugEnablement=X) — most-derived non-Void wins. See 
callLogger for the reduce-last rationale.
                getRestAnnotationsForProperty(PROPERTY_debugEnablement)
@@ -672,7 +673,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<EncoderSet.Builder> encodersBuilder = 
memoizer(() -> {
                var bs = beanStore();
-               var v = Value.of(EncoderSet.create((BasicBeanStore) bs));
+               var v = Value.of(EncoderSet.create(bs));
                getRestAnnotationsForProperty(PROPERTY_encoders).forEach(ai -> 
v.get().add(ai.inner().encoders()));
                bs.createBeanFromMethod(EncoderSet.class, resource().get(), 
RestContext::isRestInjectMethod, v.get()).ifPresent(x -> v.get().impl(x));
                return v.get();
@@ -749,7 +750,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<MethodExecStore> methodExecStore = memoizer(() 
-> {
                var bs = beanStore();
-               var b = MethodExecStore.create((BasicBeanStore) 
bs).thrownStoreOnce(getThrownStore());
+               var b = 
MethodExecStore.create(bs).thrownStoreOnce(getThrownStore());
                bs.createBeanFromMethod(MethodExecStore.class, 
resource().get(), RestContext::isRestInjectMethod, b).ifPresent(b::impl);
                return b.build();
        });
@@ -764,7 +765,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<ParserSet.Builder> parsersBuilder = memoizer(() 
-> {
                var bs = beanStore();
-               var v = Value.of(ParserSet.create((BasicBeanStore) bs));
+               var v = Value.of(ParserSet.create(bs));
                getRestAnnotationsForProperty(PROPERTY_parsers).forEach(ai -> 
v.get().add(ai.inner().parsers()));
                bs.createBeanFromMethod(ParserSet.class, resource().get(), 
RestContext::isRestInjectMethod, v.get()).ifPresent(x -> v.get().impl(x));
                return v.get();
@@ -910,7 +911,7 @@ public class RestContext extends Context {
                // DefaultConfig contributes the framework defaults at the top 
of the chain; resource-class entries append.
                // ResponseProcessorList.Builder.add(...) uses addAll (append) 
— final order: [DefaultConfig, parent, child].
                var bs = beanStore();
-               var v = Value.of(ResponseProcessorList.create((BasicBeanStore) 
bs));
+               var v = Value.of(ResponseProcessorList.create(bs));
                getRestAnnotationsForProperty(PROPERTY_responseProcessors)
                        .forEach(ai -> 
v.get().add(ai.inner().responseProcessors()));
                // Bean-store override REPLACES the entire annotation-derived 
list.
@@ -933,7 +934,7 @@ public class RestContext extends Context {
                // RestOpArgList.Builder.add(...) uses prependAll — applying 
per-annotation in chain order yields
                // final order: [child, parent, DefaultConfig], matching the 
legacy apply-pass behavior.
                var bs = beanStore();
-               var v = Value.of(RestOpArgList.create((BasicBeanStore) bs));
+               var v = Value.of(RestOpArgList.create(bs));
                getRestAnnotationsForProperty(PROPERTY_restOpArgs)
                        .forEach(ai -> v.get().add(ai.inner().restOpArgs()));
                // Bean-store override REPLACES the entire annotation-derived 
list.
@@ -953,7 +954,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<SerializerSet.Builder> serializersBuilder = 
memoizer(() -> {
                var bs = beanStore();
-               var v = Value.of(SerializerSet.create((BasicBeanStore) bs));
+               var v = Value.of(SerializerSet.create(bs));
                getRestAnnotationsForProperty(PROPERTY_serializers).forEach(ai 
-> v.get().add(ai.inner().serializers()));
                bs.createBeanFromMethod(SerializerSet.class, resource().get(), 
RestContext::isRestInjectMethod, v.get()).ifPresent(x -> v.get().impl(x));
                return v.get();
@@ -983,7 +984,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<StaticFiles> staticFiles = memoizer(() -> {
                var bs = beanStore();
-               var creator = BeanCreator.of(StaticFiles.class, 
(BasicBeanStore) bs).type(BasicStaticFiles.class);
+               var creator = BeanCreator.of(StaticFiles.class, 
bs).type(BasicStaticFiles.class);
                bs.getBeanType(StaticFiles.class).ifPresent(creator::type);
                // @Rest(staticFiles=X) — most-derived non-Void wins. See 
callLogger for the reduce-last rationale.
                getRestAnnotationsForProperty(PROPERTY_staticFiles)
@@ -1004,7 +1005,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<SwaggerProvider> swaggerProvider = memoizer(() 
-> {
                var bs = beanStore();
-               var creator = BeanCreator.of(SwaggerProvider.class, 
(BasicBeanStore) bs).type(BasicSwaggerProvider.class);
+               var creator = BeanCreator.of(SwaggerProvider.class, 
bs).type(BasicSwaggerProvider.class);
                bs.getBeanType(SwaggerProvider.class).ifPresent(creator::type);
                // @Rest(swaggerProvider=X) — most-derived non-Void wins. See 
callLogger for the reduce-last rationale.
                getRestAnnotationsForProperty(PROPERTY_swaggerProvider)
@@ -1025,7 +1026,7 @@ public class RestContext extends Context {
         */
        private final Memoizer<ThrownStore> thrownStore = memoizer(() -> {
                var bs = beanStore();
-               var b = ThrownStore.create((BasicBeanStore) 
bs).impl(parentContext() == null ? null : parentContext().getThrownStore());
+               var b = ThrownStore.create(bs).impl(parentContext() == null ? 
null : parentContext().getThrownStore());
                bs.createBeanFromMethod(ThrownStore.class, resource().get(), 
RestContext::isRestInjectMethod, b).ifPresent(b::impl);
                return b.build();
        });
@@ -1060,7 +1061,7 @@ public class RestContext extends Context {
        private final Memoizer<RestOperations> restOperations = memoizer(() -> 
safe(() -> {
                initializeFrameworkBeansForRestOps();
                var bs = beanStore();
-               var v = Value.of(RestOperations.create((BasicBeanStore) bs));
+               var v = Value.of(RestOperations.create(bs));
                var ap = getBeanContext().getAnnotationProvider();
                var rci = ClassInfo.of(resource().get());
                for (var mi : rci.getPublicMethods()) {
@@ -1106,7 +1107,7 @@ public class RestContext extends Context {
        private final Memoizer<RestChildren> restChildren = memoizer(() -> 
safe(() -> {
                var bs = beanStore();
                var servletConfig = 
bs.getBean(ServletConfig.class).orElse(null);
-               var v = Value.of(RestChildren.create((BasicBeanStore) 
bs).type(RestChildren.class));
+               var v = 
Value.of(RestChildren.create(bs).type(RestChildren.class));
 
                // Collect child classes from @Rest(children) on the annotation 
chain (parent-to-child order).
                // Deduplicate so the same child class registered on both a 
parent and child annotation
@@ -1121,7 +1122,7 @@ public class RestContext extends Context {
                        if (bs.getBean(rc2).isPresent()) {
                                so = () -> bs.getBean(rc2).get();
                        } else {
-                               Object o2 = BeanCreator.of(rc2, 
(BasicBeanStore) bs).run();
+                               Object o2 = BeanCreator.of(rc2, bs).run();
                                so = () -> o2;
                        }
                        var cc = new RestContext(new Args(rc2, this, 
servletConfig, so, "", null));
@@ -1194,6 +1195,12 @@ public class RestContext extends Context {
                        // @formatter:on
 
                        // If no parent store, promote bs to bootstrap and 
layer a fresh per-resource store on top.
+                       // NOTE: Stays on legacy `BasicBeanStore.create()...` 
chain (vs `new BasicBeanStore2(null, X)`)
+                       // because downstream consumers 
(`RestSession.java:240`, `VarResolver.java:260`) still
+                       // downcast `RestContext.getBeanStore()` / 
`builder.beanStore()` to `BasicBeanStore` to call
+                       // the legacy `BasicBeanStore.of(...)` static. 
Migrating those sites requires either
+                       // widening the field types of those consumers or 
porting `BasicBeanStore.of(...)` onto
+                       // `BasicBeanStore2` (Phase 4).
                        if (parentBs == null) {
                                bootstrapBeanStore = bs;
                                bs = 
BasicBeanStore.create().overridingParent((BasicBeanStore) 
bootstrapBeanStore).build();
@@ -2667,7 +2674,7 @@ public class RestContext extends Context {
                var params = mi.getParameters();
                var ra = new RestOpArg[params.size()];
 
-               var bs = BasicBeanStore.of((BasicBeanStore) beanStore);
+               var bs = new BasicBeanStore2(beanStore);
                var roa = getRestOpArgs();
 
                for (var i = 0; i < params.size(); i++) {
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContext.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContext.java
index c91bad5c5a..39f9b2d2ba 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContext.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContext.java
@@ -40,6 +40,7 @@ import org.apache.juneau.*;
 import org.apache.juneau.commons.annotation.*;
 import org.apache.juneau.commons.collections.FluentMap;
 import org.apache.juneau.commons.function.Memoizer;
+import org.apache.juneau.commons.inject.BasicBeanStore2;
 import org.apache.juneau.commons.inject.WritableBeanStore;
 import org.apache.juneau.commons.lang.*;
 import org.apache.juneau.commons.reflect.*;
@@ -213,7 +214,7 @@ public class RestOpContext extends Context implements 
Comparable<RestOpContext>
                        return restContext().getBeanContext();
                Value<BeanContext.Builder> v = Value.of(parent.copy());
                v.get().apply(aa);
-               var bs = BasicBeanStore.of((BasicBeanStore) beanStore())
+               var bs = new BasicBeanStore2(beanStore())
                        .addBean(Method.class, method())
                        .addBean(BeanContext.Builder.class, v.get());
                bs.createBeanFromMethod(BeanContext.class, resource(), 
this::matchesInjectScope)
@@ -433,7 +434,7 @@ public class RestOpContext extends Context implements 
Comparable<RestOpContext>
         * method scope) REPLACES the result entirely.
         */
        private final Memoizer<EncoderSet> encoders = memoizer(() -> {
-               var bs = (BasicBeanStore) beanStore();
+               var bs = beanStore();
                var b = restContext().getEncodersBuilder().copy();
                getRestOpAnnotationsForProperty(PROPERTY_encoders).forEach(ai 
-> {
                        var c = ai.getClassArray("encoders", 
Encoder.class).orElse(null);
@@ -543,7 +544,7 @@ public class RestOpContext extends Context implements 
Comparable<RestOpContext>
                        return restContext().getJsonSchemaGenerator();
                Value<JsonSchemaGenerator.Builder> v = Value.of(parent.copy());
                v.get().apply(aa);
-               var bs = BasicBeanStore.of((BasicBeanStore) beanStore())
+               var bs = new BasicBeanStore2(beanStore())
                        .addBean(Method.class, method())
                        .addBean(JsonSchemaGenerator.Builder.class, v.get());
                bs.createBeanFromMethod(JsonSchemaGenerator.class, resource(), 
this::matchesInjectScope)
@@ -661,7 +662,7 @@ public class RestOpContext extends Context implements 
Comparable<RestOpContext>
                        return restContext().getPartParser();
                Value<HttpPartParser.Creator> v = Value.of(parent.copy());
                v.get().apply(aa);
-               var bs = BasicBeanStore.of((BasicBeanStore) beanStore())
+               var bs = new BasicBeanStore2(beanStore())
                        .addBean(Method.class, method())
                        .addBean(HttpPartParser.Creator.class, v.get());
                bs.createBeanFromMethod(HttpPartParser.class, resource(), 
this::matchesInjectScope)
@@ -677,7 +678,7 @@ public class RestOpContext extends Context implements 
Comparable<RestOpContext>
                        return restContext().getPartSerializer();
                Value<HttpPartSerializer.Creator> v = Value.of(parent.copy());
                v.get().apply(aa);
-               var bs = BasicBeanStore.of((BasicBeanStore) beanStore())
+               var bs = new BasicBeanStore2(beanStore())
                        .addBean(Method.class, method())
                        .addBean(HttpPartSerializer.Creator.class, v.get());
                bs.createBeanFromMethod(HttpPartSerializer.class, resource(), 
this::matchesInjectScope)
diff --git a/todo/TODO-15-replace-basicbeanstore-with-v2.md 
b/todo/TODO-15-replace-basicbeanstore-with-v2.md
index 7242b21c70..55d0a2f5bb 100644
--- a/todo/TODO-15-replace-basicbeanstore-with-v2.md
+++ b/todo/TODO-15-replace-basicbeanstore-with-v2.md
@@ -13,19 +13,22 @@ Eliminate the legacy injection stack in 
`org.apache.juneau.cp` (`BasicBeanStore`
 - ~~`BeanCreator.of(Class, BeanStore)` overload~~ — **DONE (2026-05-08).** 
Widened `BeanCreator` to accept any `BeanStore` parent (legacy or v2): added 
`of(Class, BeanStore)` static factory, changed protected ctor to `(Class, 
BeanStore)` with internal branch (legacy parent → `BasicBeanStore.of(legacy)`; 
v2 parent → `new BasicBeanStore2(parent)`), widened `store` field to 
`WritableBeanStore`, replaced `store.add(...)` with `store.addBean(...)`. 
Legacy `of(Class, BasicBeanStore)` overload  [...]
 - ~~`BeanBuilder<T>` widening to `WritableBeanStore`~~ — **DONE 
(2026-05-08).** Field, constructor, and public `beanStore()` accessor all 
flipped from `BasicBeanStore` to `WritableBeanStore` (chosen over read-only 
`BeanStore` so callers retaining write access — e.g. 
`VarResolver.Builder.bean(...)` calling `super.beanStore().addBean(...)` — keep 
working). All 14 cascade-builder `super(X.class, (BasicBeanStore) beanStore)` 
casts dropped. Two standalone Builders (`SwaggerProvider.Builder.be [...]
 - ~~Four-memoizer migration to `BeanInstantiator` (Phase 3 sub-task)~~ — 
**ATTEMPTED + REVERTED (2026-05-08).** `callLogger` / `debugEnablement` / 
`staticFiles` / `swaggerProvider` were migrated to 
`BeanInstantiator.of(...).beanSubType(...).run()`; this broke documented 
`@Rest(callLogger=…)` / `@Rest(debugEnablement=…)` / `@Rest(swaggerProvider=…)` 
annotation overrides (3 `Rest_BeanCreatorOverrides_Test` failures) plus 
`juneau-examples-rest-jetty-ftest` (static files no longer served — ` [...]
+- ~~Phase 3 batch-3: drop vestigial `(BasicBeanStore)` casts at 
framework-defaults call sites~~ — **DONE (2026-05-08).** Sixteen 
`(BasicBeanStore) bs` casts in `RestContext.java` (lines 494, 515, 584, 676, 
753, 768, 914, 937, 957, 987, 1008, 1029, 1064, 1110, 1125) and one in 
`RestOpContext.java` (line 437) dropped. These were vestigial leftovers from 
before the utility-class `create(...)` factories were widened to 
`WritableBeanStore` in the cascade-builder work. The cast was no longer r [...]
 
-**Current remaining footprint (as of 2026-05-08, post-`BeanCreator` 
widening):**
+**Current remaining footprint (as of 2026-05-08, post-batch-3):**
 
 | Location | Legacy symbol | Nature |
 |---|---|---|
-| `RestContext.java` | `BasicBeanStore`, `BeanCreator` | 6 
`BeanCreator.of(...)` call sites (4 memoizers + user-child-resource path + 
`findRestOperationArgs`) — **all cast-free** thanks to `BeanCreator.of(Class, 
BeanStore)`; staying on legacy `BeanCreator` until **TODO-25** lands. Plus 3 
direct `BasicBeanStore.of(...)` / 
`BasicBeanStore.create().overridingParent((BasicBeanStore) parentBs)` calls — 
these are direct legacy-static API and still require the `(BasicBeanStore)` 
downcast. |
-| `RestOpContext.java` | `BasicBeanStore`, `BeanCreator` | 6 
`BasicBeanStore.of((BasicBeanStore) beanStore())` patterns (legacy 
`BasicBeanStore.of(...)` static still requires `BasicBeanStore`) + 
`BeanCreator.of(HttpPartSerializer.class).type(c)` for `partSerializer` (no 
cast — uses no-arg overload). |
+| `RestContext.java` | `BasicBeanStore`, `BeanCreator` | 6 
`BeanCreator.of(...)` call sites (4 memoizers + user-child-resource path + 
`findRestOperationArgs`) — **all cast-free** thanks to `BeanCreator.of(Class, 
BeanStore)`; staying on legacy `BeanCreator` until **TODO-25** lands. Plus 2 
direct legacy Builder-API calls 
(`BasicBeanStore.create().overridingParent((BasicBeanStore) X).build()` lines 
348, 1206) using the legacy static API. |
+| `RestOpContext.java` | `BasicBeanStore`, `BeanCreator` | 1 
`BasicBeanStore.of((BasicBeanStore) context.getBootstrapBeanStore())` (line 
1097) — registers the result as `BasicBeanStore.class` for user-facing 
`@RestPostCall`/`@RestStartCall` hook param resolution; cannot migrate without 
breaking that contract. + `BeanCreator.of(HttpPartSerializer.class).type(c)` 
for `partSerializer` (no cast — uses no-arg overload). |
+| `RestSession.java` | `cp.BasicBeanStore` | 1 
`BasicBeanStore.of((BasicBeanStore) context.getBeanStore())` site (line 240); 
requires widening private `beanStore` field + public `getBeanStore()` return 
type to migrate. |
+| `VarResolver.java` | `cp.BasicBeanStore` | 1 
`BasicBeanStore.of((BasicBeanStore) builder.beanStore())` site (line 260); 
requires widening package-private field + public 
`createSession(BasicBeanStore)` method. |
 | ~~`BeanBuilder<T>` cascade builders~~ | ~~`BasicBeanStore` cast in 
`super(...)`~~ | **RESOLVED (2026-05-08).** All 14 cascade-builder casts 
dropped after widening `BeanBuilder<T>` to accept `WritableBeanStore`. |
-| `RestInject.java`, `RestInit.java` | `cp.BasicBeanStore` | Javadoc only — 
trivial update |
-| `McpPage.java`, `McpTypedHandlers.java`, `McpEndpoint.java`, 
`McpRestServlet.java` | `cp.BasicBeanStore` | live usage in `rest-server-mcp` |
-| `Name.java`, `Named.java` | `cp.BasicBeanStore` | Javadoc / annotation 
`@see` only |
-| `HttpPartParser.java`, `HttpPartSerializer.java` | `BeanCreateMethodFinder` 
| 1 reference each — likely Javadoc |
-| `BeanStore_Test.java` | `BeanCreateMethodFinder` | 2 test references |
+| ~~`RestInject.java`, `RestInit.java`~~ | ~~`cp.BasicBeanStore`~~ | 
**RESOLVED (2026-05-08, batch 2).** Javadoc-only refs flipped to v2 
`BeanStore`. |
+| ~~`McpPage.java`, `McpTypedHandlers.java`, `McpEndpoint.java`, 
`McpRestServlet.java`~~ | ~~`cp.BasicBeanStore`~~ | **RESOLVED (2026-05-08, 
batch 2).** rest-server-mcp module fully migrated to v2 `BeanStore`. |
+| ~~`Name.java`, `Named.java`~~ | ~~`cp.BasicBeanStore`~~ | **RESOLVED 
(2026-05-08, batch 2).** Javadoc / annotation `@see` only — flipped to v2 
`BeanStore`. |
+| `HttpPartParser.java`, `HttpPartSerializer.java` | `ContextBeanCreator` | 
`Creator` inner class extends `ContextBeanCreator<...>` — gated by 
`ContextBeanCreator` migration to v2 (Phase 4). |
+| `BeanStore_Test.java` | `BeanCreateMethodFinder` | 2 test references — 
guards legacy class behavior; stays until removal. |
 
 ### Residual casts in `RestContext` / `RestOpContext` — root causes
 
@@ -35,10 +38,12 @@ Eliminate the legacy injection stack in 
`org.apache.juneau.cp` (`BasicBeanStore`
 
 3. **`BeanInstantiator` four-memoizer migration blocker.** Migrating 
`callLogger` / `debugEnablement` / `staticFiles` / `swaggerProvider` to 
`BeanInstantiator` broke documented `@Rest(callLogger=…)` / 
`@Rest(debugEnablement=…)` / `@Rest(swaggerProvider=…)` annotation overrides 
plus static-file serving (loose-builder fallthrough still picks empty-default 
builders for `BasicStaticFiles` etc.; `Basic*.init(BeanStore)` zero-outs 
builder defaults via `.orElse(null)` when optional beans aren't [...]
 
-4. **Direct `BasicBeanStore.of(...)` / 
`BasicBeanStore.create().overridingParent(...)` calls.** `RestSession`, 
`RestOpContext` (4 sites), and `RestContext` (3 sites) construct child bean 
stores via legacy static API that requires `BasicBeanStore` parents. 
Eliminating these requires either (a) porting `of(...)` / `create()` / 
`overridingParent(...)` onto `BasicBeanStore2` / `WritableBeanStore`, or (b) 
deferring until Phase 4 cutover when `BasicBeanStore2` is renamed to 
`BasicBeanStore` an [...]
+4. **Direct `BasicBeanStore.of(...)` / 
`BasicBeanStore.create().overridingParent(...)` calls (partially resolved 
2026-05-08).** Five transient internal sites in `RestOpContext` (4 lambdas) and 
`RestContext.findRestOperationArgs` migrated to `new 
BasicBeanStore2(beanStore())`. Four sites remain blocked: 
`RestContext.java:348` (Builder fluent chain with `.type(...)`/`.impl(...)` — 
needs equivalent v2 fluent API), `RestContext.java:1206` (per-resource bean 
store re-wrap exposed via public ` [...]
 
 5. ~~**`BeanBuilder<T>` parent-ctor signature.**~~ — **RESOLVED 
(2026-05-08).** `BeanBuilder<T>` field + ctor + public `beanStore()` accessor 
all flipped to `WritableBeanStore`. All 14 cascade-builder casts dropped.
 
+6. ~~**Vestigial `(BasicBeanStore) bs` casts at framework-defaults call 
sites.**~~ — **RESOLVED (2026-05-08, batch 3).** Sixteen casts in 
`RestContext.java` and one in `RestOpContext.java` dropped — utility-class 
`create(WritableBeanStore)` factories already accept the supertype, casts were 
leftover from before the cascade-builder migration.
+
 ### v2 API additions made in this PR (already landed)
 
 Promoted to the v2 surface so the `RestContext` / `RestOpContext` migration 
could land without forcing legacy casts inside those files:

Reply via email to