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 45428d2  Context API refactoring.
45428d2 is described below

commit 45428d2e21d75b6b54b1d242a35e63824b75c291
Author: JamesBognar <[email protected]>
AuthorDate: Sat Sep 11 12:47:59 2021 -0400

    Context API refactoring.
---
 .../main/java/org/apache/juneau/cp/BeanStore.java  |  14 +++
 .../java/org/apache/juneau/rest/RestContext.java   | 123 +++++++--------------
 .../org/apache/juneau/rest/RestContextBuilder.java | 102 ++++++++++++++++-
 3 files changed, 147 insertions(+), 92 deletions(-)

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 f5836d5..ce41fbc 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
@@ -271,6 +271,20 @@ public class BeanStore {
        }
 
        /**
+        * Same as {@link #addBean(Class, Object)} but returns the bean instead 
of this object.
+        *
+        * @param <T> The class to associate this bean with.
+        * @param c The class to associate this bean with.
+        * @param t The bean.
+        * @return The bean.
+        */
+       public <T> T add(Class<T> c, T t) {
+               assertCanWrite();
+               addBean(c.getName(), t);
+               return t;
+       }
+
+       /**
         * Adds a named bean of the specified type to this factory.
         *
         * @param <T> The class to associate this bean with.
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 0e15306..7fd0fbe 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
@@ -260,16 +260,15 @@ public class RestContext extends Context {
                                .addBean(RestContextBuilder.class, builder)
                                .addBean(AnnotationWorkList.class, 
builder.getApplied());
 
-                       BeanStore bf = beanStore;
+                       BeanStore bs = beanStore;
 
-                       Logger l = logger = createLogger(r, builder, bf);
-                       bf.addBean(Logger.class, l);
+                       logger = bs.add(Logger.class, builder.logger());
 
-                       ThrownStore ts = thrownStore = createThrownStore(r, 
builder, parent, bf);
-                       bf.addBean(ThrownStore.class, ts);
+                       ThrownStore ts = thrownStore = createThrownStore(r, 
builder, parent, bs);
+                       bs.addBean(ThrownStore.class, ts);
 
-                       methodExecStore = createMethodExecStore(r, builder, bf, 
ts);
-                       bf.addBean(MethodExecStore.class, methodExecStore);
+                       methodExecStore = createMethodExecStore(r, builder, bs, 
ts);
+                       bs.addBean(MethodExecStore.class, methodExecStore);
 
                        Messages m = messages = createMessages(r, builder);
 
@@ -277,42 +276,41 @@ public class RestContext extends Context {
                                .varResolver()
                                .bean(Messages.class, messages)
                                .build();
-                       bf.addBean(VarResolver.class, vr);
+                       bs.addBean(VarResolver.class, vr);
 
-                       config = builder.config.resolving(vr.createSession());
-                       bf.addBean(Config.class, config);
+                       config = bs.add(Config.class, 
builder.config().resolving(vr.createSession()));
 
-                       responseProcessors = createResponseProcessors(r, 
builder, bf).toArray();
+                       responseProcessors = createResponseProcessors(r, 
builder, bs).toArray();
 
                        callLoggerDefault = builder.callLoggerDefault;
                        debugDefault = builder.debugDefault;
 
-                       callLogger = createCallLogger(r, builder, bf, l, ts);
-                       bf.addBean(RestLogger.class, callLogger);
+                       callLogger = createCallLogger(r, builder, bs, logger, 
ts);
+                       bs.addBean(RestLogger.class, callLogger);
 
-                       partSerializer = createPartSerializer(r, builder, bf);
-                       bf.addBean(HttpPartSerializer.class, partSerializer);
+                       partSerializer = createPartSerializer(r, builder, bs);
+                       bs.addBean(HttpPartSerializer.class, partSerializer);
 
-                       partParser = createPartParser(r, builder, bf);
-                       bf.addBean(HttpPartParser.class, partParser);
+                       partParser = createPartParser(r, builder, bs);
+                       bs.addBean(HttpPartParser.class, partParser);
 
-                       jsonSchemaGenerator = createJsonSchemaGenerator(r, 
builder, bf);
-                       bf.addBean(JsonSchemaGenerator.class, 
jsonSchemaGenerator);
+                       jsonSchemaGenerator = createJsonSchemaGenerator(r, 
builder, bs);
+                       bs.addBean(JsonSchemaGenerator.class, 
jsonSchemaGenerator);
 
-                       fileFinder = createFileFinder(r, builder, bf);
-                       bf.addBean(FileFinder.class, fileFinder);
+                       fileFinder = createFileFinder(r, builder, bs);
+                       bs.addBean(FileFinder.class, fileFinder);
                        fileFinderDefault = 
builder.fileFinderDefault.value().orElse(fileFinder);
 
-                       staticFiles = createStaticFiles(r, builder, bf);
-                       bf.addBean(StaticFiles.class, staticFiles);
+                       staticFiles = createStaticFiles(r, builder, bs);
+                       bs.addBean(StaticFiles.class, staticFiles);
                        staticFilesDefault = 
builder.staticFilesDefault.value().orElse(staticFiles);
 
-                       defaultRequestHeaders = createDefaultRequestHeaders(r, 
builder, bf).build();
-                       defaultResponseHeaders = 
createDefaultResponseHeaders(r, builder, bf).build();
-                       defaultRequestAttributes = 
createDefaultRequestAttributes(r, builder, bf);
+                       defaultRequestHeaders = createDefaultRequestHeaders(r, 
builder, bs).build();
+                       defaultResponseHeaders = 
createDefaultResponseHeaders(r, builder, bs).build();
+                       defaultRequestAttributes = 
createDefaultRequestAttributes(r, builder, bs);
 
-                       opArgs = createOpArgs(r, builder, bf).asArray();
-                       hookMethodArgs = createHookMethodArgs(r, builder, 
bf).asArray();
+                       opArgs = createOpArgs(r, builder, bs).asArray();
+                       hookMethodArgs = createHookMethodArgs(r, builder, 
bs).asArray();
 
                        uriContext = builder.uriContext;
                        uriAuthority = builder.uriAuthority;
@@ -328,7 +326,7 @@ public class RestContext extends Context {
                        defaultCharset = builder.defaultCharset;
                        maxInput = builder.maxInput;
 
-                       debugEnablement = createDebugEnablement(r, builder, bf);
+                       debugEnablement = createDebugEnablement(r, builder, bs);
 
                        path = ofNullable(builder.path).orElse("");
                        fullPath = (builder.parentContext == null ? "" : 
(builder.parentContext.fullPath + '/')) + path;
@@ -338,16 +336,16 @@ public class RestContext extends Context {
                                p += "/*";
                        pathMatcher = UrlPathMatcher.of(p);
 
-                       startCallMethods = createStartCallMethods(r, builder, 
bf).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
-                       endCallMethods = createEndCallMethods(r, builder, 
bf).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
-                       postInitMethods = createPostInitMethods(r, builder, 
bf).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
-                       postInitChildFirstMethods = 
createPostInitChildFirstMethods(r, builder, 
bf).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
-                       destroyMethods = createDestroyMethods(r, builder, 
bf).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
+                       startCallMethods = createStartCallMethods(r, builder, 
bs).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
+                       endCallMethods = createEndCallMethods(r, builder, 
bs).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
+                       postInitMethods = createPostInitMethods(r, builder, 
bs).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
+                       postInitChildFirstMethods = 
createPostInitChildFirstMethods(r, builder, 
bs).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
+                       destroyMethods = createDestroyMethods(r, builder, 
bs).stream().map(this::toMethodInvoker).toArray(MethodInvoker[]::new);
 
-                       preCallMethods = createPreCallMethods(r, builder, 
bf).stream().map(this::toRestOpInvoker).toArray(RestOpInvoker[]:: new);
-                       postCallMethods = createPostCallMethods(r, builder, 
bf).stream().map(this::toRestOpInvoker).toArray(RestOpInvoker[]:: new);
+                       preCallMethods = createPreCallMethods(r, builder, 
bs).stream().map(this::toRestOpInvoker).toArray(RestOpInvoker[]:: new);
+                       postCallMethods = createPostCallMethods(r, builder, 
bs).stream().map(this::toRestOpInvoker).toArray(RestOpInvoker[]:: new);
 
-                       restOperations = createRestOperations(r, builder, bf);
+                       restOperations = createRestOperations(r, builder, bs);
 
                        List<RestOpContext> opContexts = 
restOperations.getOpContexts();
 
@@ -367,9 +365,9 @@ public class RestContext extends Context {
                                consumes = AList.unmodifiable(s);
                        }
 
-                       restChildren = createRestChildren(r, builder, bf, 
builder.inner);
+                       restChildren = createRestChildren(r, builder, bs, 
builder.inner);
 
-                       swaggerProvider = createSwaggerProvider(r, builder, bf, 
fileFinder, m, vr);
+                       swaggerProvider = createSwaggerProvider(r, builder, bs, 
fileFinder, m, vr);
 
                } catch (BasicHttpException e) {
                        _initException = e;
@@ -684,7 +682,6 @@ public class RestContext extends Context {
         *      <br>Created by {@link RestContextBuilder#beanStore()}.
         * @param logger
         *      The Java logger to use for logging messages.
-        *      <br>Created by {@link 
#createLogger(Object,RestContextBuilder,BeanStore)}.
         * @param thrownStore
         *      The thrown exception statistics store.
         *      <br>Created by {@link 
#createThrownStore(Object,RestContextBuilder,RestContext,BeanStore)}.
@@ -736,7 +733,6 @@ public class RestContext extends Context {
         *      <br>Created by {@link RestContextBuilder#beanStore()}.
         * @param logger
         *      The Java logger to use for logging messages.
-        *      <br>Created by {@link 
#createLogger(Object,RestContextBuilder,BeanStore)}.
         * @param thrownStore
         *      The thrown exception statistics store.
         *      <br>Created by {@link 
#createThrownStore(Object,RestContextBuilder,RestContext,BeanStore)}.
@@ -1029,51 +1025,6 @@ public class RestContext extends Context {
        }
 
        /**
-        * Instantiates logger for this REST resource.
-        *
-        * <p>
-        * Instantiates based on the following logic:
-        * <ul>
-        *      <li>Looks for a static or non-static <c>createLogger()</> 
method that returns <c>{@link Logger}</c> on the
-        *              resource class with any of the following arguments:
-        *              <ul>
-        *                      <li>{@link RestContext}
-        *                      <li>{@link BeanStore}
-        *                      <li>Any {@doc RestInjection injected beans}.
-        *              </ul>
-        *      <li>Resolves it via the bean store registered in this context.
-        *      <li>Instantiates via 
<c>Logger.<jsm>getLogger</jsm>(<jv>resource</jv>.getClass().getName())</c>.
-        * </ul>
-        *
-        * @param resource
-        *      The REST servlet or bean that this context defines.
-        * @param builder
-        *      The builder for this object.
-        * @param beanStore
-        *      The factory used for creating beans and retrieving injected 
beans.
-        *      <br>Created by {@link RestContextBuilder#beanStore()}.
-        * @return The logger for this REST resource.
-        * @throws Exception If logger could not be instantiated.
-        */
-       protected Logger createLogger(Object resource, RestContextBuilder 
builder, BeanStore beanStore) throws Exception {
-
-               Logger x = beanStore.getBean(Logger.class).orElse(null);
-
-               if (x == null)
-                       x = Logger.getLogger(className(resource));
-
-               x = BeanStore
-                       .of(beanStore, resource)
-                       .addBean(Logger.class, x)
-                       .beanCreateMethodFinder(Logger.class, resource)
-                       .find("createLogger")
-                       .withDefault(x)
-                       .run();
-
-               return x;
-       }
-
-       /**
         * Instantiates the JSON schema generator for this REST resource.
         *
         * <p>
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 255dd61..59090a0 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
@@ -14,6 +14,7 @@ package org.apache.juneau.rest;
 
 import static org.apache.juneau.assertions.Assertions.*;
 import static org.apache.juneau.http.HttpHeaders.*;
+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.parser.Parser.*;
@@ -27,6 +28,7 @@ import java.lang.reflect.Method;
 import java.nio.charset.*;
 import java.util.*;
 import java.util.function.*;
+import java.util.logging.*;
 import java.util.stream.*;
 
 import javax.servlet.*;
@@ -117,8 +119,10 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
        Supplier<?> resource;
        ServletContext servletContext;
 
-       Config config;
+       private Config config;
        private VarResolver.Builder varResolver;
+       private Logger logger;
+
        String
                allowedHeaderParams = env("RestContext.allowedHeaderParams", 
"Accept,Content-Type"),
                allowedMethodHeaders = env("RestContext.allowedMethodHeaders", 
""),
@@ -309,9 +313,25 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
        public RestContextBuilder init(Object resource) throws ServletException 
{
                this.resource = resource instanceof Supplier ? 
(Supplier<?>)resource : ()->resource;
 
-               ClassInfo rci = ClassInfo.ofProxy(resource);
                BeanStore bs = beanStore();
 
+               runInitHooks(bs, resource());
+               logger();
+
+               return this;
+       }
+
+       private Supplier<?> resource() {
+               if (resource == null)
+                       throw runtimeException("Resource not available.  
init(Object) has not been called.");
+               return resource;
+       }
+
+       private void runInitHooks(BeanStore beanStore, Supplier<?> resource) 
throws ServletException {
+
+               Object r = resource.get();
+               ClassInfo rci = ClassInfo.ofProxy(r);
+
                Map<String,MethodInfo> map = new LinkedHashMap<>();
                for (MethodInfo m : rci.getAllMethodsParentFirst()) {
                        if (m.hasAnnotation(RestHook.class) && 
m.getLastAnnotation(RestHook.class).value() == HookEvent.INIT) {
@@ -321,20 +341,20 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
                                        map.put(sig, m);
                        }
                }
+
                for (MethodInfo m : map.values()) {
                        List<ParamInfo> params = m.getParams();
 
-                       List<ClassInfo> missing = 
bs.getMissingParamTypes(params);
-                       if (!missing.isEmpty())
+                       List<ClassInfo> missing = 
beanStore.getMissingParamTypes(params);
+                       if (! missing.isEmpty())
                                throw new RestServletException("Could not call 
@RestHook(INIT) method {0}.{1}.  Could not find prerequisites: {2}.", 
m.getDeclaringClass().getSimpleName(), m.getSignature(), 
missing.stream().map(x->x.getSimpleName()).collect(Collectors.joining(",")));
 
                        try {
-                               m.invoke(resource, bs.getParams(params));
+                               m.invoke(r, beanStore.getParams(params));
                        } catch (Exception e) {
                                throw new RestServletException(e, "Exception 
thrown from @RestHook(INIT) method {0}.{1}.", 
m.getDeclaringClass().getSimpleName(), m.getSignature());
                        }
                }
-               return this;
        }
 
        /**
@@ -708,6 +728,76 @@ public class RestContextBuilder extends ContextBuilder 
implements ServletConfig
                return v.get();
        }
 
+       /**
+        * Returns the logger to use for the REST resource.
+        *
+        * @return The logger to use for the REST resource.
+        * @throws RuntimeException If {@link #init(Object)} has not been 
called.
+        */
+       public final Logger logger() {
+               if (logger == null)
+                       logger = createLogger(beanStore(), resource());
+               return logger;
+       }
+
+       /**
+        * Sets the logger to use for the REST resource.
+        *
+        * <p>
+        * If not specified, the logger used is created by {@link 
#createLogger(BeanStore, Supplier)}.
+        *
+        * @param value The logger to use for the REST resource.
+        * @return This object.
+        */
+       public final RestContextBuilder logger(Logger value) {
+               logger = value;
+               return this;
+       }
+
+       /**
+        * Instantiates logger for this REST resource.
+        *
+        * <p>
+        * Instantiates based on the following logic:
+        * <ul>
+        *      <li>Looks for a static or non-static <c>createLogger()</> 
method that returns <c>{@link Logger}</c> on the
+        *              resource class with any of the following arguments:
+        *              <ul>
+        *                      <li>{@link RestContext}
+        *                      <li>{@link BeanStore}
+        *                      <li>Any {@doc RestInjection injected beans}.
+        *              </ul>
+        *      <li>Resolves it via the bean store registered in this context.
+        *      <li>Instantiates via 
<c>Logger.<jsm>getLogger</jsm>(<jv>resource</jv>.getClass().getName())</c>.
+        * </ul>
+        *
+        * @param resource
+        *      The REST servlet or bean that this context defines.
+        * @param beanStore
+        *      The factory used for creating beans and retrieving injected 
beans.
+        *      <br>Created by {@link RestContextBuilder#beanStore()}.
+        * @return The logger for this REST resource.
+        */
+       protected Logger createLogger(BeanStore beanStore, Supplier<?> 
resource) {
+
+               Value<Logger> v = Value.empty();
+
+               beanStore.getBean(Logger.class).ifPresent(x -> v.set(x));
+
+               if (v.isEmpty())
+                       v.set(Logger.getLogger(className(resource.get())));
+
+               BeanStore
+                       .of(beanStore, resource.get())
+                       .addBean(Logger.class, v.get())
+                       .beanCreateMethodFinder(Logger.class, resource)
+                       .find("createLogger")
+                       .execute()
+                       .ifPresent(x -> v.set(x));
+
+               return v.get();
+       }
+
        
//----------------------------------------------------------------------------------------------------
        // Methods that give access to the config file, var resolver, and 
properties.
        
//----------------------------------------------------------------------------------------------------

Reply via email to