You are viewing a plain text version of this content. The canonical link for it is here.
Posted to axis-cvs@ws.apache.org by sc...@apache.org on 2009/11/20 20:57:29 UTC
svn commit: r882698 - in /webservices/axis2/trunk/java/modules/jaxws:
src/org/apache/axis2/jaxws/context/listener/
test/org/apache/axis2/jaxws/context/listener/
Author: scheu
Date: Fri Nov 20 19:57:29 2009
New Revision: 882698
URL: http://svn.apache.org/viewvc?rev=882698&view=rev
Log:
AXIS2-4550
Contributor:Lori VanGulick and Bill Nagy
Committer: Rich Scheuerle
Fix to ParserInputStream to correct namespaces. Also a validation test.
Modified:
webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ContextListenerUtils.java
webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilder.java
webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilderTests.java
Modified: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ContextListenerUtils.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ContextListenerUtils.java?rev=882698&r1=882697&r2=882698&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ContextListenerUtils.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ContextListenerUtils.java Fri Nov 20 19:57:29 2009
@@ -50,9 +50,9 @@
ProviderOMContextListener.create(mc.getAxisMessageContext().getServiceContext());
}
- public static InputStream createPayloadElement(InputStream payloadContent, OMNamespace ns, String localPart, OMContainer parent){
+ public static InputStream createPayloadElement(InputStream payloadContent, OMNamespace ns, String localPart, OMContainer parent, HashMap<String, String> nsElementDecls, HashMap<String, String> attrElementDecls){
CompositeInputStream inputStream = new CompositeInputStream();
- InputStream startTag = getStartTag(ns, localPart, parent);
+ InputStream startTag = getStartTag(ns, localPart, parent, nsElementDecls, attrElementDecls);
InputStream endTag = getEndTag(ns, localPart);
//Add Element startTag
((CompositeInputStream)inputStream).append(startTag);
@@ -96,7 +96,7 @@
/*
* get startElement using namespace and local part. Add all namespace prefixes from parent elements.
*/
- private static InputStream getStartTag(OMNamespace ns, String localPart, OMContainer parent){
+ private static InputStream getStartTag(OMNamespace ns, String localPart, OMContainer parent, HashMap<String, String> nsElementDecls, HashMap<String, String> attrElementDecls){
if(log.isDebugEnabled()){
log.debug("Start ParsedEntityDataSource.Data.getStartTag()");
}
@@ -104,17 +104,28 @@
StringBuffer startElement = new StringBuffer();
String prefix = (ns!=null)?ns.getPrefix():null;
String uri = (ns!=null)?ns.getNamespaceURI():null;
+
+ HashMap<String, String> nsDecls = new HashMap<String, String>();
+ //Get all of the namespaces associated with Body, envelope, etc
+ getParentnsdeclarations(nsDecls, parent);
+
+ nsDecls.putAll(nsElementDecls);
+
if(prefix!=null && prefix.length()>0){
- startElement.append("<"+prefix+":"+localPart+ " xmlns:"+prefix+"=\""+uri+"\"");
- addParentNs(startElement, parent);
-
+ startElement.append("<"+prefix+":"+localPart+ " ");
+ if (!nsDecls.containsKey(prefix) || !nsDecls.get(prefix).equals(uri)){
+ nsDecls.put(prefix, uri);
+ }
}else{
- startElement.append("<"+localPart+" xmlns=\""+uri+"\"");
- addParentNs(startElement, parent);
+ startElement.append("<"+localPart + " ");
}
+ addParentNs(startElement, parent, nsDecls);
+ addAttrs(startElement, attrElementDecls);
+
if(log.isDebugEnabled()){
- log.debug("StartElement ="+startElement);
+ log.debug("StartElement ="+startElement);
}
+
if(log.isDebugEnabled()){
log.debug("End ParsedEntityDataSource.Data.getStartTag()");
}
@@ -134,8 +145,9 @@
OMNamespace omn = (OMNamespace) ite.next();
String prefix = omn.getPrefix();
String nsUri = omn.getNamespaceURI();
- if (!nsDecls.containsKey(prefix))
+ if (!nsDecls.containsKey(prefix)) {
nsDecls.put(prefix, nsUri);
+ }
}
parent = omElement.getParent();
}
@@ -143,10 +155,7 @@
/*
* add all parent namespace declarations to the element
*/
- private static void addParentNs(StringBuffer startElement, OMContainer parent){
- HashMap<String, String> nsDecls = new HashMap<String, String>();
- //Get all the namespaces associated with Body, envelope etc.
- getParentnsdeclarations(nsDecls, parent);
+ private static void addParentNs(StringBuffer startElement, OMContainer parent, HashMap<String, String> nsDecls){
Iterator<Map.Entry<String, String>> iter = nsDecls.entrySet().iterator();
while (iter.hasNext()) {
Map.Entry<String, String> entry = iter.next();
@@ -162,7 +171,21 @@
startElement.append(uri);
startElement.append("\"");
}
- startElement.append(">");
}
+ private static void addAttrs(StringBuffer startElement, HashMap<String, String> attrDecls)
+ {
+ Iterator<Map.Entry<String, String>> iter = attrDecls.entrySet().iterator();
+ while (iter.hasNext()) {
+ Map.Entry<String, String> entry = iter.next();
+ String compoundName = entry.getKey();
+ String value = entry.getValue();
+ startElement.append(" ");
+ startElement.append(compoundName);
+ startElement.append("=\"");
+ startElement.append(value);
+ startElement.append("\"");
+ }
+ startElement.append(">");
+ }
}
Modified: webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilder.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilder.java?rev=882698&r1=882697&r2=882698&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilder.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/src/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilder.java Fri Nov 20 19:57:29 2009
@@ -19,6 +19,8 @@
package org.apache.axis2.jaxws.context.listener;
import java.io.InputStream;
+import java.util.HashMap;
+import java.util.LinkedList;
import javax.xml.stream.XMLStreamConstants;
import javax.xml.stream.XMLStreamReader;
@@ -87,7 +89,7 @@
//Do not user custom builder if Parser does not have ability to read sub content.
if(!entityReader.isParsedEntityStreamAvailable()){
if (log.isDebugEnabled()) {
- log.debug("Stream not available");
+ log.debug("ParsedEntityStream is not available, defaulting to normal build");
}
return null;
}
@@ -96,10 +98,13 @@
if(parsedStream == null){
//cant read content from EntityReader, returning null.
if (log.isDebugEnabled()) {
- log.debug("No content available");
+ log.debug("Unable to read content from the entity reader, defaulting to normal build");
}
return null;
}
+ HashMap<String, String> nsElementDecls = getElementNamespaceDeclarations(reader);
+ HashMap<String, String> attrElementDecls = getElementAttributeDeclarations(reader);
+
//read the payload. Lets move the parser forward.
if(reader.hasNext()){
reader.next();
@@ -113,7 +118,8 @@
}
}
OMNamespace ns = factory.createOMNamespace(namespace, reader.getPrefix());
- InputStream payload = ContextListenerUtils.createPayloadElement(parsedStream, ns, localPart, parent);
+ InputStream payload = ContextListenerUtils.createPayloadElement(parsedStream, ns, localPart, parent,
+ nsElementDecls, attrElementDecls);
ParserInputStreamDataSource ds = new ParserInputStreamDataSource(payload, encoding);
OMSourcedElement om = null;
@@ -182,6 +188,121 @@
}
}
+ private HashMap<String, String> getElementNamespaceDeclarations(XMLStreamReader reader)
+ {
+ HashMap<String, String> nsElementDecls = new HashMap<String, String>();
+ int count = reader.getNamespaceCount();
+ for (int i = 0; i < count; i++){
+ String prefix = reader.getNamespacePrefix(i);
+ String namespace = reader.getNamespaceURI(i);
+ if (namespace != null && namespace.length() > 0){
+ nsElementDecls.put(prefix == null ? "":prefix, namespace);
+ }
+ }
+ return nsElementDecls;
+ }
+
+ private HashMap<String, String> getElementAttributeDeclarations(XMLStreamReader reader)
+ {
+ HashMap<String, String> attrElementDecls = new HashMap<String, String>();
+ int count = reader.getAttributeCount();
+
+ for (int i = 0; i < count; i++) {
+ String prefix = reader.getAttributePrefix(i);
+ String name = reader.getAttributeLocalName(i);
+ String value = convertEntityReferences(reader.getAttributeValue(i));
+ String compoundName;
+ if (prefix != null && prefix.length() > 0){
+ compoundName = prefix+":"+name;
+ }
+ else {
+ compoundName = name;
+ }
+ attrElementDecls.put(compoundName, value);
+ }
+ return attrElementDecls;
+ }
+
+ protected String convertEntityReferences(String value)
+ {
+ if ((value == null) || (value.length() == 0))
+ return value;
+
+ int valueLen = value.length();
+
+ int[] positionsToChange = null;
+ int numChanged = 0;
+
+ for (int i = 0; i < valueLen; i++) {
+ switch (value.charAt(i)) {
+ case '<':
+ case '>':
+ case '&':
+ case '\"':
+ case '\'':
+ if (positionsToChange == null)
+ {
+ positionsToChange = new int[valueLen];
+ }
+ positionsToChange[numChanged++]=i;
+ break;
+ }
+ }
+
+ if (numChanged == 0) {
+ if(log.isDebugEnabled())
+ {
+ log.debug("No entity references were found in "+value);
+ }
+ return value;
+ }
+ else {
+ if(log.isDebugEnabled())
+ {
+ log.debug("Found "+numChanged+" entity references in "+value);
+ }
+
+ //We'll create the new builder assuming the size of the worst case
+ StringBuilder changedValue = new StringBuilder(valueLen+numChanged*5);
+ int changedPos = 0;
+ for (int i = 0; i < valueLen; i++) {
+ if (i == positionsToChange[changedPos]) {
+ switch (value.charAt(i)) {
+ case '<':
+ changedValue.append("<");
+ changedPos++;
+ break;
+ case '>':
+ changedValue.append(">");
+ changedPos++;
+ break;
+ case '&':
+ changedValue.append("&");
+ changedPos++;
+ break;
+ case '\'':
+ changedValue.append("'");
+ changedPos++;
+ break;
+ case '\"':
+ changedValue.append(""");
+ changedPos++;
+ break;
+ }
+ }
+ else {
+ changedValue.append(value.charAt(i));
+ }
+ }
+
+ if(log.isDebugEnabled())
+ {
+ log.debug("Converted to "+changedValue.toString());
+ }
+
+ return changedValue.toString();
+ }
+ }
/*
* Read content from entityReader.
*/
Modified: webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilderTests.java
URL: http://svn.apache.org/viewvc/webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilderTests.java?rev=882698&r1=882697&r2=882698&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilderTests.java (original)
+++ webservices/axis2/trunk/java/modules/jaxws/test/org/apache/axis2/jaxws/context/listener/ParserInputStreamCustomBuilderTests.java Fri Nov 20 19:57:29 2009
@@ -74,6 +74,35 @@
}
}
+ /**
+ * Tests that ParsedEntityCustomBuilder.convertEntityReferences works as expected.
+ */
+ public void testConvertEntityReferences(){
+ try{
+ ParserInputStreamCustomBuilder customBuilder = new ParserInputStreamCustomBuilder("UTF-8");
+ // test that all expected chars are converted
+ String expectedString1 = "<,>,",',&";
+ String convertedString = customBuilder.convertEntityReferences("<,>,\",',&");
+ assertTrue("Special chars didn't get converted! " +
+ "Expected: \""+expectedString1+"\" but received: \""+convertedString+"\"",
+ convertedString.equals(expectedString1));
+ // test that a string with no special chars is unchanged
+ String simpleString = "This is a simple string";
+ convertedString = customBuilder.convertEntityReferences(simpleString);
+ assertTrue("Simple string was changed unexpectedly. " +
+ "Expected: \""+simpleString+"\" but received: \""+convertedString+"\"",
+ convertedString.equals(simpleString));
+
+ // test that the mockenvelope gets converted correctly
+ String expectedString2 = "<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"><soapenv:Header/><soapenv:Body><invokeOp>Hello Provider OM</invokeOp></soapenv:Body></soapenv:Envelope>";
+ convertedString = customBuilder.convertEntityReferences(mockenvelope);
+ assertTrue("mockenvelope was not converted as expected. " +
+ "Expected: \""+expectedString2+"\" but received: \""+convertedString+"\"",
+ convertedString.equals(expectedString2));
+ }catch(Exception e){
+ fail(e.getMessage());
+ }
+ }
private SOAPEnvelope getMockEnvelope() throws Exception{
SOAPEnvelope env = (SOAPEnvelope)getOMBuilder().getDocumentElement();
return env;