[MOBY-guts] biomoby commit

Paul Gordon gordonp at pub.open-bio.org
Thu Apr 1 17:30:08 UTC 2004


gordonp
Thu Apr  1 12:30:08 EST 2004
Update of /home/repository/moby/moby-live/Java/src/main/org/biomoby/client
In directory pub.open-bio.org:/tmp/cvs-serv6601

Modified Files:
	CentralImpl.java 
Log Message:
Implements response caching, and uses JAXP DocumentBuilder to harness a XML parser in a more platform independent way

moby-live/Java/src/main/org/biomoby/client CentralImpl.java,1.8,1.9
===================================================================
RCS file: /home/repository/moby/moby-live/Java/src/main/org/biomoby/client/CentralImpl.java,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -r1.8 -r1.9
--- /home/repository/moby/moby-live/Java/src/main/org/biomoby/client/CentralImpl.java	2004/04/01 16:41:03	1.8
+++ /home/repository/moby/moby-live/Java/src/main/org/biomoby/client/CentralImpl.java	2004/04/01 17:30:08	1.9
@@ -61,11 +61,12 @@
 public class CentralImpl
     implements Central {
 
-
+    private Hashtable cache;  // To not call MOBY Central everytime the same method is called
     private URL endpoint;
     private String uri;
-    private ParserWrapper parser;
+    private javax.xml.parsers.DocumentBuilder docBuilder;
     private boolean debug = false;
+    private boolean useCache = true;
 
     /** Default location (endpoint) of a Moby registry. */
 //     public static final String DEFAULT_ENDPOINT = "http://mobycentral.cbr.nrc.ca/cgi-bin/MOBY-Central.pl";
@@ -118,8 +119,18 @@
 	}
 	this.uri = namespace;
 
-	// instantiate a DOM parser
- 	parser = Utils.getDOMParser();
+	// This method should work on almost all platforms to get an XML parser instance
+        try {
+            javax.xml.parsers.DocumentBuilderFactory dbf = 
+		javax.xml.parsers.DocumentBuilderFactory.newInstance();
+    	    dbf.setNamespaceAware(true);	
+	    docBuilder = dbf.newDocumentBuilder();
+        } catch (Exception e) {
+            throw new MobyException ("Could not configure an XML parser: " + e);
+        }
+
+	cache = new Hashtable();
+	useCache = true;
     }
 
     /*************************************************************************
@@ -192,8 +203,11 @@
 	String id = "", success = "0", message = "";
 
 	// parse returned XML
-	Document document = parser.parse (new StringReader (xml));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(xml));}
+	catch(Exception e){throw new MobyException(e.toString());}
 	Element root = document.getDocumentElement();
+
 	NodeList children = root.getChildNodes();
 	for (int i = 0; i < children.getLength(); i++) {
 	    if (children.item (i).getNodeType() != Node.ELEMENT_NODE)
@@ -403,8 +417,11 @@
      *************************************************************************/
     protected MobyService[] extractServices (String xml)
 	throws MobyException {
+	    
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(xml));}
+	catch(Exception e){throw new MobyException(e.toString());}
 
-	Document document = parser.parse (new StringReader (xml));
 	NodeList list = document.getElementsByTagName ("Service");
 	MobyService[] results = new MobyService [list.getLength()];
 	for (int i = 0; i < list.getLength(); i++) {
@@ -491,18 +508,31 @@
      *************************************************************************/
     public Map getServiceNames()
 	throws MobyException {
+
+	// First, check to se if we have the values cached from a previous call 
+	// in this instance
+	if(useCache && cache.containsKey("retrieveServiceNames"))
+	    return (Map) cache.get("retrieveServiceNames");
+
 	String result = (String)doCall ("retrieveServiceNames",
 					new Object[] {});
 
 	// parse returned XML
 	Map results = new HashMap();
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("serviceName");
 	for (int i = 0; i < list.getLength(); i++) {
 	    Element elem = (Element)list.item (i);
 	    results.put (elem.getAttribute ("name"),
 			 elem.getAttribute ("authURI"));
 	}
+
+	// Add this data to the cache in case we get called again
+	if(useCache)
+	    cache.put("retrieveServiceNames", results);
 	return results;
     }
 
@@ -516,15 +546,27 @@
      *************************************************************************/
     public String[] getProviders()
 	throws MobyException {
+
+	// First, see if we have the values cached from a previous call in this instance
+	if(useCache && cache.containsKey("retrieveServiceProviders"))
+	    return (String[]) cache.get("retrieveServiceProviders");
+
 	String result = (String)doCall ("retrieveServiceProviders",
 					new Object[] {});
 
 	// parse returned XML
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("serviceProvider");
 	String[] results = new String [list.getLength()];
 	for (int i = 0; i < list.getLength(); i++)
 	    results[i] = ((Element)list.item (i)).getAttribute ("name");
+
+	// Add this data to the cache in case we get called again
+	if(useCache)
+	    cache.put("retrieveServiceProviders", results);
 	return results;
     }
 
@@ -541,12 +583,19 @@
      *************************************************************************/
     public Map getServiceTypes()
 	throws MobyException {
+	// First, see if we have the values cached from a previous call in this instance
+	if(useCache && cache.containsKey("retrieveServiceTypes"))
+	    return (Map) cache.get("retrieveServiceTypes");
+
 	String result = (String)doCall ("retrieveServiceTypes",
 					new Object[] {});
 
 	// parse returned XML
 	Map results = new HashMap();
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("serviceType");
 	for (int i = 0; i < list.getLength(); i++) {
 	    Element elem = (Element)list.item (i);
@@ -559,6 +608,10 @@
 		}
 	    }
 	}
+
+	// Add this data to the cache in case we get called again
+	if(useCache)
+	    cache.put("retrieveServiceTypes", results);
 	return results;
     }
 
@@ -575,28 +628,43 @@
      *************************************************************************/
     public Map getNamespaces()
 	throws MobyException {
+
+	// First, see if we have the values cached from a previous call in this instance
+	if(useCache && cache.containsKey("retrieveNamespaces"))
+	    return (Map) cache.get("retrieveNamespaces");
+
 	String result = (String)doCall ("retrieveNamespaces",
 					new Object[] {});
 
 	// parse returned XML
 	Map results = new HashMap();
-	Document document = parser.parse (new StringReader (result));
-	NodeList list = document.getElementsByTagName ("Namespace");
-	for (int i = 0; i < list.getLength(); i++) {
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
+	NodeList list = document.getDocumentElement().getElementsByTagName ("Namespace");
+	if(list == null || list.getLength() == 0){
+	    throw new MobyException("Could not find Namespace children of response root node " + 
+				    document.getDocumentElement());
+	}
+	int length = list.getLength();
+	for (int i = 0; i < length; i++) {
 	    Element elem = (Element)list.item (i);
-	    NodeList children = elem.getChildNodes();
-	    for (int j = 0; j < children.getLength(); j++) {
-		if (children.item (j).getNodeName().equals ("Description")) {
-		    String desc;
-		    if (children.item (j).getFirstChild() == null)
-			desc = "";
-		    else
-			desc = children.item (j).getFirstChild().getNodeValue();
-		    results.put (elem.getAttribute ("name"), desc);
-		    break;
-		}
+	    NodeList children = elem.getElementsByTagName("Description");
+	    if(children.item(0).hasChildNodes()){
+		children.item(0).normalize();
+		results.put (elem.getAttribute ("name"),
+			     children.item(0).getFirstChild().getNodeValue());
+	    }
+	    else{
+		// No description provided
+		results.put (elem.getAttribute ("name"), "");
 	    }
 	}
+	
+	// Add this data to the cache in case we get called again
+	if(useCache)
+	    cache.put("retrieveNamespaces", results);
 	return results;
     }
 
@@ -613,12 +681,19 @@
      *************************************************************************/
     public Map getDataTypeNames()
 	throws MobyException {
+	// First, see if we have the values cached from a previous call in this instance
+	if(useCache && cache.containsKey("retrieveObjectNames"))
+	    return (Map) cache.get("retrieveObjectNames");
+
 	String result = (String)doCall ("retrieveObjectNames",
 					new Object[] {});
 
 	// parse returned XML
 	Map results = new HashMap();
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("Object");
 	for (int i = 0; i < list.getLength(); i++) {
 	    Element elem = (Element)list.item (i);
@@ -631,6 +706,9 @@
 		}
 	    }
 	}
+
+	if(useCache)
+	    cache.put("retrieveObjectNames", results);
 	return results;
     }
 
@@ -655,6 +733,11 @@
      *************************************************************************/
     public MobyDataType getDataType (String dataTypeName)
 	throws MobyException, NoSuccessException {
+
+	// See if we've already retrieved the DataType and cached it
+	if(cache.containsKey("retrieveObjectDefinition"+dataTypeName))
+	    return (MobyDataType) cache.get("retrieveObjectDefinition"+dataTypeName);
+	
 	String result =
 	    (String)doCall ("retrieveObjectDefinition",
 			    new Object[] {
@@ -664,7 +747,10 @@
 			    });
 
 	// parse returned XML
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("retrieveObjectDefinition");
 	if (list == null || list.getLength() == 0)
  	    throw new NoSuccessException ("Data Type name was not founnd.",
@@ -717,6 +803,7 @@
 		}
 	    }
 	}
+	cache.put("retrieveObjectDefinition"+dataTypeName, data);
 	return data;
     }
 
@@ -778,6 +865,11 @@
      *************************************************************************/
     public String getServiceWSDL (String serviceName, String authority)
 	throws MobyException, NoSuccessException {
+	// See if we've already retrieved the DataType and cached it
+	String cacheKey = "getServiceWSDL" + serviceName + ":" + authority;
+	if(cache.containsKey(cacheKey))
+	    return (String) cache.get(cacheKey);
+	
 	String result =
 	    (String)doCall ("retrieveService",
 			    new Object[] {
@@ -787,12 +879,17 @@
 			    });
 
 	// parse returned XML
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	Element service = document.getDocumentElement();
 	Node wsdl = service.getFirstChild();
 	if (wsdl == null)
 	    throw new NoSuccessException ("Service not found OR WSDL is not available.",
 					   serviceName + " (" + authority + ")");
+	if(useCache)
+	    cache.put(cacheKey, wsdl.getNodeValue());
 	return wsdl.getNodeValue();
     }
 
@@ -1051,14 +1148,20 @@
 	if (pattern == null)
 	    pattern = new MobyService ("dummy");
 
-	String result =
-	    (String)doCall ("findService",
-			    new Object[] { 
+	String[] query = new String[] { 
 				"<findService>" +
 				buildQueryObject (pattern, keywords, true, true, false) + 
 				"</findService>"
-			    });
-	return extractServices (result);
+	};
+	if(useCache && cache.containsKey("findService"+query[0]))
+	    return (MobyService[]) cache.get("findService"+query[0]);
+	
+	String result = (String) doCall ("findService", query);
+	MobyService[] services = extractServices (result);
+
+	if(useCache)
+	    cache.put("findService"+query[0], services);
+	return services;
     }
 
     /**************************************************************************
@@ -1106,6 +1209,10 @@
     public String[] getServiceTypeRelationships (String serviceTypeName,
 						 boolean expand)
 	throws MobyException {
+	String cacheKey = "Relationships" + serviceTypeName + ":" + expand;
+	if(useCache && cache.containsKey(cacheKey))
+	    return (String[]) cache.get(cacheKey);
+
 	String result =
 	    (String)doCall ("Relationships",
 			    new Object[] {
@@ -1118,7 +1225,10 @@
 
 	// parse returned XML
 	Vector v = new Vector();
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("Relationship");
 	for (int i = 0; i < list.getLength(); i++) {
 	    Element elem = (Element)list.item (i);
@@ -1131,6 +1241,9 @@
 	}
 	String[] results = new String [v.size()];
 	v.copyInto (results);
+
+	if(useCache)
+	    cache.put(cacheKey, results);
 	return results;
     }
 
@@ -1151,6 +1264,10 @@
      *************************************************************************/
     public Map getDataTypeRelationships (String dataTypeName)
 	throws MobyException {
+	String cacheKey = "getDataTypeRelationships"+dataTypeName;
+	if(useCache && cache.containsKey(cacheKey))
+	    return (Map) cache.get(cacheKey);
+	
 	String result =
 	    (String)doCall ("Relationships",
 			    new Object[] {
@@ -1165,7 +1282,10 @@
 
 	// parse returned XML
 	Map results = new HashMap();
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("Relationship");
 
 	for (int i = 0; i < list.getLength(); i++) {
@@ -1182,6 +1302,9 @@
 	    v.copyInto (names);
 	    results.put (relType, names);
 	}
+
+	if(useCache)
+	    cache.put(cacheKey, results);
 	return results;
     }
 
@@ -1199,6 +1322,10 @@
     public String[] getDataTypeRelationships (String dataTypeName,
 					      String relationshipType)
 	throws MobyException {
+	String cacheKey = "getDataTypeRelationships" + dataTypeName + ":" + relationshipType;
+	if(useCache && cache.containsKey(cacheKey))
+	    return (String[]) cache.get(cacheKey);
+
 	String result =
 	    (String)doCall ("Relationships",
 			    new Object[] {
@@ -1211,7 +1338,10 @@
 
 	// parse returned XML
 	Vector v = new Vector();
-	Document document = parser.parse (new StringReader (result));
+	Document document = null;
+	try{document=docBuilder.parse(new StringBufferInputStream(result));}
+	catch(Exception e){throw new MobyException(e.toString());}
+
 	NodeList list = document.getElementsByTagName ("Relationship");
 
 	// it should always be just one element in this list
@@ -1226,7 +1356,29 @@
 	}
 	String[] results = new String [v.size()];
 	v.copyInto (results);
+
+	if(useCache)
+	    cache.put(cacheKey, results);
 	return results;
     }
 
+    /**
+     * By default, caching is enabled to reduce network traffic and XML parsing.  Setting
+     * this to false will clear the cache, and not cache any further calls unless it is 
+     * set to true again.
+     *
+     * @param shouldCache whether retrieveXXX call results should be cached in case they are called again (i.e. don't requery MobyCentral every time)
+     */
+    public void setCacheMode(boolean shouldCache){
+	useCache = shouldCache;
+	if(!useCache)
+	    cache.clear();
+    }
+
+    /**
+     * @return whether retrieveXXX calls will cache their responses
+     */
+    public boolean getCacheMode(){
+	return useCache;
+    }
 }




More information about the MOBY-guts mailing list