Improved SCGI server's handling of its environment.
authorFredrik Tolf <fredrik@dolda2000.com>
Fri, 10 Sep 2010 04:29:04 +0000 (06:29 +0200)
committerFredrik Tolf <fredrik@dolda2000.com>
Fri, 10 Sep 2010 04:29:04 +0000 (06:29 +0200)
src/dolda/jsvc/scgi/DSContext.java
src/dolda/jsvc/scgi/DirServer.java
src/dolda/jsvc/scgi/Environment.java [new file with mode: 0644]
src/dolda/jsvc/util/SimpleContext.java [moved from src/dolda/jsvc/util/JarContext.java with 53% similarity]

index 9103525..c726887 100644 (file)
@@ -1,40 +1,47 @@
 package dolda.jsvc.scgi;
 
 import java.io.*;
+import java.net.*;
 import dolda.jsvc.*;
 import dolda.jsvc.util.*;
 
-public class DSContext extends JarContext {
+public class DSContext extends SimpleContext {
     public final long mtime;
-    private final File datroot;
     public final ThreadContext tg;
+    private final Environment env;
 
-    public DSContext(File jar, File datroot) throws ThreadContext.CreateException {
-       super(jar);
+    private static String mangle(File f) {
+       String ret = f.getName();
+       int p = ret.lastIndexOf('.');
+       if(p > 0)
+           ret = ret.substring(0, p);
+       for(f = f.getParentFile(); f != null; f = f.getParentFile())
+           ret = f.getName() + "/" + ret;
+       return(ret);
+    }
+
+    private static URL makingmewanttokilljavac(File jar) {
+       try {
+           return(jar.toURI().toURL());
+       } catch(MalformedURLException e) {
+           throw(new RuntimeException(e));
+       }
+    }
+
+    public DSContext(File jar, Environment env) throws ThreadContext.CreateException {
+       super(URLClassLoader.newInstance(new URL[] {makingmewanttokilljavac(jar)}, env.libloader()), mangle(jar));
        this.mtime = jar.lastModified();
-       this.datroot = datroot;
+       this.env = env;
        loadconfig();
        this.tg = ThreadContext.create(this, loader);
     }
     
     private void loadconfig() {
-       if(datroot != null) {
-           File sroot = new File(new File(datroot, "store"), name());
+       if(env.root != null) {
+           File sroot = new File(new File(env.root, "store"), name());
            sysconfig.put("jsvc.storage", "file:" + sroot.getPath());
-           File conf = new File(datroot, "jsvc.properties");
-           if(conf.exists()) {
-               try {
-                   InputStream in = new FileInputStream(conf);
-                   try {
-                       sysconfig.load(in);
-                   } finally {
-                       in.close();
-                   }
-               } catch(IOException e) {
-                   throw(new RuntimeException(e));
-               }
-           }
        }
+       sysconfig.putAll(env.sysconfig);
     }
     
     public RequestThread worker(Responder root, Request req, ThreadGroup tg, String name) {
index bd8d43c..7920977 100644 (file)
@@ -10,12 +10,12 @@ import dolda.jsvc.j2ee.PosixArgs;
 
 public class DirServer extends Server {
     private final Map<File, DSContext> contexts = new HashMap<File, DSContext>();
-    private final File datroot;
+    private final Environment env;
     private final Logger logger = Logger.getLogger("dolda.jsvc.scgi.dirserver");
     
-    public DirServer(ServerSocket sk, File datroot) {
+    public DirServer(ServerSocket sk, Environment env) {
        super(sk);
-       this.datroot = datroot;
+       this.env = env;
     }
 
     private DSContext context(File file) throws ThreadContext.CreateException {
@@ -31,7 +31,7 @@ public class DirServer extends Server {
                }
            }
            if(ctx == null) {
-               ctx = new DSContext(file, datroot);
+               ctx = new DSContext(file, env);
                contexts.put(file, ctx);
                logger.config(String.format(act, file, ctx.name()));
            }
@@ -85,11 +85,8 @@ public class DirServer extends Server {
            usage(System.err);
            System.exit(1);
        }
-       if(datroot == null) {
-           datroot = new File(System.getProperty("user.home"), ".jsvc");
-           if(!datroot.exists() || !datroot.isDirectory())
-               datroot = null;
-       }
+       Environment env = (datroot == null)?new Environment():new Environment(datroot);
+       env.initvm();
        int port = Integer.parseInt(opt.rest[0]);
        ServerSocket sk;
        try {
@@ -99,7 +96,7 @@ public class DirServer extends Server {
            System.exit(1);
            return; /* Because javac is stupid. :-/ */
        }
-       DirServer s = new DirServer(sk, datroot);
+       DirServer s = new DirServer(sk, env);
        if(charset != null)
            s.headcs = charset;
        
diff --git a/src/dolda/jsvc/scgi/Environment.java b/src/dolda/jsvc/scgi/Environment.java
new file mode 100644 (file)
index 0000000..e91f57a
--- /dev/null
@@ -0,0 +1,87 @@
+package dolda.jsvc.scgi;
+
+import java.io.*;
+import java.net.*;
+import java.util.*;
+
+public class Environment {
+    public final File root;
+    public final Properties sysconfig = new Properties();
+    private ClassLoader lib = null;
+    
+    public Environment(File root) {
+       this.root = root;
+       if(root != null)
+           loadconfig();
+    }
+    
+    private static File defroot() {
+       File root = new File(System.getProperty("user.home"), ".jsvc");
+       if(root.exists() && root.isDirectory())
+           return(root);
+       return(null);
+    }
+
+    public Environment() {
+       this(defroot());
+    }
+    
+    private void loadconfig() {
+       File conf = new File(root, "jsvc.properties");
+       if(conf.exists()) {
+           try {
+               InputStream in = new FileInputStream(conf);
+               try {
+                   sysconfig.load(in);
+               } finally {
+                   in.close();
+               }
+           } catch(IOException e) {
+               throw(new RuntimeException(e));
+           }
+       }
+       File lib = new File(root, "lib");
+       if(lib.exists() && lib.isDirectory()) {
+           List<URL> jars = new ArrayList<URL>();
+           for(File f : lib.listFiles()) {
+               if(f.isDirectory())
+                   continue;
+               if(!f.canRead())
+                   continue;
+               String nm = f.getName();
+               if((nm.length() < 4) || !nm.substring(nm.length() - 4).equals(".jar"))
+                   continue;
+               try {
+                   jars.add(f.toURI().toURL());
+               } catch(MalformedURLException e) {
+                   throw(new Error(e));
+               }
+           }
+           this.lib = URLClassLoader.newInstance(jars.toArray(new URL[0]), Environment.class.getClassLoader());
+       }
+    }
+    
+    public ClassLoader libloader() {
+       if(this.lib == null)
+           return(Environment.class.getClassLoader());
+       return(this.lib);
+    }
+    
+    public void initvm() {
+       if(root == null)
+           return;
+       File logging = new File(root, "logging.properties");
+       if(logging.exists() && logging.canRead()) {
+           try {
+               InputStream in = new FileInputStream(logging);
+               try {
+                   java.util.logging.LogManager.getLogManager().readConfiguration(in);
+               } finally {
+                   in.close();
+               }
+           } catch(IOException e) {
+               throw(new RuntimeException(e));
+           }
+       }
+    }
+}
similarity index 53%
rename from src/dolda/jsvc/util/JarContext.java
rename to src/dolda/jsvc/util/SimpleContext.java
index cb16d37..0849101 100644 (file)
@@ -2,25 +2,14 @@ package dolda.jsvc.util;
 
 import java.io.*;
 import java.util.*;
-import java.net.*;
 import dolda.jsvc.*;
 
-public class JarContext implements ServerContext {
+public class SimpleContext implements ServerContext {
     private final long ctime;
     private final String name;
     public final ClassLoader loader;
     protected final Properties sysconfig, libconfig;
     
-    private static String mangle(File f) {
-       String ret = f.getName();
-       int p = ret.lastIndexOf('.');
-       if(p > 0)
-           ret = ret.substring(0, p);
-       for(f = f.getParentFile(); f != null; f = f.getParentFile())
-           ret = f.getName() + "/" + ret;
-       return(ret);
-    }
-
     private void loadconfig() {
        try {
            InputStream pi = loader.getResourceAsStream("jsvc.properties");
@@ -36,20 +25,7 @@ public class JarContext implements ServerContext {
        }
     }
 
-    public Class<?> findboot() {
-       String clnm = libconfig("jsvc.bootstrap", null);
-       if(clnm == null)
-           return(null);
-       Class<?> bc;
-       try {
-           bc = loader.loadClass(clnm);
-       } catch(ClassNotFoundException e) {
-           return(null);
-       }
-       return(bc);
-    }
-
-    public JarContext(ClassLoader cl, String name) {
+    public SimpleContext(ClassLoader cl, String name) {
        this.ctime = System.currentTimeMillis();
        this.name = name;
        this.loader = cl;
@@ -59,18 +35,6 @@ public class JarContext implements ServerContext {
        loadconfig();
     }
     
-    private static URL makingmewanttokilljavac(File jar) {
-       try {
-           return(jar.toURI().toURL());
-       } catch(MalformedURLException e) {
-           throw(new RuntimeException(e));
-       }
-    }
-
-    public JarContext(File jar) {
-       this(new URLClassLoader(new URL[] {makingmewanttokilljavac(jar)}, JarContext.class.getClassLoader()), mangle(jar));
-    }
-    
     public long starttime() {
        return(ctime);
     }