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


The following commit(s) were added to refs/heads/master by this push:
     new 2d753de  Context API refactoring.
2d753de is described below

commit 2d753de42f13eaaf2e8acb178af74d72bc1d0736
Author: JamesBognar <james.bog...@salesforce.com>
AuthorDate: Sun Sep 19 10:15:10 2021 -0400

    Context API refactoring.
---
 .../main/java/org/apache/juneau/BeanBuilder.java   | 190 ++++++++++
 .../java/org/apache/juneau/ContextProperties.java  |   7 +-
 .../org/apache/juneau/assertions/Assertion.java    |   9 +-
 .../juneau/assertions/FluentObjectAssertion.java   |  10 +
 .../apache/juneau/cp/BeanCreateMethodFinder.java   |   4 +-
 .../java/org/apache/juneau/cp/BeanCreator.java     | 326 ++++++++++++++++
 .../main/java/org/apache/juneau/cp/BeanStore.java  | 261 ++++---------
 .../main/java/org/apache/juneau/cp/FileFinder.java |  95 ++---
 .../main/java/org/apache/juneau/cp/Messages.java   | 131 ++++---
 .../org/apache/juneau/encoders/EncoderGroup.java   |  95 ++---
 .../org/apache/juneau/http/header/HeaderList.java  |  62 +--
 .../java/org/apache/juneau/http/part/PartList.java |  55 ++-
 .../juneau/httppart/bean/RequestBeanMeta.java      |   4 +-
 .../httppart/bean/RequestBeanPropertyMeta.java     |   4 +-
 .../org/apache/juneau/mstat/MethodExecStats.java   |  82 ++--
 .../org/apache/juneau/mstat/MethodExecStore.java   | 102 ++---
 .../apache/juneau/mstat/ThrownStatsBuilder.java    |   2 +-
 .../java/org/apache/juneau/mstat/ThrownStore.java  | 104 ++---
 .../org/apache/juneau/reflect/ExecutableInfo.java  |  14 +-
 .../java/org/apache/juneau/svl/VarResolver.java    |  91 +++--
 .../org/apache/juneau/rest/client/RestClient.java  |   6 +-
 .../rest/client/remote/RemoteOperationArg.java     |   2 +-
 .../org/apache/juneau/rest/BasicStaticFiles.java   |  34 +-
 .../org/apache/juneau/rest/DebugEnablement.java    |   3 +-
 .../apache/juneau/rest/ResponseProcessorList.java  |   2 +-
 .../java/org/apache/juneau/rest/RestChildren.java  |   5 +-
 .../java/org/apache/juneau/rest/RestContext.java   |   8 +-
 .../org/apache/juneau/rest/RestContextBuilder.java |  13 +-
 .../org/apache/juneau/rest/RestConverterList.java  |   2 +-
 .../java/org/apache/juneau/rest/RestGuardList.java |   2 +-
 .../org/apache/juneau/rest/RestMatcherList.java    |   2 +-
 .../java/org/apache/juneau/rest/RestOpContext.java |  30 +-
 .../apache/juneau/rest/RestOpContextBuilder.java   |   4 +-
 .../org/apache/juneau/rest/RestOperations.java     |   3 +-
 .../java/org/apache/juneau/rest/StaticFiles.java   | 127 +++++--
 .../org/apache/juneau/rest/SwaggerProvider.java    |   3 +-
 .../org/apache/juneau/rest/logging/RestLogger.java |   3 +-
 .../org/apache/juneau/cp/BeanCreator_Test.java     | 419 +++++++++++++++++++++
 .../java/org/apache/juneau/cp/BeanStore_Test.java  | 373 +++---------------
 .../apache/juneau/mstat/MethodExecStore_Test.java  |  12 +-
 .../org/apache/juneau/mstat/ThrownStore_Test.java  |  12 +-
 41 files changed, 1652 insertions(+), 1061 deletions(-)

diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/BeanBuilder.java 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/BeanBuilder.java
new file mode 100644
index 0000000..c12fcbb
--- /dev/null
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/BeanBuilder.java
@@ -0,0 +1,190 @@
+// 
***************************************************************************************************************************
+// * Licensed to the Apache Software Foundation (ASF) under one or more 
contributor license agreements.  See the NOTICE file *
+// * distributed with this work for additional information regarding copyright 
ownership.  The ASF licenses this file        *
+// * to you under the Apache License, Version 2.0 (the "License"); you may not 
use this file except in compliance            *
+// * with the License.  You may obtain a copy of the License at                
                                              *
+// *                                                                           
                                              *
+// *  http://www.apache.org/licenses/LICENSE-2.0                               
                                              *
+// *                                                                           
                                              *
+// * Unless required by applicable law or agreed to in writing, software 
distributed under the License is distributed on an  *
+// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either 
express or implied.  See the License for the        *
+// * specific language governing permissions and limitations under the 
License.                                              *
+// 
***************************************************************************************************************************
+package org.apache.juneau;
+
+import static org.apache.juneau.internal.ExceptionUtils.*;
+import static java.util.Optional.*;
+
+import java.util.*;
+
+import org.apache.juneau.cp.*;
+import org.apache.juneau.internal.*;
+
+/**
+ * Base class for bean builders.
+ *
+ * @param <T> The bean type that the builder creates.
+ */
+public class BeanBuilder<T> {
+
+       private Class<? extends T> type, defaultType;
+       private T impl;
+       private Object outer;
+       private BeanStore beanStore = BeanStore.INSTANCE;
+
+       /**
+        * Constructor.
+        *
+        * @param defaultType The default bean type that this builder creates.
+        */
+       protected BeanBuilder(Class<? extends T> defaultType) {
+               this.defaultType = type = defaultType;
+       }
+
+       /**
+        * Copy constructor.
+        *
+        * @param copyFrom The bean store to copy from.
+        */
+       protected BeanBuilder(BeanBuilder<T> copyFrom) {
+               type = copyFrom.type;
+               impl = copyFrom.impl;
+               outer = copyFrom.outer;
+               beanStore = copyFrom.beanStore;
+       }
+
+       /**
+        * Creates a copy of this builder.
+        *
+        * @return A copy of this builder.
+        */
+       public BeanBuilder<T> copy() {
+               return new BeanBuilder<>(this);
+       }
+
+       /**
+        * Creates the bean.
+        *
+        * @return A new bean.
+        */
+       public T build() {
+               if (impl != null)
+                       return impl;
+               if (type == null || type == defaultType)
+                       return buildDefault();
+               return beanStore
+                       .creator(type().orElseThrow(()->runtimeException("Type 
not specified.")))
+                       .outer(outer)
+                       .builder(this)
+                       .run();
+       }
+
+       /**
+        * Creates the bean when the bean type is <jk>null</jk> or is the 
default value.
+        *
+        * @return A new bean.
+        */
+       protected T buildDefault() {
+               return beanStore
+                       .creator(type().orElseThrow(()->runtimeException("Type 
not specified.")))
+                       .outer(outer)
+                       .builder(this)
+                       .run();
+       }
+
+       /**
+        * Overrides the bean type produced by the {@link #build()} method.
+        *
+        * <p>
+        * Use this method if you want to instantiated a bean subclass.
+        *
+        * @param value The setting value.
+        * @return  This object.
+        */
+       @FluentSetter
+       public BeanBuilder<T> type(Class<? extends T> value) {
+               type = value;
+               return this;
+       }
+
+       /**
+        * Returns the implementation type specified via {@link #type(Class)}.
+        *
+        * @return The implementation type specified via {@link #type(Class)}.
+        */
+       protected Optional<Class<? extends T>> type() {
+               return ofNullable(type);
+       }
+
+       /**
+        * Overrides the bean returned by the {@link #build()} method.
+        *
+        * <p>
+        * Use this method if you want this builder to return an 
already-instantiated bean.
+        *
+        * @param value The setting value.
+        * @return  This object.
+        */
+       public BeanBuilder<T> impl(T value) {
+               this.impl = value;
+               return this;
+       }
+
+       /**
+        * Returns the override bean specified via {@link #impl(Object)}.
+        *
+        * @return The override bean specified via {@link #impl(Object)}.
+        */
+       protected Optional<T> impl() {
+               return ofNullable(impl);
+       }
+
+       /**
+        * Specifies the outer bean context.
+        *
+        * <p>
+        * This should be the instance of the outer object such as the servlet 
object when constructing inner classes
+        * of the servlet class.
+        *
+        * @param value The setting value.
+        * @return  This object.
+        */
+       @FluentSetter
+       public BeanBuilder<T> outer(Object value) {
+               outer = value;
+               return this;
+       }
+
+       /**
+        * Returns the outer bean context specified via {@link #outer(Object)}.
+        *
+        * @return The outer bean context specified via {@link #outer(Object)}.
+        */
+       public Optional<Object> outer() {
+               return ofNullable(outer);
+       }
+
+       /**
+        * The bean store to use for instantiating the bean.
+        *
+        * <p>
+        * The bean store can be used to inject beans into parameters of the 
constructor of the bean.
+        *
+        * @param value The setting value.
+        * @return  This object.
+        */
+       @FluentSetter
+       public BeanBuilder<T> beanStore(BeanStore value) {
+               beanStore = value;
+               return this;
+       }
+
+       /**
+        * Returns the bean store specified via {@link #outer(Object)}.
+        *
+        * @return The bean store specified via {@link #outer(Object)}.
+        */
+       public Optional<BeanStore> beanStore() {
+               return ofNullable(beanStore);
+       }
+}
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/ContextProperties.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/ContextProperties.java
index 6522d3f..eededa1 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/ContextProperties.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/ContextProperties.java
@@ -918,11 +918,8 @@ public final class ContextProperties {
                if (ClassInfo.of(c).isParentOf(value.getClass()))
                        return (T)value;
                try {
-                       if 
(ClassInfo.of(value.getClass()).isChildOf(Class.class)) {
-                               if (beanStore == null)
-                                       beanStore = BeanStore.INSTANCE;
-                               return beanStore.createBean((Class<T>)value);
-                       }
+                       if 
(ClassInfo.of(value.getClass()).isChildOf(Class.class))
+                               return 
BeanCreator.create((Class<T>)value).store(beanStore).run();
                } catch (ExecutableException e) {
                        throw new ConfigException(e, "Could not create bean of 
type ''{0}''.", value);
                }
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/Assertion.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/Assertion.java
index fe2409f..a796f15 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/Assertion.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/Assertion.java
@@ -221,7 +221,14 @@ public class Assertion {
                        out.println(msg);
                if (throwable != null) {
                        try {
-                               throw 
BeanStore.create().build().addBean(Throwable.class, 
cause).addBean(String.class, msg).addBean(Object[].class,new 
Object[0]).createBean(throwable);
+                               throw BeanStore
+                                       .create()
+                                       .build()
+                                       .addBean(Throwable.class, cause)
+                                       .addBean(String.class, msg)
+                                       .addBean(Object[].class,new Object[0])
+                                       .creator(throwable)
+                                       .run();
                        } catch (ExecutableException e) {
                                // If we couldn't create requested exception, 
just throw a RuntimeException.
                                throw runtimeException(cause, msg);
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/FluentObjectAssertion.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/FluentObjectAssertion.java
index 3d303ef..b3ebb57 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/FluentObjectAssertion.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/assertions/FluentObjectAssertion.java
@@ -244,6 +244,16 @@ public class FluentObjectAssertion<T,R> extends 
FluentAssertion<R> {
        }
 
        /**
+        * Applies a transform on the inner object and returns a new inner 
object.
+        *
+        * @param function The function to apply.
+        * @return This object (for method chaining).
+        */
+       public <T2> FluentObjectAssertion<T2,R> transform(Function<T,T2> 
function) {
+               return new FluentObjectAssertion<>(this, 
function.apply(orElse(null)), returns());
+       }
+
+       /**
         * Converts this assertion into an {@link FluentAnyAssertion} so that 
it can be converted to other assertion types.
         *
         * @return This object (for method chaining).
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreateMethodFinder.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreateMethodFinder.java
index d0dede0..73e35d0 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreateMethodFinder.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreateMethodFinder.java
@@ -25,7 +25,7 @@ import org.apache.juneau.reflect.*;
 /**
  * Used for finding methods on an object that take in arbitrary parameters and 
returns bean instances.
  *
- * See {@link BeanStore#beanCreateMethodFinder(Class, Object)} for usage.
+ * See {@link BeanStore#createMethodFinder(Class, Object)} for usage.
  *
  * @param <T> The bean type being created.
  */
@@ -86,7 +86,7 @@ public class BeanCreateMethodFinder<T> {
         * This method can be called multiple times with different method names 
or required parameters until a match is found.
         * <br>Once a method is found, subsequent calls to this method will be 
no-ops.
         *
-        * See {@link BeanStore#beanCreateMethodFinder(Class, Object)} for 
usage.
+        * See {@link BeanStore#createMethodFinder(Class, Object)} for usage.
         *
         * @param methodName The method name.
         * @param requiredParams Optional required parameters.
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreator.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreator.java
new file mode 100644
index 0000000..4f7d0a8
--- /dev/null
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanCreator.java
@@ -0,0 +1,326 @@
+// 
***************************************************************************************************************************
+// * Licensed to the Apache Software Foundation (ASF) under one or more 
contributor license agreements.  See the NOTICE file *
+// * distributed with this work for additional information regarding copyright 
ownership.  The ASF licenses this file        *
+// * to you under the Apache License, Version 2.0 (the "License"); you may not 
use this file except in compliance            *
+// * with the License.  You may obtain a copy of the License at                
                                              *
+// *                                                                           
                                              *
+// *  http://www.apache.org/licenses/LICENSE-2.0                               
                                              *
+// *                                                                           
                                              *
+// * Unless required by applicable law or agreed to in writing, software 
distributed under the License is distributed on an  *
+// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either 
express or implied.  See the License for the        *
+// * specific language governing permissions and limitations under the 
License.                                              *
+// 
***************************************************************************************************************************
+package org.apache.juneau.cp;
+
+import static java.util.stream.Collectors.*;
+import static org.apache.juneau.reflect.ReflectFlags.*;
+
+import java.lang.annotation.*;
+import java.util.*;
+import java.util.function.*;
+
+import org.apache.juneau.*;
+import org.apache.juneau.annotation.*;
+import org.apache.juneau.collections.*;
+import org.apache.juneau.reflect.*;
+
+/**
+ * Utility class for creating beans.
+ * 
+ * @param <T> The bean type being created.
+ */
+public class BeanCreator<T> {
+
+       private ClassInfo type;
+       private BeanStore store = BeanStore.INSTANCE;
+       private Object outer;
+       private Object builder;
+       private boolean findSingleton;
+
+       /**
+        * Static creator.
+        *
+        * @param type The bean type being created.
+        * @return A new creator object.
+        */
+       public static <T> BeanCreator<T> create(Class<T> type) {
+               return new BeanCreator<>(type);
+       }
+
+       /**
+        * Constructor.
+        *
+        * @param type The bean type being created.
+        */
+       protected BeanCreator(Class<T> type) {
+               this.type = ClassInfo.ofc(type);
+       }
+
+       /**
+        * Allows you to specify a subclass of the specified bean type to 
create.
+        *
+        * @param value The value for this setting.
+        * @return This object.
+        */
+       public BeanCreator<T> type(Class<?> value) {
+               if (value != null && ! type.inner().isAssignableFrom(value))
+                       throw new ExecutableException("Could not instantiate 
class of type {0} because it was not a subtype of the class: {1}.", type, 
value);
+               type = ClassInfo.ofc(value);
+               return this;
+       }
+
+       /**
+        * Specifies a bean store for looking up matching parameters on 
constructors and static creator methods.
+        *
+        * @param value The value for this setting.
+        * @return This object.
+        */
+       public BeanCreator<T> store(BeanStore value) {
+               if (value != null)
+                       store = value;
+               return this;
+       }
+
+       /**
+        * Specifies the outer "this" parameter to an inner class constructor.
+        *
+        * @param value The value for this setting.
+        * @return This object.
+        */
+       public BeanCreator<T> outer(Object value) {
+               outer = value;
+               return this;
+       }
+
+       /**
+        * Specifies a builder object for the bean type.
+        *
+        * @param value The value for this setting.
+        * @return This object.
+        */
+       public BeanCreator<T> builder(Object value) {
+               builder = value;
+               return this;
+       }
+
+       /**
+        * Specifies to look for the existence of a <c>getInstance()</c> method 
that returns a singleton.
+        *
+        * @return This object.
+        */
+       public BeanCreator<T> findSingleton() {
+               findSingleton = true;
+               return this;
+       }
+
+       /**
+        * Creates the bean.
+        *
+        * @return A new bean.
+        */
+       public T run() {
+               if (type == null)
+                       return null;
+
+               String found = null;
+
+               // Look for getInstance().
+               if (builder == null || findSingleton)
+                       for (MethodInfo m : type.getPublicMethods())
+                               if (isSingletonMethod(m))
+                                       return m.invoke(null);
+
+               if (builder == null) {
+                       // Look for static creator methods.
+
+                       MethodInfo matchedCreator = null;
+                       int matchedCreatorParams = -1;
+
+                       // Look for static creator method.
+                       for (MethodInfo m : type.getPublicMethods()) {
+                               if (isStaticCreateMethod(m)) {
+                                       found = "STATIC_CREATOR";
+                                       if (hasAllParams(m.getParams())) {
+                                               if (m.getParamCount() > 
matchedCreatorParams) {
+                                                       matchedCreatorParams = 
m.getParamCount();
+                                                       matchedCreator = m;
+                                               }
+                                       }
+                               }
+                       }
+
+                       if (matchedCreator != null)
+                               return matchedCreator.invoke(null, 
getParams(matchedCreator.getParams()));
+               }
+
+               if (type.isInterface())
+                       throw new ExecutableException("Could not instantiate 
class {0}: {1}.", type.getName(), "Class is an interface");
+
+               if (type.isAbstract())
+                       throw new ExecutableException("Could not instantiate 
class {0}: {1}.", type.getName(), "Class is abstract");
+
+               ConstructorInfo matchedConstructor = null;
+               int matchedConstructorParams = -1;
+
+               // Look for public constructor.
+               for (ConstructorInfo cc : type.getPublicConstructors()) {
+                       if (found == null)
+                               found = "PUBLIC_CONSTRUCTOR";
+                       if (hasAllParams(cc.getParams())) {
+                               if (cc.getParamCount() > 
matchedConstructorParams) {
+                                       matchedConstructorParams = 
cc.getParamCount();
+                                       matchedConstructor = cc;
+                               }
+                       }
+               }
+
+               // Look for protected constructor.
+               if (matchedConstructor == null) {
+                       for (ConstructorInfo cc : 
type.getDeclaredConstructors()) {
+                               if (cc.isProtected()) {
+                                       if (found == null)
+                                               found = "PROTECTED_CONSTRUCTOR";
+                                       if (hasAllParams(cc.getParams())) {
+                                               if (cc.getParamCount() > 
matchedConstructorParams) {
+                                                       
matchedConstructorParams = cc.getParamCount();
+                                                       matchedConstructor = 
cc.accessible();
+                                               }
+                                       }
+                               }
+                       }
+               }
+
+               // Execute.
+               if (matchedConstructor != null)
+                       return 
matchedConstructor.invoke(getParams(matchedConstructor.getParams()));
+
+               if (builder == null) {
+                       // Look for static-builder/protected-constructor pair.
+                       for (ConstructorInfo cc2 : 
type.getDeclaredConstructors()) {
+                               if (cc2.getParamCount() == 1 && 
cc2.isVisible(Visibility.PROTECTED)) {
+                                       Class<?> pt = 
cc2.getParam(0).getParameterType().inner();
+                                       for (MethodInfo m : 
type.getPublicMethods()) {
+                                               if (isStaticCreateMethod(m, 
pt)) {
+                                                       Object builder = 
m.invoke(null);
+                                                       return 
cc2.accessible().invoke(builder);
+                                               }
+                                       }
+                               }
+                       }
+               }
+
+               String msg = null;
+               if (found == null) {
+                       msg = "No public/protected constructors found";
+               } else if (found.equals("STATIC_CREATOR")) {
+                       msg = "Static creator found but could not find 
prerequisites: " + type.getPublicMethods().stream().filter(x -> 
isStaticCreateMethod(x)).map(x -> 
getMissingParams(x.getParams())).sorted().collect(joining(" or "));
+               } else if (found.equals("PUBLIC_CONSTRUCTOR")) {
+                       msg = "Public constructor found but could not find 
prerequisites: " + type.getPublicConstructors().stream().map(x -> 
getMissingParams(x.getParams())).sorted().collect(joining(" or "));
+               } else {
+                       msg = "Protected constructor found but could not find 
prerequisites: " + type.getDeclaredConstructors().stream().filter(x -> 
x.isProtected()).map(x -> 
getMissingParams(x.getParams())).sorted().collect(joining(" or "));
+               }
+               throw new ExecutableException("Could not instantiate class {0}: 
{1}.", type.getName(), msg);
+       }
+
+       /**
+        * Converts this creator into a supplier.
+        *
+        * @return A supplier that returns the results of the {@link #run()} 
method.
+        */
+       public Supplier<T> supplier() {
+               return ()->run();
+       }
+
+       private boolean hasAllParams(List<ParamInfo> params) {
+               loop: for (int i = 0; i < params.size(); i++) {
+                       ParamInfo pi = params.get(i);
+                       ClassInfo pt = pi.getParameterType();
+                       ClassInfo ptu = pt.unwrap(Optional.class);
+                       if (i == 0 && ptu.isInstance(outer))
+                               continue loop;
+                       if (pt.is(Optional.class))
+                               continue loop;
+                       if (ptu.isInstance(builder))
+                                       continue loop;
+                       String beanName = findBeanName(pi);
+                       if (beanName == null)
+                               beanName = ptu.inner().getName();
+                       if (! store.hasBean(beanName))
+                               return false;
+               }
+               return true;
+       }
+
+       private boolean isStaticCreateMethod(MethodInfo m) {
+               return isStaticCreateMethod(m, type.inner());
+       }
+
+       private boolean isStaticCreateMethod(MethodInfo m, Class<?> type) {
+               return m.isAll(STATIC, NOT_DEPRECATED)
+                       && m.hasReturnType(type)
+                       && (!m.hasAnnotation(BeanIgnore.class))
+                       && m.getSimpleName().equals("create");
+       }
+
+       private boolean isSingletonMethod(MethodInfo m) {
+               return m.isAll(STATIC, NOT_DEPRECATED)
+                       && m.getParamCount() == 0
+                       && m.hasReturnType(type)
+                       && (!m.hasAnnotation(BeanIgnore.class))
+                       && m.getSimpleName().equals("getInstance");
+       }
+
+       private Object[] getParams(List<ParamInfo> params) {
+               Object[] o = new Object[params.size()];
+               for (int i = 0; i < params.size(); i++) {
+                       ParamInfo pi = params.get(i);
+                       ClassInfo pt = pi.getParameterType();
+                       ClassInfo ptu = pt.unwrap(Optional.class);
+                       if (i == 0 && ptu.isInstance(outer))
+                               o[i] = outer;
+                       else {
+                               if (pt.isInstance(builder))
+                                       o[i] = builder;
+                               else {
+                                       String beanName = findBeanName(pi);
+                                       if (pt.is(Optional.class)) {
+                                               o[i] = store.getBean(beanName, 
ptu.inner());
+                                       } else {
+                                               o[i] = store.getBean(beanName, 
ptu.inner()).get();
+                                       }
+                               }
+                       }
+               }
+               return o;
+       }
+
+       private String getMissingParams(List<ParamInfo> params) {
+               List<String> l = AList.create();
+               loop: for (int i = 0; i < params.size(); i++) {
+                       ParamInfo pi = params.get(i);
+                       ClassInfo pt = pi.getParameterType();
+                       ClassInfo ptu = pt.unwrap(Optional.class);
+                       if (i == 0 && ptu.isInstance(outer))
+                               continue loop;
+                       if (pt.is(Optional.class))
+                               continue loop;
+                       String beanName = findBeanName(pi);
+                       if (beanName != null) {
+                               if (! store.hasBean(beanName))
+                                       l.add(beanName);
+                       } else {
+                               if (! store.hasBean(pt.inner()))
+                                       l.add(pt.inner().getSimpleName());
+                       }
+               }
+               return l.stream().sorted().collect(joining(","));
+       }
+
+       private String findBeanName(ParamInfo pi) {
+               Optional<Annotation> namedAnnotation = 
pi.getAnnotations(Annotation.class).stream().filter(x->x.annotationType().getSimpleName().equals("Named")).findFirst();
+               if (namedAnnotation.isPresent())
+                       return AnnotationInfo.of((ClassInfo)null, 
namedAnnotation.get()).getValue(String.class, "value").orElse(null);
+               return null;
+       }
+
+}
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanStore.java 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanStore.java
index 0a032f3..161cf8b 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanStore.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/BeanStore.java
@@ -12,20 +12,14 @@
 // 
***************************************************************************************************************************
 package org.apache.juneau.cp;
 
-import static org.apache.juneau.internal.ClassUtils.*;
 import static org.apache.juneau.internal.ExceptionUtils.*;
-import static org.apache.juneau.internal.StringUtils.*;
-import static org.apache.juneau.reflect.ReflectFlags.*;
 import static java.util.Optional.*;
-
 import java.lang.annotation.*;
 import java.util.*;
 import java.util.concurrent.*;
 import java.util.function.*;
-import java.util.stream.*;
 
 import org.apache.juneau.*;
-import org.apache.juneau.annotation.*;
 import org.apache.juneau.collections.*;
 import org.apache.juneau.internal.*;
 import org.apache.juneau.reflect.*;
@@ -89,18 +83,17 @@ public class BeanStore {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<BeanStore> {
 
-               Class<? extends BeanStore> type = BeanStore.class;
-               BeanStore impl;
-               Object outer;
                BeanStore parent;
                boolean readOnly;
 
                /**
                 * Constructor.
                 */
-               protected Builder() {}
+               protected Builder() {
+                       super(BeanStore.class);
+               }
 
                /**
                 * Copy constructor.
@@ -108,40 +101,25 @@ public class BeanStore {
                 * @param copyFrom The bean store to copy from.
                 */
                protected Builder(BeanStore copyFrom) {
-                       type = copyFrom.getClass();
-                       outer = copyFrom.outer.orElse(null);
+                       super(copyFrom.getClass());
                        parent = copyFrom.parent.orElse(null);
                        readOnly = copyFrom.readOnly;
                }
 
                /**
-                * Create a new {@link BeanStore} using this builder.
+                * Copy constructor.
                 *
-                * @return A new {@link BeanStore}
+                * @param copyFrom The bean store to copy from.
                 */
-               public BeanStore build() {
-                       try {
-                               if (impl != null)
-                                       return impl;
-                               if (type == BeanStore.class)
-                                       return new BeanStore(this);
-                               Class<? extends BeanStore> ic = 
isConcrete(type) ? type : BeanStore.class;
-                               return new BeanStore().addBeans(Builder.class, 
this).createBean(ic);
-                       } catch (ExecutableException e) {
-                               throw runtimeException(e);
-                       }
+               protected Builder(Builder copyFrom) {
+                       super(copyFrom);
+                       parent = copyFrom.parent;
+                       readOnly = copyFrom.readOnly;
                }
 
-               /**
-                * Specifies a subclass of {@link BeanStore} to create when the 
{@link #build()} method is called.
-                *
-                * @param value The new value for this setting.
-                * @return  This object.
-                */
-               @FluentSetter
-               public Builder type(Class<? extends BeanStore> value) {
-                       type = value;
-                       return this;
+               @Override /* BeanBuilder */
+               protected BeanStore buildDefault() {
+                       return new BeanStore(this);
                }
 
                /**
@@ -150,7 +128,7 @@ public class BeanStore {
                 * <p>
                 * Bean searches are performed recursively up this parent chain.
                 *
-                * @param value The new value for this setting.
+                * @param value The setting value.
                 * @return  This object.
                 */
                @FluentSetter
@@ -173,36 +151,38 @@ public class BeanStore {
                        return this;
                }
 
-               /**
-                * Specifies the outer bean context.
-                *
-                * <p>
-                * Used when calling {@link BeanStore#createBean(Class)} on a 
non-static inner class.
-                * This should be the instance of the outer object such as the 
servlet object when constructing inner classes
-                * of the servlet class.
-                *
-                * @param value The new value for this setting.
-                * @return  This object.
-                */
-               @FluentSetter
-               public Builder outer(Object value) {
-                       outer = value;
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends BeanStore> value) {
+                       super.type(value);
                        return this;
                }
 
-               /**
-                * Specifies an implementation of a bean store.
-                *
-                * <p>
-                * Causes the {@link #build()} method to return a predefined 
bean instead of a new one.
-                *
-                * @param value The bean that this builder should return.
-                * @return  This object.
-                */
+               @Override /* BeanBuilder */
                public Builder impl(BeanStore value) {
-                       this.impl = value;
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
                        return this;
                }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
@@ -227,7 +207,7 @@ public class BeanStore {
         */
        protected BeanStore(Builder builder) {
                this.parent = ofNullable(builder.parent);
-               this.outer = ofNullable(builder.outer);
+               this.outer = builder.outer();
                this.readOnly = builder.readOnly;
        }
 
@@ -381,6 +361,19 @@ public class BeanStore {
        }
 
        /**
+        * Removes a bean from this store.
+        *
+        * <p>
+        * This is equivalent to setting the bean type bean to <jk>null</jk>.
+        *
+        * @param c The bean type being removed.
+        * @return This object.
+        */
+       public BeanStore removeBean(Class<?> c) {
+               return addBean(c.getName(), null);
+       }
+
+       /**
         * Returns <jk>true</jk> if this factory contains the specified bean 
type instance.
         *
         * @param c The bean type to check.
@@ -405,139 +398,13 @@ public class BeanStore {
        }
 
        /**
-        * Creates a bean of the specified type.
+        * Instantiates a bean creator.
         *
-        * @param <T> The bean type to create.
-        * @param c The bean type to create.  Can be <jk>null</jk>.
-        * @return A newly-created bean, or <jk>null</jk> if the type was 
<jk>null</jk>.
-        * @throws ExecutableException If bean could not be created.
-        */
-       public <T> T createBean(Class<T> c) throws ExecutableException {
-
-               if (c == null)
-                       return null;
-
-               Optional<T> o = getBean(c);
-               if (o.isPresent())
-                       return o.get();
-
-               ClassInfo ci = ClassInfo.of(c);
-
-               Supplier<String> msg = null;
-
-               MethodInfo matchedCreator = null;
-               int matchedCreatorParams = -1;
-
-               for (MethodInfo m : ci.getPublicMethods()) {
-
-                       if (m.isAll(STATIC, NOT_DEPRECATED) && 
m.hasReturnType(c) && (!m.hasAnnotation(BeanIgnore.class))) {
-                               String n = m.getSimpleName();
-                               if (isOneOf(n, "create","getInstance")) {
-                                       List<ClassInfo> missing = 
getMissingParamTypes(m.getParams());
-                                       if (missing.isEmpty()) {
-                                               if (m.getParamCount() > 
matchedCreatorParams) {
-                                                       matchedCreatorParams = 
m.getParamCount();
-                                                       matchedCreator = m;
-                                               }
-                                       } else {
-                                               msg = ()-> "Static creator 
found but could not find prerequisites: " + 
missing.stream().map(x->x.getSimpleName()).collect(Collectors.joining(","));
-                                       }
-                               }
-                       }
-               }
-
-               if (matchedCreator != null)
-                       return matchedCreator.invoke(null, 
getParams(matchedCreator.getParams()));
-
-               if (ci.isInterface())
-                       throw new ExecutableException("Could not instantiate 
class {0}: {1}.", c.getName(), msg != null ? msg.get() : "Class is an 
interface");
-               if (ci.isAbstract())
-                       throw new ExecutableException("Could not instantiate 
class {0}: {1}.", c.getName(), msg != null ? msg.get() : "Class is abstract");
-
-               ConstructorInfo matchedConstructor = null;
-               int matchedConstructorParams = -1;
-
-               for (ConstructorInfo cc : ci.getPublicConstructors()) {
-                       List<ClassInfo> missing = 
getMissingParamTypes(cc.getParams());
-                       if (missing.isEmpty()) {
-                               if (cc.getParamCount() > 
matchedConstructorParams) {
-                                       matchedConstructorParams = 
cc.getParamCount();
-                                       matchedConstructor = cc;
-                               }
-                       } else {
-                               msg = ()-> "Public constructor found but could 
not find prerequisites: " + 
missing.stream().map(x->x.getSimpleName()).collect(Collectors.joining(","));
-                       }
-               }
-
-               if (matchedConstructor == null) {
-                       for (ConstructorInfo cc : ci.getDeclaredConstructors()) 
{
-                               if (cc.isProtected()) {
-                                       List<ClassInfo> missing = 
getMissingParamTypes(cc.getParams());
-                                       if (missing.isEmpty()) {
-                                               if (cc.getParamCount() > 
matchedConstructorParams) {
-                                                       
matchedConstructorParams = cc.getParamCount();
-                                                       matchedConstructor = 
cc.accessible();
-                                               }
-                                       } else {
-                                               msg = ()-> "Protected 
constructor found but could not find prerequisites: " + 
missing.stream().map(x->x.getSimpleName()).collect(Collectors.joining(","));
-                                       }
-                               }
-                       }
-               }
-
-               // Look for static-builder/protected-constructor pair.
-               if (matchedConstructor == null) {
-                       for (ConstructorInfo cc2 : 
ci.getDeclaredConstructors()) {
-                               if (cc2.getParamCount() == 1 && 
cc2.isVisible(Visibility.PROTECTED)) {
-                                       Class<?> pt = 
cc2.getParam(0).getParameterType().inner();
-                                       for (MethodInfo m : 
ci.getPublicMethods()) {
-                                               if (m.isAll(STATIC, 
NOT_DEPRECATED) && m.hasReturnType(pt) && (!m.hasAnnotation(BeanIgnore.class))) 
{
-                                                       Object builder = 
m.invoke(null);
-                                                       return 
cc2.accessible().invoke(builder);
-                                               }
-                                       }
-                               }
-                       }
-               }
-
-               if (matchedConstructor != null)
-                       return 
matchedConstructor.invoke(getParams(matchedConstructor.getParams()));
-
-               if (msg == null)
-                       msg = () -> "Public constructor or creator not found";
-
-               throw new ExecutableException("Could not instantiate class {0}: 
{1}.", c.getName(), msg.get());
-       }
-
-       /**
-        * Same as {@link #createBean(Class)} but allows you to validate that 
the specified type is of the specified parent class.
-        *
-        * @param <T> The bean type to create.
         * @param c The bean type to create.
-        * @param type The bean subtype to create.
-        * @return A newly-created bean.
-        * @throws ExecutableException If bean could not be created.
+        * @return A new bean creator.
         */
-       public <T> T createBean(Class<T> c, Class<? extends T> type) {
-               if (type != null && ! c.isAssignableFrom(type))
-                       throw new ExecutableException("Could not instantiate 
class of type {0} because it was not a subtype of the class: {1}.", 
c.getName(), type);
-               return createBean(type);
-       }
-
-       /**
-        * Same as {@link #createBean(Class)} but returns the bean creation 
wrapped in a supplier.
-        *
-        * @param c The bean type to create.
-        * @return A supplier for the newly-created bean.
-        */
-       public <T> Supplier<T> createBeanSupplier(Class<T> c) {
-               return () -> {
-                       try {
-                               return createBean(c);
-                       } catch (ExecutableException e) {
-                               throw runtimeException(e);
-                       }
-               };
+       public <T> BeanCreator<T> creator(Class<T> c) {
+               return new 
BeanCreator<>(c).store(this).outer(outer.orElse(null));
        }
 
        /**
@@ -578,7 +445,7 @@ public class BeanStore {
         * @param resource The class containing the bean creator method.
         * @return The created bean or the default value if method could not be 
found.
         */
-       public <T> BeanCreateMethodFinder<T> beanCreateMethodFinder(Class<T> c, 
Object resource) {
+       public <T> BeanCreateMethodFinder<T> createMethodFinder(Class<T> c, 
Object resource) {
                return new BeanCreateMethodFinder<>(c, resource, this);
        }
 
@@ -589,7 +456,7 @@ public class BeanStore {
         * @param resourceClass The class containing the bean creator method.
         * @return The created bean or the default value if method could not be 
found.
         */
-       public <T> BeanCreateMethodFinder<T> beanCreateMethodFinder(Class<T> c, 
Class<?> resourceClass) {
+       public <T> BeanCreateMethodFinder<T> createMethodFinder(Class<T> c, 
Class<?> resourceClass) {
                return new BeanCreateMethodFinder<>(c, resourceClass, this);
        }
 
@@ -613,14 +480,14 @@ public class BeanStore {
         */
        public List<ClassInfo> getMissingParamTypes(List<ParamInfo> params) {
                List<ClassInfo> l = AList.create();
-               for (int i = 0; i < params.size(); i++) {
+               loop: for (int i = 0; i < params.size(); i++) {
                        ParamInfo pi = params.get(i);
                        ClassInfo pt = pi.getParameterType();
                        ClassInfo ptu = pt.unwrap(Optional.class);
                        if (i == 0 && ptu.isInstance(outer.orElse(null)))
-                               continue;
+                               continue loop;
                        if (pt.is(Optional.class))
-                               continue;
+                               continue loop;
                        String beanName = findBeanName(pi);
                        if (beanName == null)
                                beanName = ptu.inner().getName();
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/FileFinder.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/FileFinder.java
index 82dac97..9c1ed4b 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/FileFinder.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/FileFinder.java
@@ -13,8 +13,6 @@
 package org.apache.juneau.cp;
 
 import static org.apache.juneau.assertions.Assertions.*;
-import static org.apache.juneau.internal.ClassUtils.*;
-import static org.apache.juneau.internal.ExceptionUtils.*;
 
 import java.io.*;
 import java.nio.file.*;
@@ -109,19 +107,17 @@ public interface FileFinder {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<FileFinder> {
 
                final Set<LocalDir> roots;
                long cachingLimit;
                List<Pattern> include, exclude;
-               Class<? extends FileFinder> type;
-               FileFinder impl;
-               BeanStore beanStore;
 
                /**
                 * Constructor.
                 */
                protected Builder() {
+                       super(BasicFileFinder.class);
                        roots = new LinkedHashSet<>();
                        cachingLimit = -1;
                        include = AList.of(Pattern.compile(".*"));
@@ -134,38 +130,16 @@ public interface FileFinder {
                 * @param copyFrom The builder being copied.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        roots = new LinkedHashSet<>(copyFrom.roots);
                        cachingLimit = copyFrom.cachingLimit;
                        include = AList.of(copyFrom.include);
                        exclude = AList.of(copyFrom.exclude);
-                       beanStore = copyFrom.beanStore;
-                       type = copyFrom.type;
-                       impl = copyFrom.impl;
                }
 
-               /**
-                * Create a new {@link FileFinder} using this builder.
-                *
-                * @return A new {@link FileFinder}
-                */
-               public FileFinder build() {
-                       try {
-                               if (impl != null)
-                                       return impl;
-                               Class<? extends FileFinder> ic = 
isConcrete(type) ? type : getDefaultType();
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
-                       } catch (ExecutableException e) {
-                               throw runtimeException(e);
-                       }
-               }
-
-               /**
-                * Returns the default bean type if not specified via {@link 
#type(Class)}.
-                *
-                * @return The default bean type.
-                */
-               protected Class<? extends FileFinder> getDefaultType() {
-                       return BasicFileFinder.class;
+               @Override /* BeanBuilder */
+               protected FileFinder buildDefault() {
+                       return new BasicFileFinder(this);
                }
 
                /**
@@ -250,53 +224,38 @@ public interface FileFinder {
                        return this;
                }
 
-               /**
-                * Specifies the bean store to use for instantiating the {@link 
FileFinder} object.
-                *
-                * <p>
-                * Can be used to instantiate {@link FileFinder} 
implementations with injected constructor argument beans.
-                *
-                * @param value The new value for this setting.
-                * @return  This object.
-                */
-               @FluentSetter
-               public Builder beanStore(BeanStore value) {
-                       this.beanStore = value;
-                       return this;
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
                }
 
-               /**
-                * Specifies a subclass of {@link FileFinder} to create when 
the {@link #build()} method is called.
-                *
-                * @param value The new value for this setting.
-                * @return  This object.
-                */
-               @FluentSetter
+               @Override /* BeanBuilder */
                public Builder type(Class<? extends FileFinder> value) {
-                       this.type = value;
+                       super.type(value);
                        return this;
                }
 
-               /**
-                * Specifies a pre-instantiated bean for the {@link #build()} 
method to return.
-                *
-                * @param value The value for this setting.
-                * @return This object.
-                */
-               @FluentSetter
+               @Override /* BeanBuilder */
                public Builder impl(FileFinder value) {
-                       this.impl = value;
+                       super.impl(value);
                        return this;
                }
 
-               /**
-                * Creates a copy of this builder.
-                *
-                * @return A copy of this builder.
-                */
-               public Builder copy() {
-                       return new Builder(this);
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
                }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/Messages.java 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/Messages.java
index 231cd13..daff73b 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/Messages.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/cp/Messages.java
@@ -21,6 +21,7 @@ import java.text.*;
 import java.util.*;
 import java.util.concurrent.*;
 
+import org.apache.juneau.*;
 import org.apache.juneau.collections.*;
 import org.apache.juneau.internal.*;
 import org.apache.juneau.marshall.*;
@@ -152,11 +153,10 @@ public class Messages extends ResourceBundle {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<Messages> {
 
                Class<?> forClass;
                Locale locale;
-               Messages impl;
                String name;
                Messages parent;
                List<Tuple2<Class<?>,String>> locations;
@@ -169,6 +169,7 @@ public class Messages extends ResourceBundle {
                 * @param forClass The base class.
                 */
                protected Builder(Class<?> forClass) {
+                       super(Messages.class);
                        this.forClass = forClass;
                        this.name = forClass.getSimpleName();
                        locations = new ArrayList<>();
@@ -181,14 +182,50 @@ public class Messages extends ResourceBundle {
                 * @param copyFrom The builder being copied.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        forClass = copyFrom.forClass;
                        locale = copyFrom.locale;
-                       impl = copyFrom.impl;
                        name = copyFrom.name;
                        parent = copyFrom.parent;
                        locations = new ArrayList<>(copyFrom.locations);
                }
 
+               @Override /* BeanBuilder */
+               protected Messages buildDefault() {
+
+                       if (! locations.isEmpty()) {
+                               Tuple2<Class<?>,String>[] mbl = 
locations.toArray(new Tuple2[0]);
+
+                               Builder x = null;
+
+                               for (int i = mbl.length-1; i >= 0; i--) {
+                                       Class<?> c = 
firstNonNull(mbl[i].getA(), forClass);
+                                       String value = mbl[i].getB();
+                                       if (isJsonObject(value, true)) {
+                                               MessagesString ms;
+                                               try {
+                                                       ms = 
SimpleJson.DEFAULT.read(value, MessagesString.class);
+                                               } catch (ParseException e) {
+                                                       throw 
runtimeException(e);
+                                               }
+                                               x = 
Messages.create(c).name(ms.name).baseNames(split(ms.baseNames, 
',')).locale(ms.locale).parent(x == null ? null : x.build());
+                                       } else {
+                                               x = 
Messages.create(c).name(value).parent(x == null ? null : x.build());
+                                       }
+                               }
+
+                               return x == null ? null : x.build();  // 
Shouldn't be null.
+                       }
+
+                       return new Messages(this);
+               }
+
+               private static class MessagesString {
+                       public String name;
+                       public String[] baseNames;
+                       public String locale;
+               }
+
                /**
                 * Adds a parent bundle.
                 *
@@ -258,17 +295,6 @@ public class Messages extends ResourceBundle {
                }
 
                /**
-                * Specifies a pre-instantiated bean for the {@link #build()} 
method to return.
-                *
-                * @param value The value for this setting.
-                * @return This object.
-                */
-               public Builder impl(Messages value) {
-                       this.impl = value;
-                       return this;
-               }
-
-               /**
                 * Specifies a location of where to look for messages.
                 *
                 * @param baseClass The base class.
@@ -280,49 +306,6 @@ public class Messages extends ResourceBundle {
                        return this;
                }
 
-               /**
-                * Creates a new {@link Messages} based on the setting of this 
builder.
-                *
-                * @return A new {@link Messages} object.
-                */
-               public Messages build() {
-
-                       if (impl != null)
-                               return impl;
-
-                       if (! locations.isEmpty()) {
-                               Tuple2<Class<?>,String>[] mbl = 
locations.toArray(new Tuple2[0]);
-
-                               Builder x = null;
-
-                               for (int i = mbl.length-1; i >= 0; i--) {
-                                       Class<?> c = 
firstNonNull(mbl[i].getA(), forClass);
-                                       String value = mbl[i].getB();
-                                       if (isJsonObject(value, true)) {
-                                               MessagesString ms;
-                                               try {
-                                                       ms = 
SimpleJson.DEFAULT.read(value, MessagesString.class);
-                                               } catch (ParseException e) {
-                                                       throw 
runtimeException(e);
-                                               }
-                                               x = 
Messages.create(c).name(ms.name).baseNames(split(ms.baseNames, 
',')).locale(ms.locale).parent(x == null ? null : x.build());
-                                       } else {
-                                               x = 
Messages.create(c).name(value).parent(x == null ? null : x.build());
-                                       }
-                               }
-
-                               return x == null ? null : x.build();  // 
Shouldn't be null.
-                       }
-
-                       return new Messages(this);
-               }
-
-               private static class MessagesString {
-                       public String name;
-                       public String[] baseNames;
-                       public String locale;
-               }
-
                ResourceBundle getBundle() {
                        ClassLoader cl = forClass.getClassLoader();
                        OMap m = OMap.of("name", name, "package", 
forClass.getPackage().getName());
@@ -335,14 +318,38 @@ public class Messages extends ResourceBundle {
                        return null;
                }
 
-               /**
-                * Creates a copy of this builder.
-                *
-                * @return A copy of this builder.
-                */
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
                public Builder copy() {
                        return new Builder(this);
                }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends Messages> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder impl(Messages value) {
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // <FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/encoders/EncoderGroup.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/encoders/EncoderGroup.java
index 870d8e8..9f6d5f6 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/encoders/EncoderGroup.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/encoders/EncoderGroup.java
@@ -103,19 +103,33 @@ public final class EncoderGroup {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<EncoderGroup> {
                List<Object> entries;
                Builder inheritFrom;
-               BeanStore beanStore = BeanStore.create().build();
 
-               Builder() {
+               /**
+                * Constructor.
+                */
+               protected Builder() {
+                       super(EncoderGroup.class);
                        entries = AList.create();
                }
 
-               Builder(Builder copyFrom) {
+               /**
+                * Copy constructor.
+                *
+                * @param copyFrom The builder being copied.
+                */
+               protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        entries = AList.of(copyFrom.entries);
                }
 
+               @Override /* BeanBuilder */
+               protected EncoderGroup buildDefault() {
+                       return new EncoderGroup(this);
+               }
+
                /**
                 * Registers the specified encoders with this group.
                 *
@@ -196,32 +210,6 @@ public final class EncoderGroup {
                }
 
                /**
-                * Associates a bean store with this builder.
-                *
-                * <p>
-                * Used for instantiating encoders specified via classes.
-                *
-                * @param value The new value for this setting.
-                * @return This object (for method chaining).
-                */
-               public Builder beanStore(BeanStore value) {
-                       beanStore = value;
-                       return this;
-               }
-
-               /**
-                * Creates a new {@link EncoderGroup} object using a snapshot 
of the settings defined in this builder.
-                *
-                * <p>
-                * This method can be called multiple times to produce multiple 
encoder groups.
-                *
-                * @return A new {@link EncoderGroup} object.
-                */
-               public EncoderGroup build() {
-                       return new EncoderGroup(this);
-               }
-
-               /**
                 * Returns <jk>true</jk> if this builder is empty.
                 *
                 * @return <jk>true</jk> if this builder is empty.
@@ -246,6 +234,39 @@ public final class EncoderGroup {
                        return entries;
                }
 
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends EncoderGroup> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder impl(EncoderGroup value) {
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
+
                @Override /* Object */
                public String toString() {
                        return entries.stream().map(x -> 
toString(x)).collect(joining(",","[","]"));
@@ -258,15 +279,6 @@ public final class EncoderGroup {
                                return "class:" + ((Class<?>)o).getSimpleName();
                        return "object:" + o.getClass().getSimpleName();
                }
-
-               /**
-                * Creates a copy of this builder.
-                *
-                * @return A copy of this builder.
-                */
-               public Builder copy() {
-                       return new Builder(this);
-               }
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
@@ -286,7 +298,7 @@ public final class EncoderGroup {
         * @param builder The builder for this object.
         */
        protected EncoderGroup(Builder builder) {
-               entries = builder.entries.stream().map(x -> 
instantiate(builder.beanStore, x)).toArray(Encoder[]::new);
+               entries = builder.entries.stream().map(x -> 
instantiate(builder.beanStore().orElse(BeanStore.INSTANCE), 
x)).toArray(Encoder[]::new);
 
                List<String> lc = AList.create();
                List<Encoder> l = AList.create();
@@ -301,12 +313,11 @@ public final class EncoderGroup {
                this.encodingsEncoders = l.toArray(new Encoder[l.size()]);
        }
 
-       @SuppressWarnings("unchecked")
        private static Encoder instantiate(BeanStore bs, Object o) {
                if (o instanceof Encoder)
                        return (Encoder)o;
                try {
-                       return bs.createBean(Encoder.class, (Class<? extends 
Encoder>)o);
+                       return 
bs.creator(Encoder.class).type((Class<?>)o).run();
                } catch (ExecutableException e) {
                        throw new RuntimeException(e);
                }
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/header/HeaderList.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/header/HeaderList.java
index a1c9f4b..b6026d9 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/header/HeaderList.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/header/HeaderList.java
@@ -24,6 +24,7 @@ import org.apache.http.*;
 import org.apache.http.util.*;
 import org.apache.juneau.*;
 import org.apache.juneau.annotation.*;
+import org.apache.juneau.cp.*;
 import org.apache.juneau.http.HttpHeaders;
 import org.apache.juneau.internal.*;
 import org.apache.juneau.svl.*;
@@ -240,11 +241,10 @@ public class HeaderList {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<HeaderList> {
 
                final List<Header> entries;
                List<Header> defaultEntries;
-               HeaderList impl;
                private VarResolver varResolver;
                boolean caseSensitive;
 
@@ -252,6 +252,7 @@ public class HeaderList {
                 * Constructor.
                 */
                public Builder() {
+                       super(HeaderList.class);
                        entries = new ArrayList<>();
                }
 
@@ -261,6 +262,7 @@ public class HeaderList {
                 * @param copyFrom The bean to copy from.
                 */
                protected Builder(HeaderList copyFrom) {
+                       super(copyFrom.getClass());
                        entries = new ArrayList<>(copyFrom.entries.length);
                        for (int i = 0; i < copyFrom.entries.length; i++)
                                entries.add(copyFrom.entries[i]);
@@ -273,29 +275,15 @@ public class HeaderList {
                 * @param copyFrom The bean to copy from.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        entries = new ArrayList<>(copyFrom.entries);
                        defaultEntries = copyFrom.defaultEntries == null ? null 
: new ArrayList<>(copyFrom.defaultEntries);
                        varResolver = copyFrom.varResolver;
                        caseSensitive = copyFrom.caseSensitive;
                }
 
-               /**
-                * Creates a modifiable copy of this builder.
-                *
-                * @return A shallow copy of this builder.
-                */
-               public Builder copy() {
-                       return new Builder(this);
-               }
-
-               /**
-                * Creates a new {@link HeaderList} bean based on the contents 
of this builder.
-                *
-                * @return A new {@link HeaderList} bean.
-                */
-               public HeaderList build() {
-                       if (impl != null)
-                               return impl;
+               @Override /* BeanBuilder */
+               protected HeaderList buildDefault() {
                        return entries.isEmpty() && defaultEntries == null ? 
EMPTY : new HeaderList(this);
                }
 
@@ -1157,17 +1145,39 @@ public class HeaderList {
                        return Optional.empty();
                }
 
-               /**
-                * Specifies a pre-instantiated bean for the {@link #build()} 
method to return.
-                *
-                * @param value The value for this setting.
-                * @return This object.
-                */
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends HeaderList> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
                public Builder impl(HeaderList value) {
-                       impl = value;
+                       super.impl(value);
                        return this;
                }
 
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
+
                @Override /* Object */
                public String toString() {
                        return "[" + join(entries, ", ") + "]";
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/part/PartList.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/part/PartList.java
index ebb80f0..b6ef8c1 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/part/PartList.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/http/part/PartList.java
@@ -24,6 +24,7 @@ import org.apache.http.*;
 import org.apache.http.util.*;
 import org.apache.juneau.*;
 import org.apache.juneau.annotation.*;
+import org.apache.juneau.cp.*;
 import org.apache.juneau.http.HttpParts;
 import org.apache.juneau.http.annotation.*;
 import org.apache.juneau.internal.*;
@@ -228,7 +229,7 @@ public class PartList {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<PartList> {
 
                final List<NameValuePair> entries;
                List<NameValuePair> defaultEntries;
@@ -239,6 +240,7 @@ public class PartList {
                 * Constructor.
                 */
                public Builder() {
+                       super(PartList.class);
                        entries = new ArrayList<>();
                }
 
@@ -248,6 +250,7 @@ public class PartList {
                 * @param copyFrom The bean to copy from.
                 */
                public Builder(PartList copyFrom) {
+                       super(copyFrom.getClass());
                        entries = new ArrayList<>(copyFrom.entries.length);
                        for (int i = 0; i < copyFrom.entries.length; i++)
                                entries.add(copyFrom.entries[i]);
@@ -260,27 +263,15 @@ public class PartList {
                 * @param copyFrom The bean to copy from.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        entries = new ArrayList<>(copyFrom.entries);
                        defaultEntries = copyFrom.defaultEntries == null ? null 
: new ArrayList<>(copyFrom.defaultEntries);
                        varResolver = copyFrom.varResolver;
                        caseInsensitive = copyFrom.caseInsensitive;
                }
 
-               /**
-                * Creates a modifiable copy of this builder.
-                *
-                * @return A shallow copy of this builder.
-                */
-               public Builder copy() {
-                       return new Builder(this);
-               }
-
-               /**
-                * Creates a new {@link PartList} bean based on the contents of 
this builder.
-                *
-                * @return A new {@link PartList} bean.
-                */
-               public PartList build() {
+               @Override /* BeanBuilder */
+               protected PartList buildDefault() {
                        return entries.isEmpty() && defaultEntries == null ? 
EMPTY : new PartList(this);
                }
 
@@ -1136,10 +1127,42 @@ public class PartList {
                        return Optional.empty();
                }
 
+               // <FluentSetters>
+
                @Override /* Object */
                public String toString() {
                        return "[" + join(entries, ", ") + "]";
                }
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends PartList> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder impl(PartList value) {
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanMeta.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanMeta.java
index 0534fa1..039f11c 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanMeta.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanMeta.java
@@ -67,8 +67,8 @@ public class RequestBeanMeta {
 
        RequestBeanMeta(Builder b) {
                this.cm = b.cm;
-               this.serializer = 
BeanStore.INSTANCE.createBean(HttpPartSerializer.class, b.serializer);
-               this.parser = 
BeanStore.INSTANCE.createBean(HttpPartParser.class, b.parser);
+               this.serializer = 
BeanCreator.create(HttpPartSerializer.class).type(b.serializer).run();
+               this.parser = 
BeanCreator.create(HttpPartParser.class).type(b.parser).run();
                Map<String,RequestBeanPropertyMeta> properties = new 
LinkedHashMap<>();
                for (Map.Entry<String,RequestBeanPropertyMeta.Builder> e : 
b.properties.entrySet())
                        properties.put(e.getKey(), 
e.getValue().build(serializer, parser));
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanPropertyMeta.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanPropertyMeta.java
index bcbb3e9..6f6b925 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanPropertyMeta.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/httppart/bean/RequestBeanPropertyMeta.java
@@ -50,8 +50,8 @@ public class RequestBeanPropertyMeta {
                this.partType = b.partType;
                this.schema = b.schema;
                this.getter = b.getter;
-               this.serializer = ofNullable(schema.getSerializer() == null ? 
serializer : BeanStore.INSTANCE.createBean(HttpPartSerializer.class, 
schema.getSerializer()));
-               this.parser = schema.getParser() == null ? parser : 
BeanStore.INSTANCE.createBean(HttpPartParser.class, schema.getParser());
+               this.serializer = ofNullable(schema.getSerializer() == null ? 
serializer : 
BeanCreator.create(HttpPartSerializer.class).type(schema.getSerializer()).run());
+               this.parser = schema.getParser() == null ? parser : 
BeanCreator.create(HttpPartParser.class).type(schema.getParser()).run();
        }
 
        static class Builder {
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStats.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStats.java
index 2160d1c..499ad3e 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStats.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStats.java
@@ -13,8 +13,6 @@
 package org.apache.juneau.mstat;
 
 import static java.util.Optional.*;
-import static org.apache.juneau.internal.ClassUtils.*;
-import static org.apache.juneau.internal.ExceptionUtils.*;
 import static org.apache.juneau.internal.StringUtils.*;
 
 import java.lang.reflect.*;
@@ -53,53 +51,32 @@ public class MethodExecStats {
         * Builder class.
         */
        @FluentSetters
-       public static class Builder {
+       public static class Builder extends BeanBuilder<MethodExecStats> {
 
                Method method;
                ThrownStore thrownStore;
 
-               Class<? extends MethodExecStats> implClass;
-               BeanStore beanStore;
-
                /**
-                * Create a new {@link MethodExecStats} using this builder.
-                *
-                * @return A new {@link ThrownStats}
+                * Constructor.
                 */
-               public MethodExecStats build() {
-                       try {
-                               Class<? extends MethodExecStats> ic = 
isConcrete(implClass) ? implClass : MethodExecStats.class;
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
-                       } catch (ExecutableException e) {
-                               throw runtimeException(e);
-                       }
+               protected Builder() {
+                       super(MethodExecStats.class);
                }
 
                /**
-                * Specifies the bean store to use for instantiating the {@link 
MethodExecStats} object.
+                * Copy constructor.
                 *
-                * <p>
-                * Can be used to instantiate {@link MethodExecStats} 
implementations with injected constructor argument beans.
-                *
-                * @param value The new value for this setting.
-                * @return  This object (for method chaining).
+                * @param copyFrom The builder being copied.
                 */
-               @FluentSetter
-               public Builder beanStore(BeanStore value) {
-                       beanStore = value;
-                       return this;
+               protected Builder(Builder copyFrom) {
+                       super(copyFrom);
+                       method = copyFrom.method;
+                       thrownStore = copyFrom.thrownStore;
                }
 
-               /**
-                * Specifies a subclass of {@link MethodExecStats} to create 
when the {@link #build()} method is called.
-                *
-                * @param value The new value for this setting.
-                * @return  This object (for method chaining).
-                */
-               @FluentSetter
-               public Builder implClass(Class<? extends MethodExecStats> 
value) {
-                       implClass = value;
-                       return this;
+               @Override /* BeanBuilder */
+               protected MethodExecStats buildDefault() {
+                       return new MethodExecStats(this);
                }
 
                /**
@@ -125,6 +102,39 @@ public class MethodExecStats {
                        thrownStore = value;
                        return this;
                }
+
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends MethodExecStats> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder impl(MethodExecStats value) {
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStore.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStore.java
index cabb90b..2d3c0bb 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStore.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/MethodExecStore.java
@@ -13,8 +13,6 @@
 package org.apache.juneau.mstat;
 
 import static java.util.Optional.*;
-import static org.apache.juneau.internal.ClassUtils.*;
-import static org.apache.juneau.internal.ExceptionUtils.*;
 
 import java.lang.reflect.*;
 import java.util.*;
@@ -51,18 +49,17 @@ public class MethodExecStore {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<MethodExecStore> {
 
                ThrownStore thrownStore;
-               private Class<? extends MethodExecStore> implClass;
-               MethodExecStore impl;
-               BeanStore beanStore;
                Class<? extends MethodExecStats> statsImplClass;
 
                /**
                 * Constructor.
                 */
-               protected Builder() {}
+               protected Builder() {
+                       super(MethodExecStore.class);
+               }
 
                /**
                 * Copy constructor.
@@ -70,52 +67,14 @@ public class MethodExecStore {
                 * @param copyFrom The builder to copy.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        thrownStore = copyFrom.thrownStore;
-                       implClass = copyFrom.implClass;
-                       impl = copyFrom.impl;
-                       beanStore = copyFrom.beanStore;
                        statsImplClass = copyFrom.statsImplClass;
                }
 
-               /**
-                * Create a new {@link MethodExecStore} using this builder.
-                *
-                * @return A new {@link MethodExecStore}
-                */
-               public MethodExecStore build() {
-                       try {
-                               if (impl != null)
-                                       return impl;
-                               Class<? extends MethodExecStore> ic = 
isConcrete(implClass) ? implClass : MethodExecStore.class;
-                               return 
BeanStore.of(beanStore).addBean(Builder.class, this).createBean(ic);
-                       } catch (ExecutableException e) {
-                               throw runtimeException(e);
-                       }
-               }
-
-               /**
-                * Specifies the bean store to use for instantiating the {@link 
MethodExecStore} object.
-                *
-                * <p>
-                * Can be used to instantiate {@link MethodExecStore} 
implementations with injected constructor argument beans.
-                *
-                * @param value The new value for this setting.
-                * @return  This object.
-                */
-               public Builder beanStore(BeanStore value) {
-                       beanStore = value;
-                       return this;
-               }
-
-               /**
-                * Specifies a subclass of {@link MethodExecStore} to create 
when the {@link #build()} method is called.
-                *
-                * @param value The new value for this setting.
-                * @return  This object.
-                */
-               public Builder implClass(Class<? extends MethodExecStore> 
value) {
-                       implClass = value;
-                       return this;
+               @Override /* BeanBuilder */
+               protected MethodExecStore buildDefault() {
+                       return new MethodExecStore(this);
                }
 
                /**
@@ -158,25 +117,38 @@ public class MethodExecStore {
                        return this;
                }
 
-               /**
-                * Specifies an already-instantiated bean for the {@link 
#build()} method to return.
-                *
-                * @param value The new value for this setting.
-                * @return This object.
-                */
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends MethodExecStore> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
                public Builder impl(MethodExecStore value) {
-                       impl = value;
+                       super.impl(value);
                        return this;
                }
 
-               /**
-                * Returns a copy of this builder.
-                *
-                * @return A copy of this builder.
-                */
-               public Builder copy() {
-                       return new Builder(this);
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
                }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
@@ -194,7 +166,7 @@ public class MethodExecStore {
         * @param builder The store to use for storing thrown exception 
statistics.
         */
        protected MethodExecStore(Builder builder) {
-               this.beanStore = 
ofNullable(builder.beanStore).orElseGet(()->BeanStore.create().build());
+               this.beanStore = 
builder.beanStore().orElseGet(()->BeanStore.create().build());
                this.thrownStore = 
ofNullable(builder.thrownStore).orElse(beanStore.getBean(ThrownStore.class).orElseGet(ThrownStore::new));
                this.statsImplClass = builder.statsImplClass;
        }
@@ -214,7 +186,7 @@ public class MethodExecStore {
                        stats = MethodExecStats
                                .create()
                                .beanStore(beanStore)
-                               .implClass(statsImplClass)
+                               .type(statsImplClass)
                                .method(m)
                                
.thrownStore(ThrownStore.create().parent(thrownStore).build())
                                .build();
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStatsBuilder.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStatsBuilder.java
index 5f22fb3..dad37bb 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStatsBuilder.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStatsBuilder.java
@@ -43,7 +43,7 @@ public class ThrownStatsBuilder {
        public ThrownStats build() {
                try {
                        Class<? extends ThrownStats> ic = isConcrete(implClass) 
? implClass : getDefaultImplClass();
-                       return 
BeanStore.of(beanStore).addBeans(ThrownStatsBuilder.class, this).createBean(ic);
+                       return 
BeanCreator.create(ic).store(beanStore).builder(this).run();
                } catch (ExecutableException e) {
                        throw runtimeException(e);
                }
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStore.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStore.java
index 9567562..1039d94 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStore.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/mstat/ThrownStore.java
@@ -14,8 +14,6 @@ package org.apache.juneau.mstat;
 
 import static java.util.stream.Collectors.*;
 import static java.util.Collections.*;
-import static org.apache.juneau.internal.ClassUtils.*;
-import static org.apache.juneau.internal.ExceptionUtils.*;
 import static org.apache.juneau.internal.ObjectUtils.*;
 import static java.util.Optional.*;
 import static java.util.Comparator.*;
@@ -58,19 +56,18 @@ public class ThrownStore {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<ThrownStore> {
 
                ThrownStore parent;
-               Class<? extends ThrownStore> implClass;
-               ThrownStore impl;
-               BeanStore beanStore;
                Class<? extends ThrownStats> statsImplClass;
                Set<Class<?>> ignoreClasses;
 
                /**
                 * Constructor.
                 */
-               protected Builder() {}
+               protected Builder() {
+                       super(ThrownStore.class);
+               }
 
                /**
                 * Copy constructor.
@@ -78,64 +75,15 @@ public class ThrownStore {
                 * @param copyFrom The builder to copy.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        parent = copyFrom.parent;
-                       implClass = copyFrom.implClass;
-                       impl = copyFrom.impl;
-                       beanStore = copyFrom.beanStore;
                        statsImplClass = copyFrom.statsImplClass;
                        ignoreClasses = copyFrom.ignoreClasses == null ? null : 
ASet.of(copyFrom.ignoreClasses);
                }
 
-               /**
-                * Create a new {@link ThrownStore} using this builder.
-                *
-                * @return A new {@link ThrownStore}
-                */
-               public ThrownStore build() {
-                       try {
-                               if (impl != null)
-                                       return impl;
-                               Class<? extends ThrownStore> ic = 
isConcrete(implClass) ? implClass : ThrownStore.class;
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
-                       } catch (ExecutableException e) {
-                               throw runtimeException(e);
-                       }
-               }
-
-               /**
-                * Specifies the bean store to use for instantiating the {@link 
ThrownStore} object.
-                *
-                * <p>
-                * Can be used to instantiate {@link ThrownStore} 
implementations with injected constructor argument beans.
-                *
-                * @param value The new value for this setting.
-                * @return  This object (for method chaining).
-                */
-               public Builder beanStore(BeanStore value) {
-                       this.beanStore = value;
-                       return this;
-               }
-
-               /**
-                * Specifies a subclass of {@link ThrownStore} to create when 
the {@link #build()} method is called.
-                *
-                * @param value The new value for this setting.
-                * @return  This object (for method chaining).
-                */
-               public Builder implClass(Class<? extends ThrownStore> value) {
-                       this.implClass = value;
-                       return this;
-               }
-
-               /**
-                * Specifies a pre-instantiated bean to return when the {@link 
#build()} method is called.
-                *
-                * @param value The new value for this setting.
-                * @return  This object (for method chaining).
-                */
-               public Builder impl(ThrownStore value) {
-                       this.impl = value;
-                       return this;
+               @Override /* BeanBuilder */
+               protected ThrownStore buildDefault() {
+                       return new ThrownStore(this);
                }
 
                /**
@@ -178,14 +126,38 @@ public class ThrownStore {
                        return this;
                }
 
-               /**
-                * Creates a copy of this builder.
-                *
-                * @return A copy of this builder.
-                */
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
                public Builder copy() {
                        return new Builder(this);
                }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends ThrownStore> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder impl(ThrownStore value) {
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
@@ -212,7 +184,7 @@ public class ThrownStore {
         */
        public ThrownStore(Builder builder) {
                this.parent = ofNullable(builder.parent);
-               this.beanStore = 
ofNullable(builder.beanStore).orElseGet(()->BeanStore.create().build());
+               this.beanStore = 
builder.beanStore().orElseGet(()->BeanStore.create().build());
 
                this.statsImplClass = firstNonNull(builder.statsImplClass, 
parent.isPresent() ? parent.get().statsImplClass : null, null);
 
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/reflect/ExecutableInfo.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/reflect/ExecutableInfo.java
index 6e7d171..7db0224 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/reflect/ExecutableInfo.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/reflect/ExecutableInfo.java
@@ -302,7 +302,19 @@ public abstract class ExecutableInfo {
         */
        public final Annotation[] getParameterAnnotations(int index) {
                checkIndex(index);
-               return e.getParameterAnnotations()[index];
+               Annotation[][] x = e.getParameterAnnotations();
+               int c = e.getParameterCount();
+               if (c != x.length) {
+                       // Seems to be a JVM bug where 
getParameterAnnotations() don't take mandated parameters into account.
+                       Annotation[][] x2 = new Annotation[c][];
+                       int diff = c - x.length;
+                       for (int i = 0; i < diff; i++)
+                               x2[i] = new Annotation[0];
+                       for (int i = diff; i < c; i++)
+                               x2[i] = x[i-diff];
+                       x = x2;
+               }
+               return x[index];
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
diff --git 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/svl/VarResolver.java
 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/svl/VarResolver.java
index 5d55945..b8951b7 100644
--- 
a/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/svl/VarResolver.java
+++ 
b/juneau-core/juneau-marshall/src/main/java/org/apache/juneau/svl/VarResolver.java
@@ -16,6 +16,7 @@ import java.io.*;
 import java.util.*;
 import java.util.concurrent.*;
 
+import org.apache.juneau.*;
 import org.apache.juneau.collections.*;
 import org.apache.juneau.cp.*;
 import org.apache.juneau.svl.vars.*;
@@ -104,18 +105,17 @@ public class VarResolver {
        /**
         * Builder class.
         */
-       public static class Builder {
+       public static class Builder extends BeanBuilder<VarResolver> {
 
                final VarList vars;
-               BeanStore beanStore;
-               VarResolver impl;
 
                /**
                 * Constructor.
                 */
                protected Builder() {
+                       super(VarResolver.class);
                        vars = VarList.create();
-                       beanStore = BeanStore.create().build();
+                       beanStore(BeanStore.create().build());
                }
 
                /**
@@ -124,8 +124,9 @@ public class VarResolver {
                 * @param copyFrom The bean to copy from.
                 */
                protected Builder(VarResolver copyFrom) {
+                       super(copyFrom.getClass());
                        vars = VarList.of(copyFrom.vars);
-                       beanStore = BeanStore.of(copyFrom.beanStore);
+                       beanStore(copyFrom.beanStore.copy().build());
                }
 
                /**
@@ -134,9 +135,13 @@ public class VarResolver {
                 * @param copyFrom The builder to copy from.
                 */
                protected Builder(Builder copyFrom) {
+                       super(copyFrom);
                        vars = copyFrom.vars.copy();
-                       beanStore = BeanStore.of(copyFrom.beanStore);
-                       impl = copyFrom.impl;
+               }
+
+               @Override /* BeanBuilder */
+               protected VarResolver buildDefault() {
+                       return new VarResolver(this);
                }
 
                /**
@@ -180,17 +185,6 @@ public class VarResolver {
                }
 
                /**
-                * Specify a pre-instantiated bean for the {@link #build()} 
method to return.
-                *
-                * @param value The pre-instantiated bean.
-                * @return This object.
-                */
-               public Builder impl(VarResolver value) {
-                       this.impl = value;
-                       return this;
-               }
-
-               /**
                 * Adds the default variables to this builder.
                 *
                 * <p>
@@ -221,17 +215,6 @@ public class VarResolver {
                }
 
                /**
-                * Associates a bean store with this builder.
-                *
-                * @param value The bean store to associate with this var 
resolver.
-                * @return This object .
-                */
-               public Builder beanStore(BeanStore value) {
-                       this.beanStore = BeanStore.of(value);
-                       return this;
-               }
-
-               /**
                 * Adds a bean to the bean store in this session.
                 *
                 * @param <T> The bean type.
@@ -240,27 +223,42 @@ public class VarResolver {
                 * @return This object .
                 */
                public <T> Builder bean(Class<T> c, T value) {
-                       beanStore.addBean(c, value);
+                       beanStore().get().addBean(c, value);
                        return this;
                }
 
-               /**
-                * Create a new var resolver using the settings in this builder.
-                *
-                * @return A new var resolver.
-                */
-               public VarResolver build() {
-                       return impl != null ? impl : new VarResolver(this);
-               }
+               // <FluentSetters>
 
-               /**
-                * Creates a copy of this builder.
-                *
-                * @return A new copy of this builder.
-                */
+               @Override /* BeanBuilder */
                public Builder copy() {
                        return new Builder(this);
                }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends VarResolver> value) {
+                       super.type(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder impl(VarResolver value) {
+                       super.impl(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
+                       return this;
+               }
+
+               // </FluentSetters>
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
@@ -277,20 +275,19 @@ public class VarResolver {
         * @param builder The builder for this object.
         */
        protected VarResolver(Builder builder) {
-               this.vars = builder.vars.stream().map(x -> 
toVar(builder.beanStore,x)).toArray(Var[]::new);
+               this.vars = builder.vars.stream().map(x -> 
toVar(builder.beanStore().get(),x)).toArray(Var[]::new);
 
                Map<String,Var> m = new ConcurrentSkipListMap<>();
                for (Var v : vars)
                        m.put(v.getName(), v);
 
                this.varMap = AMap.unmodifiable(m);
-               this.beanStore = BeanStore.of(builder.beanStore);
+               this.beanStore = BeanStore.of(builder.beanStore().get());
        }
 
-       @SuppressWarnings("unchecked")
        private static Var toVar(BeanStore bs, Object o) {
                if (o instanceof Class)
-                       return bs.createBean(Var.class, (Class<? extends 
Var>)o);
+                       return bs.creator(Var.class).type((Class<?>)o).run();
                return (Var)o;
        }
 
diff --git 
a/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/RestClient.java
 
b/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/RestClient.java
index aba8ba1..288ccfc 100644
--- 
a/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/RestClient.java
+++ 
b/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/RestClient.java
@@ -1852,7 +1852,7 @@ public class RestClient extends BeanContextable 
implements HttpClient, Closeable
 
                this.executorService = 
cp.getInstance(RESTCLIENT_executorService, ExecutorService.class).orElse(null);
 
-               this.callHandler = cp.getInstance(RESTCLIENT_callHandler, 
RestCallHandler.class, 
bs).orElseGet(bs.createBeanSupplier(BasicRestCallHandler.class));
+               this.callHandler = cp.getInstance(RESTCLIENT_callHandler, 
RestCallHandler.class, 
bs).orElseGet(bs.creator(BasicRestCallHandler.class).supplier());
 
                this.interceptors = 
cp.getInstanceArray(RESTCLIENT_interceptors, 
RestCallInterceptor.class).orElse(new RestCallInterceptor[0]);
 
@@ -3139,7 +3139,7 @@ public class RestClient extends BeanContextable 
implements HttpClient, Closeable
                HttpPartSerializer x = partSerializers.get(c);
                if (x == null) {
                        try {
-                               x = beanStore.createBean(c);
+                               x = beanStore.creator(c).run();
                        } catch (ExecutableException e) {
                                throw new RuntimeException(e);
                        }
@@ -3158,7 +3158,7 @@ public class RestClient extends BeanContextable 
implements HttpClient, Closeable
                HttpPartParser x = partParsers.get(c);
                if (x == null) {
                        try {
-                               x = beanStore.createBean(c);
+                               x = beanStore.creator(c).run();
                        } catch (ExecutableException e) {
                                throw new RuntimeException(e);
                        }
diff --git 
a/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/remote/RemoteOperationArg.java
 
b/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/remote/RemoteOperationArg.java
index 0f647fa..6a3ab18 100644
--- 
a/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/remote/RemoteOperationArg.java
+++ 
b/juneau-rest/juneau-rest-client/src/main/java/org/apache/juneau/rest/client/remote/RemoteOperationArg.java
@@ -40,7 +40,7 @@ public final class RemoteOperationArg {
        RemoteOperationArg(int index, HttpPartType partType, HttpPartSchema 
schema) {
                this.index = index;
                this.partType = partType;
-               this.serializer = 
ofNullable(BeanStore.INSTANCE.createBean(schema.getSerializer()));
+               this.serializer = 
ofNullable(BeanCreator.create(schema.getSerializer()).run());
                this.schema = schema;
        }
 
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicStaticFiles.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicStaticFiles.java
index a8c1429..c3c7203 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicStaticFiles.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/BasicStaticFiles.java
@@ -36,11 +36,12 @@ import org.apache.juneau.internal.*;
  * Provides the same functionality as {@link BasicFileFinder} but adds support 
for returning files as {@link HttpResource}
  * objects with arbitrary headers.
  */
-public class BasicStaticFiles extends BasicFileFinder implements StaticFiles {
+public class BasicStaticFiles implements StaticFiles {
 
        private final Header[] headers;
        private final MimetypesFileTypeMap mimeTypes;
        private final int hashCode;
+       private final FileFinder fileFinder;
 
        /**
         * Creates a new builder for this object.
@@ -57,10 +58,10 @@ public class BasicStaticFiles extends BasicFileFinder 
implements StaticFiles {
         * @param builder The builder object.
         */
        public BasicStaticFiles(StaticFiles.Builder builder) {
-               super(builder);
                this.headers = builder.headers.toArray(new 
Header[builder.headers.size()]);
                this.mimeTypes = builder.mimeTypes;
                this.hashCode = HashCode.of(hashCode(), headers);
+               this.fileFinder = builder.fileFinder.build();
        }
 
        /**
@@ -74,6 +75,7 @@ public class BasicStaticFiles extends BasicFileFinder 
implements StaticFiles {
                this.headers = new Header[0];
                this.mimeTypes = null;
                this.hashCode = HashCode.of(hashCode(), headers);
+               this.fileFinder = null;
        }
 
        /**
@@ -103,9 +105,13 @@ public class BasicStaticFiles extends BasicFileFinder 
implements StaticFiles {
                }
        }
 
-       @Override /* FileFinder */
+       /**
+        * Returns a map representation of this bean.
+        *
+        * @return A map representation of this bean.
+        */
        public OMap toMap() {
-               return super.toMap()
+               return OMap.create()
                        .a("headers", headers)
                ;
        }
@@ -119,4 +125,24 @@ public class BasicStaticFiles extends BasicFileFinder 
implements StaticFiles {
        public boolean equals(Object o) {
                return super.equals(o) && o instanceof BasicStaticFiles && 
eq(this, (BasicStaticFiles)o, (x,y)->eq(x.headers, y.headers));
        }
+
+       @Override /* FileFinder */
+       public Optional<InputStream> getStream(String name, Locale locale) 
throws IOException {
+               return fileFinder.getStream(name, locale);
+       }
+
+       @Override /* FileFinder */
+       public Optional<InputStream> getStream(String name) throws IOException {
+               return fileFinder.getStream(name);
+       }
+
+       @Override /* FileFinder */
+       public Optional<String> getString(String name) throws IOException {
+               return fileFinder.getString(name);
+       }
+
+       @Override /* FileFinder */
+       public Optional<String> getString(String name, Locale locale) throws 
IOException {
+               return fileFinder.getString(name, locale);
+       }
 }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/DebugEnablement.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/DebugEnablement.java
index 971440a..2087c7d 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/DebugEnablement.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/DebugEnablement.java
@@ -101,8 +101,7 @@ public interface DebugEnablement {
                        try {
                                if (impl != null)
                                        return impl;
-                               Class<? extends DebugEnablement> ic = 
isConcrete(type) ? type : getDefaultImplClass();
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
+                               return 
BeanCreator.create(DebugEnablement.class).type(isConcrete(type) ? type : 
getDefaultImplClass()).store(beanStore).builder(this).run();
                        } catch (Exception e) {
                                throw toHttpException(e, 
InternalServerError.class);
                        }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/ResponseProcessorList.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/ResponseProcessorList.java
index fa3e9b4..9b771b2 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/ResponseProcessorList.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/ResponseProcessorList.java
@@ -159,7 +159,7 @@ public class ResponseProcessorList {
                if (o instanceof ResponseProcessor)
                        return (ResponseProcessor)o;
                try {
-                       return (ResponseProcessor)bs.createBean((Class<?>)o);
+                       return 
bs.creator(ResponseProcessor.class).type((Class<?>)o).run();
                } catch (ExecutableException e) {
                        throw new ConfigException(e, "Could not instantiate 
class {0}", o);
                }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestChildren.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestChildren.java
index 506c51a..9943578 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestChildren.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestChildren.java
@@ -12,7 +12,7 @@
 // 
***************************************************************************************************************************
 package org.apache.juneau.rest;
 
-import static org.apache.juneau.internal.ObjectUtils.*;
+import static org.apache.juneau.internal.ClassUtils.*;
 import static org.apache.juneau.rest.HttpRuntimeException.*;
 
 import java.util.*;
@@ -77,8 +77,7 @@ public class RestChildren {
                        try {
                                if (impl != null)
                                        return impl;
-                               Class<? extends RestChildren> ic = 
firstNonNull(type, getDefaultImplClass());
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
+                               return 
BeanCreator.create(RestChildren.class).type(isConcrete(type) ? type : 
getDefaultImplClass()).store(beanStore).builder(this).run();
                        } catch (Exception e) {
                                throw toHttpException(e, 
InternalServerError.class);
                        }
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 5728559..a2b0b02 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
@@ -138,7 +138,9 @@ public class RestContext extends Context {
                        .addBean(Class.class, resourceClass)
                        .addBean(RestContext.class, parentContext)
                        .addBean(ServletConfig.class, servletConfig)
-                       .createBean(v.get());
+                       .creator(RestContextBuilder.class)
+                       .type(v.get())
+                       .run();
        }
 
        
//-------------------------------------------------------------------------------------------------------------------
@@ -993,7 +995,7 @@ public class RestContext extends Context {
                        beanStore.addBean(ParamInfo.class, pi);
                        for (Class<? extends RestOpArg> c : restOpArgs) {
                                try {
-                                       ra[i] = beanStore.createBean(c);
+                                       ra[i] = 
beanStore.creator(RestOpArg.class).type(c).run();
                                        if (ra[i] != null)
                                                break;
                                } catch (ExecutableException e) {
@@ -1028,7 +1030,7 @@ public class RestContext extends Context {
                        beanStore.addBean(ParamInfo.class, pi);
                        for (Class<? extends RestOpArg> c : hookMethodArgs) {
                                try {
-                                       ra[i] = beanStore.createBean(c);
+                                       ra[i] = 
beanStore.creator(RestOpArg.class).type(c).run();
                                        if (ra[i] != null)
                                                break;
                                } catch (ExecutableException e) {
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContextBuilder.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContextBuilder.java
index 2a6daab..390b11b 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContextBuilder.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestContextBuilder.java
@@ -211,7 +211,7 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
        @Override /* BeanContextBuilder */
        public RestContext build() {
                try {
-                       return (RestContext) BeanStore.of(beanStore(), 
resource.get()).addBeans(RestContextBuilder.class, 
this).createBean(getType().orElse(RestContext.class));
+                       return 
BeanCreator.create(RestContext.class).outer(resource.get()).store(beanStore()).builder(this).type(getType().orElse(RestContext.class)).run();
                } catch (Exception e) {
                        throw toHttpException(e, InternalServerError.class);
                }
@@ -893,7 +893,7 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
                // Specify the implementation class if its set as a default.
                defaultClasses()
                        .get(ThrownStore.class)
-                       .ifPresent(x -> v.get().implClass(x));
+                       .ifPresent(x -> v.get().type(x));
 
                // Replace with builder from bean store.
                beanStore
@@ -959,7 +959,7 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
                // Specify the implementation class if its set as a default.
                defaultClasses()
                        .get(MethodExecStore.class)
-                       .ifPresent(x -> v.get().implClass(x));
+                       .ifPresent(x -> v.get().type(x));
 
                // Replace with builder from bean store.
                beanStore
@@ -3332,11 +3332,10 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
                                if (oc == resourceClass)
                                        continue;
                                cb = RestContext.create(oc, restContext, inner);
-                               BeanStore bf = BeanStore.of(beanStore, 
resource).addBean(RestContextBuilder.class, cb);
-                               if (bf.getBean(oc).isPresent()) {
-                                       so = ()->bf.getBean(oc).get();  // If 
we resolved via injection, always get it this way.
+                               if (beanStore.getBean(oc).isPresent()) {
+                                       so = ()->beanStore.getBean(oc).get();  
// If we resolved via injection, always get it this way.
                                } else {
-                                       Object o2 = bf.createBean(oc);
+                                       Object o2 = 
beanStore.creator(oc).builder(cb).outer(resource).run();
                                        so = ()->o2;
                                }
                        } else {
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestConverterList.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestConverterList.java
index 22bea1b..88ba6eb 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestConverterList.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestConverterList.java
@@ -121,7 +121,7 @@ public class RestConverterList {
                if (o instanceof RestConverter)
                        return (RestConverter)o;
                try {
-                       return (RestConverter)bs.createBean((Class<?>)o);
+                       return 
BeanCreator.create(RestConverter.class).type((Class<?>)o).store(bs).run();
                } catch (ExecutableException e) {
                        throw new ConfigException(e, "Could not instantiate 
class {0}", o);
                }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestGuardList.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestGuardList.java
index 536fa22..e1c4436 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestGuardList.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestGuardList.java
@@ -121,7 +121,7 @@ public class RestGuardList {
                if (o instanceof RestGuard)
                        return (RestGuard)o;
                try {
-                       return (RestGuard)bs.createBean((Class<?>)o);
+                       return 
BeanCreator.create(RestGuard.class).type((Class<?>)o).store(bs).run();
                } catch (ExecutableException e) {
                        throw new ConfigException(e, "Could not instantiate 
class {0}", o);
                }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestMatcherList.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestMatcherList.java
index a5f73af..96aac5d 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestMatcherList.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestMatcherList.java
@@ -128,7 +128,7 @@ public class RestMatcherList {
                if (o instanceof RestMatcher)
                        return (RestMatcher)o;
                try {
-                       return (RestMatcher)bs.createBean((Class<?>)o);
+                       return 
BeanCreator.create(RestMatcher.class).type((Class<?>)o).store(bs).run();
                } catch (ExecutableException e) {
                        throw new ConfigException(e, "Could not instantiate 
class {0}", o);
                }
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 e03d954..8d4d9ce 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
@@ -253,7 +253,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(RestConverterList.Builder.class, x)
-                       
.beanCreateMethodFinder(RestConverterList.Builder.class, resource)
+                       .createMethodFinder(RestConverterList.Builder.class, 
resource)
                        .find("createConverters", Method.class)
                        .thenFind("createConverters")
                        .withDefault(x)
@@ -310,7 +310,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(RestGuardList.Builder.class, x)
-                       .beanCreateMethodFinder(RestGuardList.Builder.class, 
resource)
+                       .createMethodFinder(RestGuardList.Builder.class, 
resource)
                        .find("createGuards", Method.class)
                        .thenFind("createGuards")
                        .withDefault(x)
@@ -358,7 +358,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(RestMatcherList.Builder.class, x)
-                       .beanCreateMethodFinder(RestMatcherList.Builder.class, 
resource)
+                       .createMethodFinder(RestMatcherList.Builder.class, 
resource)
                        .find("createMatchers", Method.class)
                        .withDefault(x)
                        .run();
@@ -405,7 +405,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(EncoderGroup.Builder.class, x)
-                       .beanCreateMethodFinder(EncoderGroup.Builder.class, 
resource)
+                       .createMethodFinder(EncoderGroup.Builder.class, 
resource)
                        .find("createEncoders", Method.class)
                        .thenFind("createEncoders")
                        .withDefault(x)
@@ -456,7 +456,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(SerializerGroup.Builder.class, x)
-                       .beanCreateMethodFinder(SerializerGroup.Builder.class, 
resource)
+                       .createMethodFinder(SerializerGroup.Builder.class, 
resource)
                        .find("createSerializers", Method.class)
                        .thenFind("createSerializers")
                        .withDefault(x)
@@ -507,7 +507,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(ParserGroup.Builder.class, x)
-                       .beanCreateMethodFinder(ParserGroup.Builder.class, 
resource)
+                       .createMethodFinder(ParserGroup.Builder.class, resource)
                        .find("createParsers", Method.class)
                        .thenFind("createParsers")
                        .withDefault(x)
@@ -560,7 +560,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(HttpPartSerializer.Creator.class, x)
-                       
.beanCreateMethodFinder(HttpPartSerializer.Creator.class, resource)
+                       .createMethodFinder(HttpPartSerializer.Creator.class, 
resource)
                        .find("createPartSerializer", Method.class)
                        .thenFind("createPartSerializer")
                        .withDefault(x)
@@ -613,7 +613,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(HttpPartParser.Creator.class, x)
-                       .beanCreateMethodFinder(HttpPartParser.Creator.class, 
resource)
+                       .createMethodFinder(HttpPartParser.Creator.class, 
resource)
                        .find("createPartParser", Method.class)
                        .thenFind("createPartParser")
                        .withDefault(x)
@@ -670,7 +670,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(UrlPathMatcherList.class, x)
-                       .beanCreateMethodFinder(UrlPathMatcherList.class, 
resource)
+                       .createMethodFinder(UrlPathMatcherList.class, resource)
                        .find("createPathMatchers", Method.class)
                        .withDefault(x)
                        .run();
@@ -703,7 +703,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(JsonSchemaGenerator.class, x)
-                       .beanCreateMethodFinder(JsonSchemaGenerator.class, 
resource)
+                       .createMethodFinder(JsonSchemaGenerator.class, resource)
                        .find("createJsonSchemaGenerator", Method.class)
                        .thenFind("createJsonSchemaGenerator")
                        .withDefault(x)
@@ -746,7 +746,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(HeaderList.Builder.class, x)
-                       .beanCreateMethodFinder(HeaderList.Builder.class, 
resource)
+                       .createMethodFinder(HeaderList.Builder.class, resource)
                        .find("createDefaultRequestHeaders", Method.class)
                        .withDefault(x)
                        .run();
@@ -772,7 +772,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(HeaderList.Builder.class, x)
-                       .beanCreateMethodFinder(HeaderList.Builder.class, 
resource)
+                       .createMethodFinder(HeaderList.Builder.class, resource)
                        .find("createDefaultResponseHeaders", Method.class)
                        .withDefault(x)
                        .run();
@@ -798,7 +798,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(NamedAttributeList.class, x)
-                       .beanCreateMethodFinder(NamedAttributeList.class, 
resource)
+                       .createMethodFinder(NamedAttributeList.class, resource)
                        .find("createDefaultRequestAttributes", Method.class)
                        .withDefault(x)
                        .run();
@@ -839,7 +839,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(PartList.Builder.class, x)
-                       .beanCreateMethodFinder(PartList.Builder.class, 
resource)
+                       .createMethodFinder(PartList.Builder.class, resource)
                        .find("createDefaultRequestQuery", Method.class)
                        .thenFind("createDefaultRequestQuery")
                        .withDefault(x)
@@ -881,7 +881,7 @@ public class RestOpContext extends BeanContext implements 
Comparable<RestOpConte
                x = BeanStore
                        .of(beanStore, resource)
                        .addBean(PartList.Builder.class, x)
-                       .beanCreateMethodFinder(PartList.Builder.class, 
resource)
+                       .createMethodFinder(PartList.Builder.class, resource)
                        .find("createDefaultRequestFormData", Method.class)
                        .thenFind("createDefaultRequestFormData")
                        .withDefault(x)
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContextBuilder.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContextBuilder.java
index 4a1021b..f230dda 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContextBuilder.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOpContextBuilder.java
@@ -76,12 +76,10 @@ public class RestOpContextBuilder extends 
BeanContextBuilder {
                throw new NoSuchMethodError("Not implemented.");
        }
 
-       @SuppressWarnings("unchecked")
        @Override /* BeanContextBuilder */
        public RestOpContext build() {
                try {
-                       Class<? extends RestOpContext> ic = (Class<? extends 
RestOpContext>) getType().orElse(getDefaultImplClass());
-                       return 
BeanStore.of(beanStore).addBean(RestOpContextBuilder.class, 
this).createBean(ic);
+                       return 
BeanCreator.create(RestOpContext.class).type(getType().orElse(getDefaultImplClass())).store(beanStore).builder(this).run();
                } catch (Exception e) {
                        throw toHttpException(e, InternalServerError.class);
                }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOperations.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOperations.java
index 340a92c..226182c 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOperations.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/RestOperations.java
@@ -76,8 +76,7 @@ public class RestOperations {
                        try {
                                if (impl != null)
                                        return impl;
-                               Class<? extends RestOperations> ic = 
firstNonNull(type, getDefaultImplClass());
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
+                               return 
BeanCreator.create(RestOperations.class).type(firstNonNull(type, 
getDefaultImplClass())).store(beanStore).builder(this).run();
                        } catch (Exception e) {
                                throw toHttpException(e, 
InternalServerError.class);
                        }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/StaticFiles.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/StaticFiles.java
index 11cff5c..e35590f 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/StaticFiles.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/StaticFiles.java
@@ -18,6 +18,7 @@ import java.util.*;
 import javax.activation.*;
 
 import org.apache.http.*;
+import org.apache.juneau.*;
 import org.apache.juneau.collections.*;
 import org.apache.juneau.cp.*;
 import org.apache.juneau.http.resource.*;
@@ -53,16 +54,19 @@ public interface StaticFiles extends FileFinder {
         * Builder class.
         */
        @FluentSetters
-       public static class Builder extends FileFinder.Builder {
+       public static class Builder extends BeanBuilder<StaticFiles> {
 
                List<Header> headers;
                MimetypesFileTypeMap mimeTypes;
+               FileFinder.Builder fileFinder;
 
                /**
                 * Constructor.
                 */
                protected Builder() {
+                       super(BasicStaticFiles.class);
                        headers = AList.create();
+                       fileFinder = FileFinder.create();
                        mimeTypes = new ExtendedMimetypesFileTypeMap();
                }
 
@@ -77,14 +81,9 @@ public interface StaticFiles extends FileFinder {
                        mimeTypes = copyFrom.mimeTypes;
                }
 
-               @Override
-               public StaticFiles build() {
-                       return (StaticFiles)super.build();
-               }
-
-               @Override
-               protected Class<? extends FileFinder> getDefaultType() {
-                       return BasicStaticFiles.class;
+               @Override /* BeanBuilder */
+               protected StaticFiles buildDefault() {
+                       return new BasicStaticFiles(this);
                }
 
                /**
@@ -126,58 +125,112 @@ public interface StaticFiles extends FileFinder {
                        return this;
                }
 
-               @Override
-               public Builder copy() {
-                       return new Builder(this);
+               /**
+                * Enables in-memory caching of files for quicker retrieval.
+                *
+                * @param cachingLimit The maximum file size in bytes.
+                * @return This object.
+                */
+               @FluentSetter
+               public Builder caching(long cachingLimit) {
+                       fileFinder.caching(cachingLimit);
+                       return this;
                }
 
-               // <FluentSetters>
-
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder beanStore(BeanStore value) {
-                       super.beanStore(value);
+               /**
+                * Adds a class subpackage to the lookup paths.
+                *
+                * @param c The class whose package will be added to the lookup 
paths.  Must not be <jk>null</jk>.
+                * @param path The absolute or relative subpath.
+                * @param recursive If <jk>true</jk>, also recursively adds all 
the paths of the parent classes as well.
+                * @return This object.
+                */
+               @FluentSetter
+               public Builder cp(Class<?> c, String path, boolean recursive) {
+                       fileFinder.cp(c, path, recursive);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder caching(long cachingLimit) {
-                       super.caching(cachingLimit);
+               /**
+                * Adds a file system directory to the lookup paths.
+                *
+                * @param path The path relative to the working directory.  
Must not be <jk>null</jk>
+                * @return This object.
+                */
+               @FluentSetter
+               public Builder dir(String path) {
+                       fileFinder.dir(path);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder cp(Class<?> c, String path, boolean recursive) {
-                       super.cp(c, path, recursive);
+               /**
+                * Specifies the regular expression file name pattern to use to 
exclude files from being retrieved from the file source.
+                *
+                * @param patterns
+                *      The regular expression exclude patterns.
+                *      <br>If none are specified, no files will be excluded.
+                * @return This object.
+                */
+               @FluentSetter
+               public Builder exclude(String...patterns) {
+                       fileFinder.exclude(patterns);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder dir(String path) {
-                       super.dir(path);
+               /**
+                * Specifies the regular expression file name patterns to use 
to include files being retrieved from the file source.
+                *
+                * @param patterns
+                *      The regular expression include patterns.
+                *      <br>The default is <js>".*"</js>.
+                * @return This object.
+                */
+               @FluentSetter
+               public Builder include(String...patterns) {
+                       fileFinder.include(patterns);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder exclude(String...patterns) {
-                       super.exclude(patterns);
+               /**
+                * Adds a file system directory to the lookup paths.
+                *
+                * @param path The directory path.
+                * @return This object.
+                */
+               @FluentSetter
+               public Builder path(Path path) {
+                       fileFinder.path(path);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder type(Class<? extends 
org.apache.juneau.cp.FileFinder> value) {
+               // <FluentSetters>
+
+               @Override /* BeanBuilder */
+               public Builder copy() {
+                       return new Builder(this);
+               }
+
+               @Override /* BeanBuilder */
+               public Builder type(Class<? extends StaticFiles> value) {
                        super.type(value);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder include(String...patterns) {
-                       super.include(patterns);
+               @Override /* BeanBuilder */
+               public Builder impl(StaticFiles value) {
+                       super.impl(value);
                        return this;
                }
 
-               @Override /* GENERATED - FileFinderBuilder */
-               public Builder path(Path path) {
-                       super.path(path);
+               @Override /* BeanBuilder */
+               public Builder outer(Object value) {
+                       super.outer(value);
+                       return this;
+               }
+
+               @Override /* BeanBuilder */
+               public Builder beanStore(BeanStore value) {
+                       super.beanStore(value);
                        return this;
                }
 
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/SwaggerProvider.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/SwaggerProvider.java
index a29b087..e064ba6 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/SwaggerProvider.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/SwaggerProvider.java
@@ -103,8 +103,7 @@ public interface SwaggerProvider {
                        try {
                                if (impl != null)
                                        return impl;
-                               Class<? extends SwaggerProvider> ic = 
isConcrete(type) ? type : getDefaultType();
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
+                               return 
BeanCreator.create(SwaggerProvider.class).type(isConcrete(type) ? type : 
getDefaultType()).store(beanStore).builder(this).run();
                        } catch (Exception e) {
                                throw toHttpException(e, 
InternalServerError.class);
                        }
diff --git 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/logging/RestLogger.java
 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/logging/RestLogger.java
index 5d4feb5..4304b85 100644
--- 
a/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/logging/RestLogger.java
+++ 
b/juneau-rest/juneau-rest-server/src/main/java/org/apache/juneau/rest/logging/RestLogger.java
@@ -200,8 +200,7 @@ public interface RestLogger {
                        try {
                                if (impl != null)
                                        return impl;
-                               Class<? extends RestLogger> ic = 
isConcrete(type) ? type : BasicRestLogger.class;
-                               return 
BeanStore.of(beanStore).addBeans(Builder.class, this).createBean(ic);
+                               return 
BeanCreator.create(RestLogger.class).type(isConcrete(type) ? type : 
BasicRestLogger.class).store(beanStore).builder(this).findSingleton().run();
                        } catch (Exception e) {
                                throw toHttpException(e, 
InternalServerError.class);
                        }
diff --git 
a/juneau-utest/src/test/java/org/apache/juneau/cp/BeanCreator_Test.java 
b/juneau-utest/src/test/java/org/apache/juneau/cp/BeanCreator_Test.java
new file mode 100644
index 0000000..bdd0021
--- /dev/null
+++ b/juneau-utest/src/test/java/org/apache/juneau/cp/BeanCreator_Test.java
@@ -0,0 +1,419 @@
+// 
***************************************************************************************************************************
+// * Licensed to the Apache Software Foundation (ASF) under one or more 
contributor license agreements.  See the NOTICE file *
+// * distributed with this work for additional information regarding copyright 
ownership.  The ASF licenses this file        *
+// * to you under the Apache License, Version 2.0 (the "License"); you may not 
use this file except in compliance            *
+// * with the License.  You may obtain a copy of the License at                
                                              *
+// *                                                                           
                                              *
+// *  http://www.apache.org/licenses/LICENSE-2.0                               
                                              *
+// *                                                                           
                                              *
+// * Unless required by applicable law or agreed to in writing, software 
distributed under the License is distributed on an  *
+// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either 
express or implied.  See the License for the        *
+// * specific language governing permissions and limitations under the 
License.                                              *
+// 
***************************************************************************************************************************
+package org.apache.juneau.cp;
+
+import static org.apache.juneau.assertions.Assertions.*;
+import static org.junit.runners.MethodSorters.*;
+
+import java.util.*;
+
+import javax.inject.*;
+
+import static org.apache.juneau.cp.BeanCreator.*;
+
+import org.apache.juneau.annotation.*;
+import org.junit.*;
+
+@FixMethodOrder(NAME_ASCENDING)
+public class BeanCreator_Test {
+
+       
//-----------------------------------------------------------------------------------------------------------------
+       // Basic tests.
+       
//-----------------------------------------------------------------------------------------------------------------
+
+       public static class A1 {}
+
+       @Test
+       public void a01_basic() {
+               assertObject(create(A1.class).run()).isNotNull();
+               assertObject(create(null).run()).isNull();
+       }
+
+       public class A2 {}
+
+       @Test
+       public void a02_outer() {
+               BeanCreator_Test outer = new BeanCreator_Test();
+               assertObject(create(A2.class).outer(outer).run()).isNotNull();
+       }
+
+       
//-----------------------------------------------------------------------------------------------------------------
+       // Static creators.
+       
//-----------------------------------------------------------------------------------------------------------------
+
+       public static class B1 {
+               public String a;
+               public static B1 create() {
+                       B1 x = new B1();
+                       x.a = "foo";
+                       return x;
+               }
+       }
+
+       @Test
+       public void b01_staticCreator_create() {
+               assertString(create(B1.class).run().a).is("foo");
+
+       }
+
+       public static abstract class B2 {
+               public String a;
+               public static B2 getInstance() {
+                       B2 x = new B2(){};
+                       x.a = "foo";
+                       return x;
+               }
+       }
+
+       @Test
+       public void b02_staticCreator_getInstance() {
+               assertString(create(B2.class).run().a).is("foo");
+       }
+
+       public static class B3a {
+               public String a;
+               public static B3a getFoo() {
+                       B3a x = new B3a();
+                       x.a = "foo";
+                       return x;
+               }
+               protected static B3a create() {
+                       B3a x = new B3a();
+                       x.a = "foo";
+                       return x;
+               }
+               public static B3a create(String foo) {
+                       B3a x = new B3a();
+                       x.a = "foo";
+                       return x;
+               }
+               @Deprecated protected static B3a getInstance() {
+                       B3a x = new B3a();
+                       x.a = "foo";
+                       return x;
+               }
+               protected B3a() {
+                       a = "bar";
+               }
+       }
+
+       public static class B3b {
+               public String a;
+               public B3b create() {
+                       B3b x = new B3b();
+                       x.a = "foo";
+                       return x;
+               }
+               @BeanIgnore public static B3b getInstance() {
+                       B3b x = new B3b();
+                       x.a = "foo";
+                       return x;
+               }
+               protected B3b() {
+                       a = "bar";
+               }
+       }
+
+       public static class B3c {
+               public String a;
+               public static String create() {
+                       return null;
+               }
+               protected B3c() {
+                       a = "bar";
+               }
+       }
+
+       @Test
+       public void b03_staticCreator_invalidSignatures() {
+               BeanStore bs = BeanStore.INSTANCE;
+               assertString(bs.creator(B3a.class).run().a).is("bar");
+               assertString(bs.creator(B3b.class).run().a).is("bar");
+               assertString(bs.creator(B3c.class).run().a).is("bar");
+       }
+
+       public static class B4 {
+               public String a;
+               public static B4 create() {
+                       B4 x = new B4();
+                       x.a = "foo";
+                       return x;
+               }
+               public static B4 create(Integer i, String s) {
+                       B4 x = new B4();
+                       x.a = i.toString() + s;
+                       return x;
+               }
+               public static B4 create(Integer i) {
+                       B4 x = new B4();
+                       x.a = i.toString();
+                       return x;
+               }
+               protected B4() {
+                       a = "bar";
+               }
+       }
+
+       @Test
+       public void b04_staticCreator_withBeans() {
+               BeanStore bs = BeanStore.create().build();
+               assertString(bs.creator(B4.class).run().a).is("foo");
+               bs.add(Integer.class, 1);
+               assertString(bs.creator(B4.class).run().a).is("1");
+               bs.add(String.class, "x");
+               assertString(bs.creator(B4.class).run().a).is("1x");
+               bs.add(Integer.class, null);
+               assertString(bs.creator(B4.class).run().a).is("foo");
+       }
+
+       public static class B5 {
+               public String a;
+               public static B5 create() {
+                       return new B5("foo");
+               }
+               protected B5(String s) {
+                       a = s;
+               }
+       }
+
+       @Test
+       public void b05_staticCreator_ignoredWithBuilder() {
+               assertString(create(B5.class).builder("bar").run().a).is("bar");
+       }
+
+       public static class B6 {
+               public String a = "foo";
+               public static B6 create(Optional<String> s) {
+                       B6 x = new B6();
+                       x.a = s.orElse(null);
+                       return x;
+               }
+       }
+
+       @Test
+       public void b06_staticCreator_withOptional() {
+               BeanStore bs = BeanStore.create().build();
+               assertString(bs.creator(B6.class).run().a).isNull();
+               bs.add(String.class, "bar");
+               assertString(bs.creator(B6.class).run().a).is("bar");
+       }
+
+       public static class B7 {
+               public String a = "foo";
+               public static B7 create(Optional<String> s, Integer i) {
+                       B7 x = new B7();
+                       x.a = s.orElse(null) + "," + i;
+                       return x;
+               }
+               private B7() {}
+       }
+
+       @Test
+       public void b07_staticCreator_missingPrereqs() {
+               BeanStore bs = BeanStore.create().build();
+               
assertThrown(()->bs.creator(B7.class).run()).message().is("Could not 
instantiate class org.apache.juneau.cp.BeanCreator_Test$B7: Static creator 
found but could not find prerequisites: Integer.");
+               bs.add(Integer.class, 1);
+               assertString(bs.creator(B7.class).run().a).is("null,1");
+               bs.add(String.class, "bar");
+               assertString(bs.creator(B7.class).run().a).is("bar,1");
+       }
+       
//-----------------------------------------------------------------------------------------------------------------
+       // Invalid types.
+       
//-----------------------------------------------------------------------------------------------------------------
+
+       public static abstract class C1 {
+               public C1() {}
+       }
+
+       public interface C2 {}
+
+       @Test
+       public void c01_staticCreator_withBeans() {
+               assertThrown(()->create(C1.class).run()).message().is("Could 
not instantiate class "+C1.class.getName()+": Class is abstract.");
+               assertThrown(()->create(C2.class).run()).message().is("Could 
not instantiate class "+C2.class.getName()+": Class is an interface.");
+       }
+
+       
//-----------------------------------------------------------------------------------------------------------------
+       // Constructors.
+       
//-----------------------------------------------------------------------------------------------------------------
+
+       public static class D1 {
+               public String a;
+               public D1(String s) {
+                       a = "s="+s;
+               }
+               public D1(Integer i) {
+                       a = "i="+i;
+               }
+               public D1(String s, Integer i) {
+                       a = "s="+s+",i="+i;
+               }
+       }
+
+       @Test
+       public void d01_constructors_public() {
+               BeanStore bs = BeanStore.create().build();
+               
assertThrown(()->bs.creator(D1.class).run()).message().is("Could not 
instantiate class "+D1.class.getName()+": Public constructor found but could 
not find prerequisites: Integer or Integer,String or String.");
+               bs.add(String.class, "foo");
+               assertString(bs.creator(D1.class).run().a).is("s=foo");
+               bs.add(Integer.class, 1);
+               assertString(bs.creator(D1.class).run().a).is("s=foo,i=1");
+               bs.removeBean(String.class);
+               assertString(bs.creator(D1.class).run().a).is("i=1");
+       }
+
+       public static class D2 {
+               public String a;
+               protected D2(String s) {
+                       a = "s="+s;
+               }
+               protected D2(Integer i) {
+                       a = "i="+i;
+               }
+               protected D2(String s, Integer i) {
+                       a = "s="+s+",i="+i;
+               }
+       }
+
+       @Test
+       public void d02_constructors_protected() {
+               BeanStore bs = BeanStore.create().build();
+               
assertThrown(()->bs.creator(D2.class).run()).message().is("Could not 
instantiate class "+D2.class.getName()+": Protected constructor found but could 
not find prerequisites: Integer or Integer,String or String.");
+               bs.add(String.class, "foo");
+               assertString(bs.creator(D2.class).run().a).is("s=foo");
+               bs.add(Integer.class, 1);
+               assertString(bs.creator(D2.class).run().a).is("s=foo,i=1");
+               bs.removeBean(String.class);
+               assertString(bs.creator(D2.class).run().a).is("i=1");
+       }
+
+       public static class D3 {
+               public String a;
+               public D3(String s) {
+                       a = "s="+s;
+               }
+               protected D3(String s, Integer i) {
+                       a = "s="+s+",i="+i;
+               }
+       }
+
+       @Test
+       public void d03_constructors_publicOverProtected() {
+               BeanStore bs = BeanStore.create().build();
+               
assertThrown(()->bs.creator(D3.class).run()).message().is("Could not 
instantiate class "+D3.class.getName()+": Public constructor found but could 
not find prerequisites: String.");
+               bs.add(String.class, "foo");
+               bs.add(Integer.class, 1);
+               assertString(bs.creator(D3.class).run().a).is("s=foo");
+       }
+
+       public static class D4 {
+               private D4() {}
+       }
+
+       @Test
+       public void d04_constructors_private() {
+               assertThrown(()->create(D4.class).run()).message().is("Could 
not instantiate class "+D4.class.getName()+": No public/protected constructors 
found.");
+       }
+
+       public static class D5 {
+               public String a;
+               public D5(@Named("foo") Object o) {
+                       a = o.toString();
+               }
+               public D5(@Named("foo") Object o, Integer i) {
+                       a = o.toString() + "," + i;
+               }
+       }
+
+       @Test
+       public void d05_constructors_namedBean() {
+               BeanStore bs = BeanStore.create().build();
+               
assertThrown(()->bs.creator(D5.class).run()).message().is("Could not 
instantiate class "+D5.class.getName()+": Public constructor found but could 
not find prerequisites: Integer,foo or foo.");
+               bs.add("foo", "bar");
+               assertString(bs.creator(D5.class).run().a).is("bar");
+       }
+
+       public class D6 {
+               public String a;
+               public D6(@Named("foo") Object o) {
+                       a = o.toString();
+               }
+               public D6(@Named("foo") Object o, Integer i) {
+                       a = o.toString() + "," + i;
+               }
+       }
+
+       @Test
+       public void d06_constructors_namedBean_withOuter() {
+               BeanStore bs = BeanStore.create().build();
+               Object outer = new BeanCreator_Test();
+               
assertThrown(()->bs.creator(D6.class).outer(outer).run()).message().is("Could 
not instantiate class "+D6.class.getName()+": Public constructor found but 
could not find prerequisites: Integer,foo or foo.");
+               bs.add("foo", "bar");
+               
assertString(bs.creator(D6.class).outer(outer).run().a).is("bar");
+       }
+
+       
//-----------------------------------------------------------------------------------------------------------------
+       // Builders.
+       
//-----------------------------------------------------------------------------------------------------------------
+
+       public static class E1 {
+               public String a;
+
+               public static Builder create() {
+                       return new Builder();
+               }
+
+               public static class Builder {
+                       public String b;
+               }
+
+               protected E1(Builder b) {
+                       a = b.b;
+               }
+       }
+
+       @Test
+       public void e01_builders() {
+               BeanStore bs = BeanStore.create().build();
+               E1.Builder b = E1.create();
+               b.b = "foo";
+               assertString(bs.creator(E1.class).builder(b).run().a).is("foo");
+       }
+
+       public static class E2 {
+               public String a;
+               public static Builder create() {
+                       return new Builder();
+               }
+               public static class Builder {
+                       public String b;
+               }
+               protected E2(Builder b, Integer i) {
+                       a = b.b;
+               }
+               protected E2(Integer i) {
+               }
+               E2(String s) {
+               }
+               protected E2(Builder b) {
+                       a = b.b;
+               }
+       }
+
+       @Test
+       public void e02_builders_inherent() {
+               BeanStore bs = BeanStore.create().build();
+               assertString(bs.creator(E2.class).run().a).isNull();
+               
assertThrown(()->bs.creator(E2.class).builder(true).run()).message().is("Could 
not instantiate class "+E2.class.getName()+": Protected constructor found but 
could not find prerequisites: Builder or Builder,Integer or Integer.");
+       }
+}
diff --git 
a/juneau-utest/src/test/java/org/apache/juneau/cp/BeanStore_Test.java 
b/juneau-utest/src/test/java/org/apache/juneau/cp/BeanStore_Test.java
index 603cd5f..39f2650 100644
--- a/juneau-utest/src/test/java/org/apache/juneau/cp/BeanStore_Test.java
+++ b/juneau-utest/src/test/java/org/apache/juneau/cp/BeanStore_Test.java
@@ -47,274 +47,6 @@ public class BeanStore_Test {
        }
 
        
//-----------------------------------------------------------------------------------------------------------------
-       // Create bean - No args
-       
//-----------------------------------------------------------------------------------------------------------------
-
-       public static class B1 {
-               public static B1 create() {
-                       return new B1();
-               }
-               private B1() {}
-       }
-
-       @Test
-       public void b01_createBean_create() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertObject(bs.createBean(B1.class)).isType(B1.class);
-       }
-
-       public static class B2 {
-               public static B2 getInstance() {
-                       return new B2();
-               }
-               private B2() {}
-       }
-
-       @Test
-       public void b02_createBean_getInstance() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertObject(bs.createBean(B2.class)).isType(B2.class);
-       }
-
-       public static class B3a {
-               protected static B3a create() {
-                       return new B3a();
-               }
-               private B3a() {}
-       }
-
-       @Test
-       public void b03a_createBean_create_notVisible() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(B3a.class)).message().is("Could 
not instantiate class "+CNAME+"$B3a: Public constructor or creator not found.");
-       }
-
-       public static class B3b {
-               public static B3b create2() {
-                       return new B3b();
-               }
-               private B3b() {}
-       }
-
-       @Test
-       public void b03b_createBean_create_wrongName() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(B3b.class)).message().is("Could 
not instantiate class "+CNAME+"$B3b: Public constructor or creator not found.");
-       }
-
-       public static class B3c {
-               public static B3b create() {
-                       return new B3b();
-               }
-               private B3c() {}
-       }
-
-       @Test
-       public void b03c_createBean_create_wrongReturnType() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(B3c.class)).message().is("Could 
not instantiate class "+CNAME+"$B3c: Public constructor or creator not found.");
-       }
-
-       public static class B3d {
-               @Deprecated
-               public static B3d create() {
-                       return new B3d();
-               }
-               private B3d() {}
-       }
-
-       @Test
-       public void b03d_createBean_create_deprecated() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(B3d.class)).message().is("Could 
not instantiate class "+CNAME+"$B3d: Public constructor or creator not found.");
-       }
-
-       public static class B3e {
-               @BeanIgnore
-               public static B3e create() {
-                       return new B3e();
-               }
-               private B3e() {}
-       }
-
-       @Test
-       public void b03e_createBean_create_beanIgnore() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(B3e.class)).message().is("Could 
not instantiate class "+CNAME+"$B3e: Public constructor or creator not found.");
-       }
-
-       public abstract static class B4a {
-               public static B4a create() {
-                       return new B4a() {};
-               }
-               private B4a() {}
-       }
-
-       @Test
-       public void b04a_createBean_create_abstract() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertObject(bs.createBean(B4a.class)).exists();
-       }
-
-       public static interface B4b {
-               public static B4b create() {
-                       return new B4b() {};
-               }
-       }
-
-       @Test
-       public void b04b_createBean_create_interface() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertObject(bs.createBean(B4b.class)).exists();
-       }
-
-       
//-----------------------------------------------------------------------------------------------------------------
-       // Create bean - With args
-       
//-----------------------------------------------------------------------------------------------------------------
-
-       public static class C1a {
-               public A a;
-               public static C1a create(A a) {
-                       C1a x = new C1a();
-                       x.a = a;
-                       return x;
-               }
-               private C1a() {}
-       }
-
-       @Test
-       public void c01_createBean_create_withArgs() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(C1a.class)).message().is("Could 
not instantiate class "+CNAME+"$C1a: Static creator found but could not find 
prerequisites: A.");
-               bs.addBean(A.class, new A());
-               assertObject(bs.createBean(C1a.class)).exists();
-               assertObject(bs.createBean(C1a.class)).exists();
-       }
-
-       public interface C2a {
-               public static C2a create(A a) {
-                       return new C2a(){};
-               }
-       }
-
-       @Test
-       public void c02a_createBean_create_withArgs_interface() throws 
Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(C2a.class)).message().is("Could 
not instantiate class "+CNAME+"$C2a: Static creator found but could not find 
prerequisites: A.");
-               bs.addBean(A.class, new A());
-               assertObject(bs.createBean(C2a.class)).exists();
-               assertObject(bs.createBean(C2a.class)).exists();
-       }
-
-       public static abstract class C2b {
-               public static C2b create(A a) {
-                       return new C2b(){};
-               }
-       }
-
-       @Test
-       public void c02b_createBean_create_withArgs_abstractClass() throws 
Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(C2b.class)).message().is("Could 
not instantiate class "+CNAME+"$C2b: Static creator found but could not find 
prerequisites: A.");
-               bs.addBean(A.class, new A());
-               assertObject(bs.createBean(C2b.class)).exists();
-               assertObject(bs.createBean(C2b.class)).exists();
-       }
-
-       public static interface C2c {}
-
-       @Test
-       public void c02c_createBean_create_withArgs_interface() throws 
Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(C2c.class)).message().is("Could 
not instantiate class "+CNAME+"$C2c: Class is an interface.");
-               bs.addBean(A.class, new A());
-               assertThrown(()->bs.createBean(C2c.class)).message().is("Could 
not instantiate class "+CNAME+"$C2c: Class is an interface.");
-       }
-
-       public static abstract class C2d {}
-
-       @Test
-       public void c02d_createBean_create_withArgs_abstractClass() throws 
Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(C2d.class)).message().is("Could 
not instantiate class "+CNAME+"$C2d: Class is abstract.");
-               bs.addBean(A.class, new A());
-               assertThrown(()->bs.createBean(C2d.class)).message().is("Could 
not instantiate class "+CNAME+"$C2d: Class is abstract.");
-       }
-
-       public static class C3a {
-               public A a;
-               public static C3a create(@Named("Foo") A a) {
-                       C3a x = new C3a();
-                       x.a = a;
-                       return x;
-               }
-               private C3a() {}
-       }
-
-       @Test
-       public void c03_createBean_create_withNamedArgs() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(C3a.class)).message().is("Could 
not instantiate class "+CNAME+"$C3a: Static creator found but could not find 
prerequisites: A.");
-               bs.addBean("Foo", new A());
-               assertObject(bs.createBean(C3a.class)).exists();
-               assertObject(bs.createBean(C3a.class)).exists();
-       }
-
-       
//-----------------------------------------------------------------------------------------------------------------
-       // Construct bean - With args
-       
//-----------------------------------------------------------------------------------------------------------------
-
-       public static class D1a {
-               public A a;
-               public D1a(A a) {
-                       this.a = a;
-               }
-       }
-
-       @Test
-       public void d01a_createBean_construct_withArgs() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(D1a.class)).message().is("Could 
not instantiate class "+CNAME+"$D1a: Public constructor found but could not 
find prerequisites: A.");
-               bs.addBean(A.class, new A());
-               assertObject(bs.createBean(D1a.class)).exists();
-               assertObject(bs.createBean(D1a.class)).exists();
-       }
-
-       public class D1b {
-               public A a;
-               public D1b(A a) {
-                       this.a = a;
-               }
-       }
-
-       @Test
-       public void d01b_createBean_construct_withArgs_inner() throws Exception 
{
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(D1b.class)).message().is("Could 
not instantiate class "+CNAME+"$D1b: Public constructor found but could not 
find prerequisites: BeanStore_Test,A.");
-               BeanStore bs2 = BeanStore.of(null,this);
-               assertThrown(()->bs2.createBean(D1b.class)).message().is("Could 
not instantiate class "+CNAME+"$D1b: Public constructor found but could not 
find prerequisites: A.");
-               bs2.addBean(A.class, new A());
-               assertObject(bs2.createBean(D1b.class)).exists();
-               assertObject(bs2.createBean(D1b.class)).exists();
-       }
-
-       public static class D2a {
-               public A a;
-               public D2a(@Named("Foo") A a) {
-                       this.a = a;
-               }
-       }
-
-       @Test
-       public void d02a_createBean_construct_withNamedArgs() throws Exception {
-               BeanStore bs = new BeanStore();
-               assertThrown(()->bs.createBean(D2a.class)).message().is("Could 
not instantiate class "+CNAME+"$D2a: Public constructor found but could not 
find prerequisites: A.");
-               bs.addBean("Foo", new A());
-               assertObject(bs.createBean(D2a.class)).exists();
-               assertObject(bs.createBean(D2a.class)).exists();
-       }
-
-       
//-----------------------------------------------------------------------------------------------------------------
        // Create bean via method.
        
//-----------------------------------------------------------------------------------------------------------------
 
@@ -402,70 +134,67 @@ public class BeanStore_Test {
                BeanStore bs = BeanStore.create().build();
                E1 x = new E1();
 
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA0").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA1").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA2").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA3").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA4").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA5").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA6").run()).isNull();
-               assertThrown(()->bs.beanCreateMethodFinder(E.class, 
x).find("createA7").run()).message().is("foo");
-
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB0").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB1").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB2").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB3").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB4").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB5").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createB6").run()).isNull();
-               assertThrown(()->bs.beanCreateMethodFinder(E.class, 
x).find("createB7").run()).message().is("foo");
-
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC1").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC2").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run().a).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA0").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA1").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA2").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA3").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA4").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA5").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA6").run()).isNull();
+               assertThrown(()->bs.createMethodFinder(E.class, 
x).find("createA7").run()).message().is("foo");
+
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB0").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB1").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB2").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB3").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB4").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB5").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createB6").run()).isNull();
+               assertThrown(()->bs.createMethodFinder(E.class, 
x).find("createB7").run()).message().is("foo");
+
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC1").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC2").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run().a).isNull();
                bs.addBean(A.class, new A());
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC1").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC2").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run().a).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC1").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC2").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run().a).exists();
                bs.addSupplier(A.class, ()->(A)null);
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC1").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC2").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run().a).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC1").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC2").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run().a).isNull();
                bs.addSupplier(A.class, ()->new A());
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC1").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC2").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run().a).exists();
-
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC4").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC5").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC5").run().a).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC1").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC2").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run().a).exists();
+
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC4").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC5").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC5").run().a).isNull();
                bs.addSupplier("Foo", ()->new A());
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC4").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC5").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC5").run().a).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC4").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC5").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC5").run().a).exists();
                bs.addSupplier("Foo", null);
 
                bs.addSupplier(A.class, ()->null);
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC1").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC2").run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createC3").run().a).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC1").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC2").run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createC3").run().a).isNull();
 
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createAx").thenFind("createA1").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA1").thenFind("createAx").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA1", A.class).thenFind("createA2", A.class).run()).isNull();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA1", A.class).thenFind("createA1").run()).exists();
-               assertObject(bs.beanCreateMethodFinder(E.class, 
x).find("createA1", A.class).withDefault(new E()).run()).exists();
-
-               bs.addSupplier(A.class, ()->new A());
-               assertObject(bs.createBean(A.class)).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createAx").thenFind("createA1").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, 
x).find("createA1").thenFind("createAx").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, x).find("createA1", 
A.class).thenFind("createA2", A.class).run()).isNull();
+               assertObject(bs.createMethodFinder(E.class, x).find("createA1", 
A.class).thenFind("createA1").run()).exists();
+               assertObject(bs.createMethodFinder(E.class, x).find("createA1", 
A.class).withDefault(new E()).run()).exists();
 
                BeanStore bs2 = BeanStore.of(bs, null);
-               assertObject(bs2.beanCreateMethodFinder(E.class, 
x).find("createA1").run()).exists();
+               assertObject(bs2.createMethodFinder(E.class, 
x).find("createA1").run()).exists();
 
                
assertString(bs2.toString()).is("{parent:{beanMap:['"+CNAME+"$A']}}");
        }
diff --git 
a/juneau-utest/src/test/java/org/apache/juneau/mstat/MethodExecStore_Test.java 
b/juneau-utest/src/test/java/org/apache/juneau/mstat/MethodExecStore_Test.java
index 3752f7e..64e5b06 100644
--- 
a/juneau-utest/src/test/java/org/apache/juneau/mstat/MethodExecStore_Test.java
+++ 
b/juneau-utest/src/test/java/org/apache/juneau/mstat/MethodExecStore_Test.java
@@ -42,7 +42,7 @@ public class MethodExecStore_Test {
 
        @Test
        public void a02_builder_implClass() {
-               
assertObject(MethodExecStore.create().implClass(A1.class).build()).isType(A1.class);
+               
assertObject(MethodExecStore.create().type(A1.class).build()).isType(A1.class);
        }
 
        public static class A4 extends MethodExecStore {
@@ -54,7 +54,7 @@ public class MethodExecStore_Test {
 
        @Test
        public void a04_builder_implClass_bad() {
-               
assertThrown(()->MethodExecStore.create().implClass(A4.class).build()).messages().contains("foobar");
+               
assertThrown(()->MethodExecStore.create().type(A4.class).build()).messages().contains("foobar");
        }
 
        public static class A5a {}
@@ -79,12 +79,12 @@ public class MethodExecStore_Test {
        public void a05_builder_beanFactory() throws Exception {
                BeanStore bs = BeanStore.create().build();
 
-               
assertThrown(()->MethodExecStore.create().beanStore(bs).implClass(A5b.class).build()).messages().any(contains("Public
 constructor found but could not find prerequisites: A5a"));
-               
assertObject(MethodExecStore.create().beanStore(bs).implClass(A5c.class).build()).isType(A5c.class);
+               
assertThrown(()->MethodExecStore.create().beanStore(bs).type(A5b.class).build()).messages().any(contains("Public
 constructor found but could not find prerequisites: A5a"));
+               
assertObject(MethodExecStore.create().beanStore(bs).type(A5c.class).build()).isType(A5c.class);
 
                bs.addBean(A5a.class, new A5a());
-               
assertObject(MethodExecStore.create().beanStore(bs).implClass(A5b.class).build()).isType(A5b.class);
-               
assertObject(MethodExecStore.create().beanStore(bs).implClass(A5c.class).build()).isType(A5c.class);
+               
assertObject(MethodExecStore.create().beanStore(bs).type(A5b.class).build()).isType(A5b.class);
+               
assertObject(MethodExecStore.create().beanStore(bs).type(A5c.class).build()).isType(A5c.class);
        }
 
 
diff --git 
a/juneau-utest/src/test/java/org/apache/juneau/mstat/ThrownStore_Test.java 
b/juneau-utest/src/test/java/org/apache/juneau/mstat/ThrownStore_Test.java
index 55fa449..2f694ba 100644
--- a/juneau-utest/src/test/java/org/apache/juneau/mstat/ThrownStore_Test.java
+++ b/juneau-utest/src/test/java/org/apache/juneau/mstat/ThrownStore_Test.java
@@ -195,7 +195,7 @@ public class ThrownStore_Test {
 
        @Test
        public void b02_builder_implClass() {
-               
assertObject(ThrownStore.create().implClass(B1.class).build()).isType(B1.class);
+               
assertObject(ThrownStore.create().type(B1.class).build()).isType(B1.class);
        }
 
        public static class B4 extends ThrownStore {
@@ -206,7 +206,7 @@ public class ThrownStore_Test {
 
        @Test
        public void b04_builder_implClass_bad() {
-               
assertThrown(()->ThrownStore.create().implClass(B4.class).build()).messages().contains("foobar");
+               
assertThrown(()->ThrownStore.create().type(B4.class).build()).messages().contains("foobar");
        }
 
        public static class B5a {}
@@ -229,12 +229,12 @@ public class ThrownStore_Test {
        public void b05_builder_beanFactory() throws Exception {
                BeanStore bs = BeanStore.create().build();
 
-               
assertThrown(()->ThrownStore.create().beanStore(bs).implClass(B5b.class).build()).messages().any(contains("Public
 constructor found but could not find prerequisites: B5a"));
-               
assertObject(ThrownStore.create().beanStore(bs).implClass(B5c.class).build()).isType(B5c.class);
+               
assertThrown(()->ThrownStore.create().beanStore(bs).type(B5b.class).build()).messages().any(contains("Public
 constructor found but could not find prerequisites: B5a"));
+               
assertObject(ThrownStore.create().beanStore(bs).type(B5c.class).build()).isType(B5c.class);
 
                bs.addBean(B5a.class, new B5a());
-               
assertObject(ThrownStore.create().beanStore(bs).implClass(B5b.class).build()).isType(B5b.class);
-               
assertObject(ThrownStore.create().beanStore(bs).implClass(B5c.class).build()).isType(B5c.class);
+               
assertObject(ThrownStore.create().beanStore(bs).type(B5b.class).build()).isType(B5b.class);
+               
assertObject(ThrownStore.create().beanStore(bs).type(B5c.class).build()).isType(B5c.class);
        }
 
        public static class B6a {}

Reply via email to