[MOBY-guts] biomoby commit
Paul Gordon
gordonp at dev.open-bio.org
Mon Aug 17 21:17:13 UTC 2009
gordonp
Mon Aug 17 17:17:13 EDT 2009
Update of /home/repository/moby/moby-live/Java/src/main/ca/ucalgary/services/util
In directory dev.open-bio.org:/tmp/cvs-serv25823/src/main/ca/ucalgary/services/util
Modified Files:
PBERecorder.java
Log Message:
Refactoring to provide generic DataRecorder callbacks during SoapServlet execution, was PBERecorder hardcoded before
moby-live/Java/src/main/ca/ucalgary/services/util PBERecorder.java,1.1,1.2
===================================================================
RCS file: /home/repository/moby/moby-live/Java/src/main/ca/ucalgary/services/util/PBERecorder.java,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- /home/repository/moby/moby-live/Java/src/main/ca/ucalgary/services/util/PBERecorder.java 2009/06/09 19:37:17 1.1
+++ /home/repository/moby/moby-live/Java/src/main/ca/ucalgary/services/util/PBERecorder.java 2009/08/17 21:17:13 1.2
@@ -33,7 +33,7 @@
/**
* This class controls the interaction between the web browser and Seahawk via the pasting actions.
*/
-public class PBERecorder{
+public class PBERecorder implements DataRecorder{
private Map<String,MobyContentGUI> sessionId2gui; // link the http session with the GUI
private Map<String,Node> sessionId2dom; // link the http session with the results of the WSDL service
private Map<String,String> sessionId2wsdlSpec; // link the http session with the wsdl service/port/op def
@@ -218,6 +218,107 @@
transformer = t;
}
+ public boolean shouldIntercept(HttpServletRequest request){
+ return request.getParameter(PBERecorder.RETURN_XPATH_PARAM) != null ||
+ request.getParameter(PBERecorder.AUTOCOMPLETE_PARAM) != null ||
+ request.getParameter(PBERecorder.RESOURCE_FILE_PARAM) != null ||
+ request.getParameter(PBERecorder.RAW_XPATH_PARAM) != null;
+ // TODO: deal with wsdl-less POST, which need writeWrapperForm call
+ }
+
+ public void interceptRequest(HttpServletRequest request,
+ HttpServletResponse response){
+
+ String xpath = request.getParameter(PBERecorder.RETURN_XPATH_PARAM);
+ String autocompleteRequest = request.getParameter(PBERecorder.AUTOCOMPLETE_PARAM);
+ String resource = request.getParameter(PBERecorder.RESOURCE_FILE_PARAM);
+ String raw = request.getParameter(PBERecorder.RAW_XPATH_PARAM);
+
+ if(raw != null && raw.trim().length() != 0){
+ getRawXml(request, response);
+ }
+ else if(resource != null && resource.trim().length() != 0){
+ getResource(request, response);
+ }
+ //AJAX call for autocomplete
+ else if(autocompleteRequest != null && autocompleteRequest.trim().length() != 0){
+ writeAutocompleteReply(request, response, autocompleteRequest);
+ }
+ else if(xpath != null && xpath.trim().length() != 0){
+ writeWrapperForm(request, response);
+ }
+ // TODO: deal with wsdl-less POST, which need writeWrapperForm call
+ else{
+ // Shouldn't get here unless shouldIntercept() was not checked before calling this method,
+ // or the logic of shouldIntercept() is inconsistent with that of this method.
+
+ }
+ }
+
+ private void writeAutocompleteReply(HttpServletRequest request,
+ HttpServletResponse response,
+ String seed){
+ java.io.OutputStream out = null;
+ response.setContentType("text/plain");
+ try{
+ out = response.getOutputStream();
+ }
+ catch(java.io.IOException ioe){
+ logger.log(Level.SEVERE, "While getting servlet output stream (for HTML form response to client)", ioe);
+ return;
+ }
+
+ String answer = "";
+ try{
+ answer = autocomplete(request, seed);
+ } catch(Exception e){
+ //todo: make pretty, more verbose, etc., fit on one line for AJAX client
+ answer = e.toString();
+ }
+
+ try{
+ out.write(answer.getBytes());
+ }
+ catch(java.io.IOException ioe){
+ logger.log(Level.SEVERE, "While printing HTML form to servlet output stream", ioe);
+ return;
+ }
+ }
+
+ // This is called when the user has picked a part of the service response to return in the MOBY service being created
+ private void writeWrapperForm(HttpServletRequest request,
+ HttpServletResponse response){
+ java.io.OutputStream out = null;
+ response.setContentType("text/html");
+ try{
+ out = response.getOutputStream();
+ }
+ catch(java.io.IOException ioe){
+ logger.log(Level.SEVERE, "While getting servlet output stream (for HTML form response to client)", ioe);
+ return;
+ }
+
+ String answer = "";
+ try{
+ out.write(writeWrapperForm(request).getBytes());
+ return;
+ } catch(Exception e){
+ answer = "Error in PBE system:\n" + e.toString()+"\n";
+ for(StackTraceElement ste: e.getStackTrace()){
+ answer += ste.toString()+"\n";
+ }
+ }
+
+ try{
+ out.write("<html><head><title>Service Definition Error</title></head>\n".getBytes());
+ out.write(("<body>"+answer+"</body></html>").getBytes());
+ }
+ catch(java.io.IOException ioe){
+ logger.log(Level.SEVERE, "While printing HTML form to servlet output stream", ioe);
+ return;
+ }
+ }
+
/**
* Called when data in a field is being updated via a paste event.
*/
@@ -227,7 +328,7 @@
MobyContentGUI gui = sessionId2gui.get(session.getId());
// datatype<->event unification for Seahawk->browser drag 'n' drop
- String action = request.getParameter("seahawkAction");
+ String action = request.getParameter(DataRecorder.PASSTHROUGH_ACTION);
if(action.equals("pasteEvent")){
dataPasted(request);
}
@@ -252,7 +353,8 @@
try{
response.getOutputStream().write(statusMessage.getBytes());
} catch(Exception e){
- logger.log(Level.SEVERE, "Cannot write the response to a seahawkAction request", e);
+ logger.log(Level.SEVERE, "Cannot write the response to a " +
+ DataRecorder.PASSTHROUGH_ACTION + " request", e);
}
}
@@ -391,7 +493,7 @@
"the service (probably an internal error): " + e);
}
- System.err.println(stringResult.toString());
+ //System.err.println(stringResult.toString());
// Replace any enclosing tag with links that indicate the tag contents are of
// interest based on tag or attribute name, or attribute value
String markup = stringResult.toString().replaceAll("</", "</");
@@ -400,8 +502,9 @@
"=\"(.*?)#(.*?)\"", Pattern.MULTILINE | Pattern.DOTALL);
Pattern attributePattern = Pattern.compile("(\\S+)=\"([^\"]*)\"", Pattern.MULTILINE | Pattern.DOTALL);
-
+ StringBuilder newMarkup = new StringBuilder();
Matcher elementMatcher = elementPattern.matcher(markup);
+ int markupLengthRemoved = 0;
while(elementMatcher.find()){
// These data structure keeps track changes we need to make to elementText
Vector<int[]> ranges = new Vector<int[]>();
@@ -460,7 +563,13 @@
}
// literal string replacement
String linkedElement = applyEdits(elementText, ranges, replacements);
- markup = markup.replace(elementText, linkedElement);
+ newMarkup.append(markup.substring(markupLengthRemoved, elementMatcher.start()));
+ newMarkup.append(linkedElement);
+ //markup = elementMatcher.end() >= markup.length() ? "" :
+ // markup.substring(elementMatcher.end()-markupLengthRemoved);
+ markupLengthRemoved = elementMatcher.end();
+ //elementMatcher = elementPattern.matcher(markup);
+ //markup = markup.replace(elementText, linkedElement);
}
}
@@ -470,7 +579,7 @@
"Below, click the most indented <b>element name</b>, <b>attribute name</b>, or <b>specific attribute value</b> "+
"that you expect to be <b>always present</b> in a <b>successful</b> execution. You will then be taken to "+
"a form asking you about how you want this data returned using the Moby data types." +
- "</td></tr></table>"+"<pre>"+markup+"</pre>";
+ "</td></tr></table>"+"<pre>"+newMarkup+"</pre>";
}
private void addEdit(Vector<int[]> exciseRanges, int[] newRange,
@@ -595,12 +704,16 @@
// give surrounding words (numChars worth total) around targetWord in text
private String getContext(String text, String targetWord, int numChars){
+ return getContext(text, targetWord, numChars, true); // true = use tool tips for ellipsis expansion
+ }
+
+ private String getContext(String text, String targetWord, int numChars, boolean useToolTip){
text = text.replaceAll("\n",""); //new-line obvious messes up ajax one-line per response format
if(text.length() < numChars){
return text; //can fit the whole thing
}
-
+
int start = 0;
if(targetWord.length() > 0){
start = text.toLowerCase().indexOf(targetWord)-numChars/2;
@@ -628,8 +741,8 @@
}
}
- String prefix = start == 0 ? "" : "<acronym title=\""+text.substring(0,start)+"\">...</acronym>";
- String suffix = end == text.length() ? "" : "<acronym title=\""+text.substring(end)+"\">...</acronym>";
+ String prefix = start == 0 ? "" : (useToolTip ? "<acronym title=\""+text.substring(0,start)+"\">...</acronym>" : "...");
+ String suffix = end == text.length() ? "" : (useToolTip ? "<acronym title=\""+text.substring(end)+"\">...</acronym>" : "...");
return prefix+text.substring(start, end)+suffix;
}
@@ -1228,15 +1341,30 @@
if(dataType.length() != 0){
MobyDataType dt = MobyDataType.getDataType(dataType, SeahawkOptions.getRegistry());
- // xpaths should be called foo-memberName foo-otherMemberName etc.
- for(MobyRelationship relationship: dt.getAllChildren()){
- String memberName = relationship.getName();
- String memberXPath = request.getParameter(VALUE_XPATH_PARAM+memberName);
+ String dataTypeName = dt.getName();
+ if(dataTypeName.equals(MobyTags.MOBYSTRING) ||
+ dataTypeName.equals(MobyTags.MOBYFLOAT) ||
+ dataTypeName.equals(MobyTags.MOBYINTEGER) ||
+ dataTypeName.equals(MobyTags.MOBYBOOLEAN) ||
+ dataTypeName.equals(MobyTags.MOBYDATETIME)){ // is it a primitive? no suffix in that case...
+ String memberXPath = request.getParameter(VALUE_XPATH_PARAM);
if(memberXPath == null){
- throw new Exception("Cannot find XPath param ("+VALUE_XPATH_PARAM+memberName+
- ") for '"+dataType + "' data type's member " + memberName);
+ throw new Exception("Cannot find XPath param ("+VALUE_XPATH_PARAM+
+ ") for the '"+dataTypeName + "' primitive value ");
+ }
+ memberMap.put(MobyComplexBuilder.PRIMITIVE_VALUE_SENTINEL, fixXPath(memberXPath, request)); // "" is special member name key for primitives
+ }
+ else{
+ // xpaths should be called foo-memberName foo-otherMemberName etc.
+ for(MobyRelationship relationship: dt.getAllChildren()){
+ String memberName = relationship.getName();
+ String memberXPath = request.getParameter(VALUE_XPATH_PARAM+memberName);
+ if(memberXPath == null){
+ throw new Exception("Cannot find XPath param ("+VALUE_XPATH_PARAM+memberName+
+ ") for '"+dataType + "' data type's member " + memberName);
+ }
+ memberMap.put(memberName, fixXPath(memberXPath, request));
}
- memberMap.put(memberName, memberXPath);
}
}
else{
@@ -1496,12 +1624,12 @@
ex.printStackTrace();
}
}
- NodeList nl = e.getElementsByTagName("*");
- for(int i = 0; i < nl.getLength(); i++){
- Element child = (Element) nl.item(i);
- System.err.println("Element " + child.getNodeName() + " ns " + child.getNamespaceURI() +
- " for prefix " + child.getPrefix());
- }
+ // NodeList nl = e.getElementsByTagName("*");
+// for(int i = 0; i < nl.getLength(); i++){
+// Element child = (Element) nl.item(i);
+// //System.err.println("Element " + child.getNodeName() + " ns " + child.getNamespaceURI() +
+// // " for prefix " + child.getPrefix());
+// }
}
// The namespace prefixes used in the selection xpath will use the following node's prefix:ns mappings
@@ -1528,7 +1656,7 @@
xPathResults = (NodeList) xPathObj.evaluate(fixXPath(xPath, request), domNode, XPathConstants.NODESET);
numResults = xPathResults.getLength();
if(numResults == 0){
- result.append("[<font color=\"red\" style=\"bold\">the selection XPath does " +
+ result.append("[<font color=\"red\" style=\"bold\">the selection XPath ("+fixXPath(xPath, request)+") does " +
"not select any data, please modify</font>"+
"]\n"); // <input type=\"submit\" value=\"Reselect\"/><br/>\n");
}
@@ -1544,7 +1672,8 @@
}
//todo output xsd type: xPathResults.item(0).getNamespaceURI(), xPathResults.item(0).getLocalName;
- Vector<String> valXPathSuggestions = RuleCreator.suggestValueXPathsFromSelectionXPath(xPath, xPathResults.item(0));
+
+ Vector<String> valXPathSuggestions = (numResults == 0 ? new Vector<String>() : RuleCreator.suggestValueXPathsFromSelectionXPath(xPath, xPathResults.item(0)));
String valueXPath = getParam(request, VALUE_XPATH_PARAM);
String selectOptions = null;
boolean suggestable = false;
@@ -1567,9 +1696,14 @@
// If no value already, let's suggest the first one
if(valueXPath.length() == 0){
- valueXPath = valXPathSuggestions.elementAt(0).replaceAll("(.*) -- .*", "$1");
- valXPathSuggestions.removeElementAt(0);
- suggestable = true;
+ if(valXPathSuggestions.size() == 0){
+ valueXPath = "";
+ }
+ else{
+ valueXPath = valXPathSuggestions.elementAt(0).replaceAll("(.*) -- .*", "$1");
+ valXPathSuggestions.removeElementAt(0);
+ suggestable = true;
+ }
}
}
// a custom XPath
@@ -1799,7 +1933,8 @@
// we do this here rather than on the referring page because the regex code
// used to generate the referring page links can't make the prefixes easily
//return xPath.replaceAll("/([a-zA-Z_0-9\\-]+)(?=/|$|\\[)", "/"+XPATH_DEFAULT_NS_PREFIX+":$1");
- return xPath.replaceAll("/([a-zA-Z_0-9\\-]+)(?=/|$)", "/*[local-name() = '$1']");
+ return xPath.replaceAll("/([a-zA-Z_0-9\\-]+)(?=/|$)", "/*[local-name() = '$1']")
+ .replaceAll("/([a-zA-Z_0-9\\-]+)\\[", "/*[local-name() = '$1' and ");
}
else{
return xPath; //rpc nodes usually have no namespace
@@ -2179,13 +2314,13 @@
if(i == 0){
MobyNamespace ns = obj.getPrimaryNamespace();
if(ns != null){
- result.append("<option title=\""+getContext(ns.getDescription(), "", 50)+
+ result.append("<option title=\""+getContext(ns.getDescription(), "", 50, false)+
(partValue.equals(MobyTags.MOBYOBJECT+":"+ns.getName()) ? "\" selected=\"selected" : "") +
"\">"+MobyTags.MOBYOBJECT+":"+ns.getName()+"</option>");
}
}
else{
- result.append("<option title=\""+getContext(lineage[i].getDescription(),"", 50)+
+ result.append("<option title=\""+getContext(lineage[i].getDescription(),"", 50, false)+
(partValue.equals(lineage[i].getName()) ? "\" selected=\"selected" : "") +
"\">"+lineage[i].getName()+"</option>");
}
More information about the MOBY-guts
mailing list