You are viewing a plain text version of this content. The canonical link for it is here.
Posted to cvs@cocoon.apache.org by re...@apache.org on 2008/04/14 16:22:18 UTC

svn commit: r647812 - in /cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve: jnet/ jnet/source/ test/

Author: reinhard
Date: Mon Apr 14 07:22:15 2008
New Revision: 647812

URL: http://svn.apache.org/viewvc?rev=647812&view=rev
Log:
COCOON-2195 Refactoring of JNet

. make the hierarchy of URLStreamHandlerFactories an internal concept
. the DynamicURLStreamHandlerFactory uses a LinkedList for storing factories

Added:
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/URLStreamHandlerFactoryInstaller.java
      - copied, changed from r647793, cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/Installer.java
Removed:
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/Installer.java
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/ParentAwareURLStreamHandlerFactory.java
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/URLStreamHandlerFactoryWrapper.java
Modified:
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/DynamicURLStreamHandlerFactory.java
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/source/SourceURLStreamHandlerFactory.java
    cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/test/Test.java

Modified: cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/DynamicURLStreamHandlerFactory.java
URL: http://svn.apache.org/viewvc/cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/DynamicURLStreamHandlerFactory.java?rev=647812&r1=647811&r2=647812&view=diff
==============================================================================
--- cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/DynamicURLStreamHandlerFactory.java (original)
+++ cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/DynamicURLStreamHandlerFactory.java Mon Apr 14 07:22:15 2008
@@ -18,33 +18,50 @@
 
 import java.net.URLStreamHandler;
 import java.net.URLStreamHandlerFactory;
+import java.util.LinkedList;
+import java.util.List;
 
-public class DynamicURLStreamHandlerFactory extends ParentAwareURLStreamHandlerFactory {
+public class DynamicURLStreamHandlerFactory implements URLStreamHandlerFactory {
 
-    protected static final ThreadLocal FACTORY = new InheritableThreadLocal();
+    private static final ThreadLocal<List<URLStreamHandlerFactory>> FACTORIES = new InheritableThreadLocal<List<URLStreamHandlerFactory>>();
+
+    public static void pop() {
+        getList().remove(0);
+    }
 
     public static void push(URLStreamHandlerFactory factory) {
-        // no need to synchronize as we use a thread local
-        if ( !(factory instanceof ParentAwareURLStreamHandlerFactory) ) {
-            factory = new URLStreamHandlerFactoryWrapper(factory);
-        }
-        URLStreamHandlerFactory old = (URLStreamHandlerFactory) FACTORY.get();
-        ((ParentAwareURLStreamHandlerFactory)factory).setParentFactory(old);
-        FACTORY.set(factory);
+        getList().add(0, factory);
     }
 
-    public static void pop() {
-        ParentAwareURLStreamHandlerFactory factory = (ParentAwareURLStreamHandlerFactory)FACTORY.get();
-        if ( factory != null ) {
-            FACTORY.set(factory.getParent());
+    private static List<URLStreamHandlerFactory> getList() {
+        List<URLStreamHandlerFactory> list = FACTORIES.get();
+
+        if (list == null) {
+            list = new LinkedList<URLStreamHandlerFactory>();
+            FACTORIES.set(list);
         }
+
+        return list;
     }
 
     /**
-     * @see org.apache.excalibur.sourceresolve.jnet.ParentAwareURLStreamHandlerFactory#create(java.lang.String)
+     * {@inheritDoc}
+     * 
+     * @see java.net.URLStreamHandlerFactory#createURLStreamHandler(java.lang.String)
      */
-    protected URLStreamHandler create(String protocol) {
-        ParentAwareURLStreamHandlerFactory factory = (ParentAwareURLStreamHandlerFactory)FACTORY.get();
-        return factory.createURLStreamHandler(protocol);
+    public URLStreamHandler createURLStreamHandler(String protocol) {
+        System.out.println("DynamicURLStreamHandlerFactory.createURLStreamHandler(" + protocol + ")");
+        List<URLStreamHandlerFactory> list = getList();
+
+        for (URLStreamHandlerFactory urlStreamHandlerFactory : list) {
+            System.out.println("DynamicURLStreamHandlerFactory calling " + urlStreamHandlerFactory);
+            URLStreamHandler handler = urlStreamHandlerFactory.createURLStreamHandler(protocol);
+
+            if (handler != null) {
+                return handler;
+            }
+        }
+
+        return null;
     }
 }

Copied: cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/URLStreamHandlerFactoryInstaller.java (from r647793, cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/Installer.java)
URL: http://svn.apache.org/viewvc/cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/URLStreamHandlerFactoryInstaller.java?p2=cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/URLStreamHandlerFactoryInstaller.java&p1=cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/Installer.java&r1=647793&r2=647812&rev=647812&view=diff
==============================================================================
--- cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/Installer.java (original)
+++ cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/URLStreamHandlerFactoryInstaller.java Mon Apr 14 07:22:15 2008
@@ -19,40 +19,36 @@
 import java.lang.reflect.Field;
 import java.lang.reflect.Modifier;
 import java.net.URL;
+import java.net.URLStreamHandler;
 import java.net.URLStreamHandlerFactory;
 
 /**
- * The installer is a general purpose class to install an own
- * {@link URLStreamHandlerFactory} in any environment.
+ * The installer is a general purpose class to install an own {@link URLStreamHandlerFactory} in any environment.
  */
-public class Installer {
+public class URLStreamHandlerFactoryInstaller {
 
     public static void setURLStreamHandlerFactory(URLStreamHandlerFactory factory) throws Exception {
         try {
             // if we can set the factory, its the first!
-            URL.setURLStreamHandlerFactory(factory);
+            URL.setURLStreamHandlerFactory(new ParentableURLStreamHandlerFactory(factory, null));
         } catch (Error err) {
-            Field factoryField = getFactoryField();
+            ParentableURLStreamHandlerFactory currentFactory = getCurrentFactory();
+            setCurrentFactory(new ParentableURLStreamHandlerFactory(factory, currentFactory));
+        }
+    }
 
-            if (factoryField == null) {
-                throw new Exception(
-                        "Unable to detect static field in the URL class for the URLStreamHandlerFactory. Please report this error together with your exact environment to the Apache Excalibur project.");
-            }
-            try {
-                URLStreamHandlerFactory oldFactory = (URLStreamHandlerFactory) factoryField.get(null);
-                if (factory instanceof ParentAwareURLStreamHandlerFactory) {
-                    ((ParentAwareURLStreamHandlerFactory) factory).setParentFactory(oldFactory);
-                }
-                factoryField.set(null, factory);
-            } catch (IllegalArgumentException e) {
-                throw new Exception("Unable to set url stream handler factory " + factory);
-            } catch (IllegalAccessException e) {
-                throw new Exception("Unable to set url stream handler factory " + factory);
-            }
+    private static ParentableURLStreamHandlerFactory getCurrentFactory() throws Exception {
+        Field factoryField = getFactoryField();
+
+        URLStreamHandlerFactory currentFactory = (URLStreamHandlerFactory) factoryField.get(null);
+        if (currentFactory instanceof ParentableURLStreamHandlerFactory) {
+            return (ParentableURLStreamHandlerFactory) currentFactory;
         }
+
+        return new ParentableURLStreamHandlerFactory(currentFactory, null);
     }
 
-    private static Field getFactoryField() {
+    private static Field getFactoryField() throws Exception {
         // let's use reflection to get the field holding the factory
         final Field[] fields = URL.class.getDeclaredFields();
 
@@ -62,8 +58,35 @@
                 return current;
             }
         }
-        return null;
 
+        throw new Exception("Unable to detect static field in the URL class for the URLStreamHandlerFactory."
+                + " Please report this error together with your exact environment to the Apache Excalibur project.");
+    }
+
+    private static void setCurrentFactory(ParentableURLStreamHandlerFactory parentableURLStreamHandlerFactory) throws Exception {
+        Field factoryField = getFactoryField();
+        factoryField.set(null, parentableURLStreamHandlerFactory);
     }
 
+    private static class ParentableURLStreamHandlerFactory implements URLStreamHandlerFactory {
+
+        private final URLStreamHandlerFactory factory;
+        private final ParentableURLStreamHandlerFactory parent;
+
+        public ParentableURLStreamHandlerFactory(URLStreamHandlerFactory factory, ParentableURLStreamHandlerFactory parent) {
+            super();
+            this.parent = parent;
+            this.factory = factory;
+        }
+
+        public URLStreamHandler createURLStreamHandler(String protocol) {
+            URLStreamHandler handler = this.factory.createURLStreamHandler(protocol);
+
+            if (handler == null && this.parent != null) {
+                handler = this.parent.createURLStreamHandler(protocol);
+            }
+
+            return handler;
+        }
+    }
 }

Modified: cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/source/SourceURLStreamHandlerFactory.java
URL: http://svn.apache.org/viewvc/cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/source/SourceURLStreamHandlerFactory.java?rev=647812&r1=647811&r2=647812&view=diff
==============================================================================
--- cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/source/SourceURLStreamHandlerFactory.java (original)
+++ cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/jnet/source/SourceURLStreamHandlerFactory.java Mon Apr 14 07:22:15 2008
@@ -17,18 +17,17 @@
 package org.apache.excalibur.sourceresolve.jnet.source;
 
 import java.net.URLStreamHandler;
+import java.net.URLStreamHandlerFactory;
 import java.util.Map;
 
 import org.apache.excalibur.source.SourceFactory;
-import org.apache.excalibur.sourceresolve.jnet.ParentAwareURLStreamHandlerFactory;
 
-public class SourceURLStreamHandlerFactory extends ParentAwareURLStreamHandlerFactory {
+public class SourceURLStreamHandlerFactory implements URLStreamHandlerFactory {
 
     /**
      * @see org.apache.excalibur.sourceresolve.jnet.ParentAwareURLStreamHandlerFactory#create(java.lang.String)
      */
-    @Override
-    protected URLStreamHandler create(String protocol) {
+    public URLStreamHandler createURLStreamHandler(String protocol) {
         final Map factories = SourceFactoriesManager.getCurrentFactories();
         final SourceFactory factory = (SourceFactory) factories.get(protocol);
         if (factory != null) {

Modified: cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/test/Test.java
URL: http://svn.apache.org/viewvc/cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/test/Test.java?rev=647812&r1=647811&r2=647812&view=diff
==============================================================================
--- cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/test/Test.java (original)
+++ cocoon/whiteboard/corona/trunk/corona-servlet/src/main/java/org/apache/excalibur/sourceresolve/test/Test.java Mon Apr 14 07:22:15 2008
@@ -22,7 +22,7 @@
 import java.util.Map;
 
 import org.apache.excalibur.source.SourceFactory;
-import org.apache.excalibur.sourceresolve.jnet.Installer;
+import org.apache.excalibur.sourceresolve.jnet.URLStreamHandlerFactoryInstaller;
 import org.apache.excalibur.sourceresolve.jnet.source.SourceFactoriesManager;
 import org.apache.excalibur.sourceresolve.jnet.source.SourceURLStreamHandlerFactory;
 
@@ -30,12 +30,12 @@
 
     public static void main(String[] args) {
         try {
-            Installer.setURLStreamHandlerFactory(new SourceURLStreamHandlerFactory());
-            Installer.setURLStreamHandlerFactory(new SourceURLStreamHandlerFactory());
+            URLStreamHandlerFactoryInstaller.setURLStreamHandlerFactory(new SourceURLStreamHandlerFactory());
+            URLStreamHandlerFactoryInstaller.setURLStreamHandlerFactory(new SourceURLStreamHandlerFactory());
             final Map<String, SourceFactory> factories = new HashMap<String, SourceFactory>();
-            factories.put("carsten", new FileSourceFactory());
+            factories.put("test", new FileSourceFactory());
             SourceFactoriesManager.setGlobalFactories(factories);
-            final URL url = new URL("carsten:///F:/os/cocoon/trunk/pom.xml");
+            final URL url = new URL("test:///F:/os/cocoon/trunk/pom.xml");
             final InputStream is = (InputStream) url.getContent();
             final byte[] b = new byte[100];
             int l = is.read(b);