adding more base objects, started on stack layer. added config parser
authorerickson <erickson@9efc2488-bf62-4759-914b-345cdb29e865>
Thu, 10 May 2007 20:59:27 +0000 (20:59 +0000)
committererickson <erickson@9efc2488-bf62-4759-914b-345cdb29e865>
Thu, 10 May 2007 20:59:27 +0000 (20:59 +0000)
git-svn-id: svn://svn.open-ils.org/OpenSRF/trunk@883 9efc2488-bf62-4759-914b-345cdb29e865

src/java/org/opensrf/ClientSession.java [new file with mode: 0644]
src/java/org/opensrf/Request.java [new file with mode: 0644]
src/java/org/opensrf/ServerSession.java [new file with mode: 0644]
src/java/org/opensrf/Session.java
src/java/org/opensrf/Stack.java [new file with mode: 0644]
src/java/org/opensrf/test/TestConfig.java [new file with mode: 0644]
src/java/org/opensrf/util/Config.java [new file with mode: 0644]
src/java/org/opensrf/util/ConfigException.java [new file with mode: 0644]
src/java/org/opensrf/util/JSONException.java [new file with mode: 0644]
src/java/org/opensrf/util/Utils.java

diff --git a/src/java/org/opensrf/ClientSession.java b/src/java/org/opensrf/ClientSession.java
new file mode 100644 (file)
index 0000000..9f3483e
--- /dev/null
@@ -0,0 +1,40 @@
+package org.opensrf;
+import java.util.Date;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Random;
+
+import org.opensrf.util.*;
+
+
+/**
+ * Models an OpenSRF client session.
+ */
+public class ClientSession extends Session {
+
+    /** The remote service to communicate with */
+    private String service;
+    private String domain;
+    private String router;
+    private String origRemoteNode;
+    private int nextId;
+    private List<Request> requests;
+
+    /**
+     * @param service The remove service to communicate with
+     */
+    public ClientSession(String service) throws ConfigException {
+        this.service = service;
+        domain = (String) Config.getFirst("/domain/domains");
+        router = (String) Config.getString("/router_name");
+        setRemoteNode(router + "@" + domain + "/" + service);
+        origRemoteNode = getRemoteNode();
+        requests = new ArrayList<Request>();
+        nextId = 0;
+        long time = new Date().getTime();
+        Random rand = new Random(time);
+        thread = rand.nextInt()+""+rand.nextInt()+""+time;
+        cacheSession();
+    }
+}
+
diff --git a/src/java/org/opensrf/Request.java b/src/java/org/opensrf/Request.java
new file mode 100644 (file)
index 0000000..b646950
--- /dev/null
@@ -0,0 +1,32 @@
+package org.opensrf;
+import java.util.Queue;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.List;
+import org.opensrf.net.xmpp.XMPPException;
+
+public class Request {
+    
+    private ClientSession session;
+    private Method method;
+    private int id;
+    private Queue<Result> resultQueue;
+    private boolean resetTimeout;
+    private boolean complete;
+
+    public Request(ClientSession ses, int id, Method method) {
+        this.session = ses;
+        this.id = id;
+        this.method = method;
+        resultQueue = new ConcurrentLinkedQueue<Result>();
+        complete = false;
+        resetTimeout = false;
+    }
+
+    public Request(ClientSession ses, int id, String methodName, List<Object> params) {
+        this(ses, id, new Method(methodName, params));
+    }
+
+    public void send() throws XMPPException {
+        session.send(new Message(id, Message.Type.REQUEST, method));
+    }
+}
diff --git a/src/java/org/opensrf/ServerSession.java b/src/java/org/opensrf/ServerSession.java
new file mode 100644 (file)
index 0000000..62e5133
--- /dev/null
@@ -0,0 +1,8 @@
+package org.opensrf;
+
+/**
+ * Models an OpenSRF server session.
+ */
+public class ServerSession extends Session {
+}
+
index fca03fa..2eb9aa9 100644 (file)
@@ -28,7 +28,7 @@ public abstract class Session {
      * In other words, each session has a unique thread, and all messages 
      * in that session will carry this thread around as an indicator.
      */
-    private String thread;
+    protected String thread;
 
     public Session() {
         connectState = ConnectState.DISCONNECTED;
@@ -83,4 +83,15 @@ public abstract class Session {
     public static Session findCachedSession(String thread) {
         return sessionCache.get(thread);
     }
+
+    protected void cacheSession() {
+        sessionCache.put(thread, this);
+    }
+
+    public void setRemoteNode(String nodeName) {
+        remoteNode = nodeName;
+    }
+    public String getRemoteNode() {
+        return remoteNode;
+    }
 }
diff --git a/src/java/org/opensrf/Stack.java b/src/java/org/opensrf/Stack.java
new file mode 100644 (file)
index 0000000..8ee753d
--- /dev/null
@@ -0,0 +1,60 @@
+package org.opensrf;
+import org.opensrf.net.xmpp.XMPPMessage;
+import org.opensrf.util.*;
+import java.util.Date;
+import java.util.List;
+import java.util.Iterator;
+
+
+public class Stack {
+
+    public static void processXMPPMessage(XMPPMessage msg) {
+
+        Session ses = Session.findCachedSession(msg.getThread());
+
+        if(ses == null) {
+            /** inbound client request, create a new server session */
+            return;
+        }
+
+        /** parse the JSON message body, which should result in a list of OpenSRF messages */
+        List msgList; 
+
+        try {
+            msgList = new JSONReader(msg.getBody()).readArray();
+        } catch(JSONException e) {
+            /** XXX LOG error */
+            return;
+        }
+
+        Iterator itr = msgList.iterator();
+
+        OSRFObject obj = null;
+        long start = new Date().getTime();
+
+        while(itr.hasNext()) {
+            /** Construct a Message object from the generic OSRFObject returned from parsing */
+            obj = (OSRFObject) itr.next();
+            processOSRFMessage(ses, 
+                new Message(
+                    ((Integer) obj.get("threadTrace")).intValue(),
+                    (Message.Type) obj.get("type"),
+                    obj.get("payload")));
+        }
+
+        /** LOG the duration */
+    }
+
+    public static void processOSRFMessage(Session ses, Message msg) {
+        if( ses instanceof ClientSession ) 
+            processServerResponse((ClientSession) ses, msg);
+        else
+            processClientRequest((ServerSession) ses, msg);
+    }
+
+    public static void processServerResponse(ClientSession session, Message msg) {
+    }
+
+    public static void processClientRequest(ServerSession session, Message msg) {
+    }
+}
diff --git a/src/java/org/opensrf/test/TestConfig.java b/src/java/org/opensrf/test/TestConfig.java
new file mode 100644 (file)
index 0000000..5cd4eb3
--- /dev/null
@@ -0,0 +1,16 @@
+package org.opensrf.test;
+import org.opensrf.*;
+import org.opensrf.util.*;
+
+public class TestConfig {
+    public static void main(String args[]) throws Exception {
+        Config config = new Config("");
+        config.parse(args[0]);
+        Config.setConfig(config);
+        System.out.println(config);
+        System.out.println("");
+
+        for(int i = 1; i < args.length; i++) 
+            System.out.println("Found config value: " + args[i] + ": " + Config.get(args[i]));
+    }
+}
diff --git a/src/java/org/opensrf/util/Config.java b/src/java/org/opensrf/util/Config.java
new file mode 100644 (file)
index 0000000..6f430c4
--- /dev/null
@@ -0,0 +1,93 @@
+package org.opensrf.util;
+
+import org.json.*;
+import java.util.Map;
+import java.util.List;
+
+
+/**
+ * Config reader and accesor module.  This module reads an XML config file,
+ * then loads the file into an internal config, whose values may be accessed
+ * by xpath-style lookup paths.
+ */
+public class Config {
+
+    /** The globl config instance */
+    private static Config config;
+    /** The object form of the parsed config */
+    private Map configObject;
+    private String context;
+
+    public Config(String context) {
+        this.context = context;
+    }
+
+    /**
+     * Sets the global config object.
+     * @param c The config object to use.
+     */
+    public static void setConfig(Config c) {
+        config = c;
+    }
+
+    /**
+     * Parses an XML config file.
+     * @param filename The path to the file to parse.
+     */
+    public void parse(String filename) throws Exception {
+        String xml = Utils.fileToString(filename);
+        JSONObject jobj = XML.toJSONObject(xml);
+        configObject = (Map) new JSONReader(jobj.toString()).readObject();
+    }
+
+    /**
+     * Returns the configuration value found at the requested path.
+     * @see org.opensrf.util.Utils.findPath for path description.
+     * @param path The search path
+     * @return The config value, or null if no value exists at the given path.  
+     * @throws ConfigException thrown if nothing is found at the path
+     */
+    public static String getString(String path) throws ConfigException {
+        try {
+            return (String) get(path);
+        } catch(Exception e) {
+            throw new 
+                ConfigException("No config string found at " + path);
+        }
+    }
+
+    /**
+     * Returns the configuration object found at the requested path.
+     * @see org.opensrf.util.Utils.findPath for path description.
+     * @param path The search path
+     * @return The config value
+     * @throws ConfigException thrown if nothing is found at the path
+     */
+    public static Object get(String path) throws ConfigException {
+        try {
+            Object obj = Utils.findPath(config.configObject, config.context + path);
+            if(obj == null)
+                throw new ConfigException("");
+            return obj;
+        } catch(Exception e) {
+            e.printStackTrace();
+            throw new ConfigException("No config object found at " + path);
+        }
+    }
+
+    public static Object getFirst(String path) throws ConfigException {
+        Object obj = get(path); 
+        if(obj instanceof List) 
+            return ((List) obj).get(0);
+        return obj;
+    }
+
+
+    /**
+     * Returns the config as a JSON string
+     */
+    public String toString() {
+        return new JSONWriter(configObject).write();
+    }
+}
+
diff --git a/src/java/org/opensrf/util/ConfigException.java b/src/java/org/opensrf/util/ConfigException.java
new file mode 100644 (file)
index 0000000..be7c0cf
--- /dev/null
@@ -0,0 +1,11 @@
+package org.opensrf.util;
+
+/**
+ * Thrown by the Config module when a user requests a configuration
+ * item that does not exist
+ */
+public class ConfigException extends Exception {
+    public ConfigException(String info) {
+        super(info);
+    }
+}
diff --git a/src/java/org/opensrf/util/JSONException.java b/src/java/org/opensrf/util/JSONException.java
new file mode 100644 (file)
index 0000000..69a5c20
--- /dev/null
@@ -0,0 +1,6 @@
+package org.opensrf.util;
+public class JSONException extends Exception {
+    public JSONException(String s) {
+        super(s);
+    }
+}
index 60c476f..9bf819f 100644 (file)
@@ -80,6 +80,26 @@ public class Utils {
             }
         }
     }
+
+
+    /** 
+     * Descends into the map along the given XPATH-style path 
+     * and returns the object found there.
+     * @param path The XPATH-style path to search.  Path 
+     * components are separated by '/' characters.  
+     * Example:  /opensrf/loglevel
+     * @return The found object. 
+     */
+
+    public static Object findPath(Map map, String path) {
+        String keys[] = path.split("/", -1);
+        int i = 0;
+        if(path.charAt(0) == '/') i++;
+        for(; i < keys.length - 1; i++ ) 
+            map = (Map) map.get(keys[i]);
+
+        return map.get(keys[i]);
+    }
 }