diff --git a/gsf-core/src/main/java/tools/gsf/config/DefaultFactoryProducer.java b/gsf-core/src/main/java/tools/gsf/config/DefaultFactoryProducer.java index b32338c8..908e3da4 100644 --- a/gsf-core/src/main/java/tools/gsf/config/DefaultFactoryProducer.java +++ b/gsf-core/src/main/java/tools/gsf/config/DefaultFactoryProducer.java @@ -165,14 +165,21 @@ protected Factory getFactory(ICS ics) { *

* This implementation uses the constructor configured in the {@link #CONFIG_FILE}. It also * uses ICS to locate the ServletContext, and then gets the servletContext-backed factory - * which it will use as a delegate for the ics-backed factory. + * which it will use as a delegate for the ics-backed factory, if possible. * * @param ics the ics context * @return the factory */ protected Factory createFactory(ICS ics) { - ServletContext servletContext = ics.getIServlet().getServlet().getServletContext(); - Factory delegate = getFactory(servletContext); + + Factory delegate; + try { + delegate = getFactory(ics.getIServlet().getServlet().getServletContext()); + LOG.debug("Creating ICS-backed factory that delegates to a servletContext-backed factory"); + } catch (RuntimeException e) { + delegate = null; + LOG.debug("Creating ICS-backed factory that has no delegate because no servletContext could be located"); + } Constructor con = factoryConstructors.get(ICS.class); try { diff --git a/gsf-core/src/main/java/tools/gsf/config/FactoryLocator.java b/gsf-core/src/main/java/tools/gsf/config/FactoryLocator.java index e9ba7404..ae4873e9 100644 --- a/gsf-core/src/main/java/tools/gsf/config/FactoryLocator.java +++ b/gsf-core/src/main/java/tools/gsf/config/FactoryLocator.java @@ -16,8 +16,11 @@ package tools.gsf.config; import COM.FutureTense.Interfaces.ICS; +import COM.FutureTense.Interfaces.IServlet; +import javax.servlet.Servlet; import javax.servlet.ServletContext; +import javax.servlet.http.HttpServlet; /** * Utility class for working with the factory producer and factories. @@ -49,12 +52,34 @@ public static FactoryProducer locateFactoryProducer(ServletContext servletContex * Convenience method for locating the factory producer that resides in the servlet context. * Never returns null. * - * @param ics the ics object (which of course holds a pointer to the servlet context) + * @param ics the ics object (which, should of course, hold a pointer to the servlet context). If the + * specified ICS object does NOT hold a pointer to the servlet context, this locator method + * will fall back to the DefaultFactoryProducer class, as there is no defined + * configuration capability for creating custom factory producers without a servlet context. * @return the factory producer, never null */ public static FactoryProducer locateFactoryProducer(ICS ics) { - ServletContext servletContext = ics.getIServlet().getServlet().getServletContext(); - return locateFactoryProducer(servletContext); + if (ics == null) throw new IllegalArgumentException("No ICS found - cannot locate factory without a scope"); + + ServletContext servletContext; + try { + servletContext = ics.getIServlet().getServlet().getServletContext(); + } catch (RuntimeException e) { + servletContext = null; + } + + if (servletContext == null) { + Object o = ics.GetObj(ServletContextLoader.GSF_FACTORY_PRODUCER); + if (o == null) { + // There is no defined configuration capability for a factory producer that does not involve + // the servlet context. Rather than fail, return the default factory producer instead. + o = new DefaultFactoryProducer(); + ics.SetObj(ServletContextLoader.GSF_FACTORY_PRODUCER, o); + } + return (FactoryProducer)o; + } else { + return locateFactoryProducer(servletContext); + } } /** diff --git a/gsf-core/src/main/java/tools/gsf/config/IcsBackedFactory.java b/gsf-core/src/main/java/tools/gsf/config/IcsBackedFactory.java index 6f84493d..a92a900f 100644 --- a/gsf-core/src/main/java/tools/gsf/config/IcsBackedFactory.java +++ b/gsf-core/src/main/java/tools/gsf/config/IcsBackedFactory.java @@ -34,6 +34,7 @@ import tools.gsf.facade.assetapi.asset.TemplateAssetAccess; import tools.gsf.mapping.IcsMappingService; import tools.gsf.mapping.MappingService; +import tools.gsf.time.LoggerStopwatch; import tools.gsf.time.Stopwatch; import tools.gsf.properties.AssetApiPropertyDao; import tools.gsf.properties.PropertyDao; @@ -58,6 +59,11 @@ public IcsBackedFactory(ICS ics, Factory delegate) { this.ics = ics; } + @ServiceProducer + public Stopwatch newStopwatch() { + return LoggerStopwatch.getInstance(); + } + @ServiceProducer(cache = true, name="bindInjector") public Injector createBindInjector() { return new BindInjector(ics);