001 //$HeadURL: svn+ssh://rbezema@svn.wald.intevation.org/deegree/base/tags/2.1/src/org/deegree/enterprise/control/RPCFactory.java $ 002 package org.deegree.enterprise.control; 003 004 import java.io.Reader; 005 import java.util.Date; 006 007 import org.deegree.framework.log.ILogger; 008 import org.deegree.framework.log.LoggerFactory; 009 import org.deegree.framework.util.TimeTools; 010 import org.deegree.framework.xml.ElementList; 011 import org.deegree.framework.xml.NamespaceContext; 012 import org.deegree.framework.xml.XMLTools; 013 import org.deegree.ogcbase.CommonNamespaces; 014 import org.w3c.dom.Document; 015 import org.w3c.dom.Element; 016 017 /** 018 * Factory class for creating RPC methodCall and methodResponse objects from their XML 019 * representation 020 * 021 * @author <a href="mailto:poth@lat-lon.de">Andreas Poth</a> 022 * @version $Revision: 6259 $ $Date: 2007-03-20 10:15:15 +0100 (Di, 20 Mär 2007) $ 023 */ 024 public class RPCFactory { 025 026 private static final ILogger LOG = LoggerFactory.getLogger( RPCFactory.class ); 027 028 private static NamespaceContext nsContext = CommonNamespaces.getNamespaceContext(); 029 030 /** 031 * creates an instance of <tt>RPCMethodCall</tt> from an XML document that can be accessed 032 * through the passed <tt>Reader</tt> 033 * 034 * @param reader 035 * reader to access an XML document 036 * @return an RPCMethodCall 037 */ 038 public static RPCMethodCall createRPCMethodCall( Reader reader ) throws RPCException { 039 040 Document doc = null; 041 try { 042 doc = XMLTools.parse( reader ); 043 } catch (Exception e) { 044 LOG.logError( e.getMessage(), e ); 045 throw new RPCException( e.toString() ); 046 } 047 048 return createRPCMethodCall( doc ); 049 } 050 051 /** 052 * creates an instance of <tt>RPCMethodCall</tt> from the XML document passed 053 * 054 * @param doc 055 * XML document containing a RPC method call 056 * @return an RPCMethodCall 057 */ 058 public static RPCMethodCall createRPCMethodCall( Document doc ) throws RPCException { 059 060 RPCMethodCall mc = null; 061 try { 062 Element root = doc.getDocumentElement(); 063 // get methode name - mandatory 064 String methodName = XMLTools.getRequiredStringValue( "methodName", null, root ); 065 066 Element params = XMLTools.getChildElement( "params", null, root ); 067 068 RPCParameter[] parameters = null; 069 if ( params != null ) { 070 ElementList el = XMLTools.getChildElements( params ); 071 if ( el != null ) { 072 parameters = new RPCParameter[el.getLength()]; 073 for (int i = 0; i < el.getLength(); i++) { 074 parameters[i] = createRPCParam( el.item( i ) ); 075 } 076 } 077 } else { 078 parameters = new RPCParameter[0]; 079 } 080 081 mc = new RPCMethodCall( methodName, parameters ); 082 } catch (Exception e) { 083 LOG.logError( e.getMessage(), e ); 084 throw new RPCException( e.toString() ); 085 } 086 087 return mc; 088 } 089 090 /** 091 * creates an instance of <tt>RPCMethodResponse</tt> from an XML document that can be accessed 092 * through the passed <tt>Reader</tt> 093 * 094 * @param reader 095 * reader to access an XML document 096 * @return created <tt>RPCMethodResponse</tt> 097 */ 098 public static RPCMethodResponse createRPCMethodResponse( Reader reader ) throws RPCException { 099 100 Document doc = null; 101 try { 102 doc = XMLTools.parse( reader ); 103 } catch (Exception e) { 104 LOG.logError( e.getMessage(), e ); 105 throw new RPCException( e.toString() ); 106 } 107 108 return createRPCMethodResponse( doc ); 109 } 110 111 /** 112 * creates an instance of <tt>RPCMethodResponse</tt> from the XML document passed 113 * 114 * @param doc 115 * XML document containing a RPC method call 116 * @return created <tt>RPCMethodResponse</tt> 117 */ 118 public static RPCMethodResponse createRPCMethodResponse( Document doc ) throws RPCException { 119 120 RPCMethodResponse mc = null; 121 try { 122 Element root = doc.getDocumentElement(); 123 124 Element params = XMLTools.getChildElement( "params", null, root ); 125 126 if ( params != null ) { 127 ElementList el = XMLTools.getChildElements( params ); 128 RPCParameter[] parameters = null; 129 if ( el != null ) { 130 parameters = new RPCParameter[el.getLength()]; 131 for (int i = 0; i < el.getLength(); i++) { 132 parameters[i] = createRPCParam( el.item( i ) ); 133 } 134 } 135 mc = new RPCMethodResponse( parameters ); 136 } else { 137 // a fault is contained instead of the expected result 138 Element fault = XMLTools.getChildElement( "fault", null, root ); 139 RPCFault rpcFault = createRPCFault( fault ); 140 mc = new RPCMethodResponse( rpcFault ); 141 } 142 143 } catch (Exception e) { 144 LOG.logError( e.getMessage(), e ); 145 throw new RPCException( e.toString() ); 146 } 147 148 return mc; 149 } 150 151 /** 152 * @param par 153 * @return 154 * @throws RPCException 155 */ 156 public static RPCMethodResponse createRPCMethodResponse( RPCParameter[] par ) { 157 RPCMethodResponse mc = null; 158 if ( par != null ) { 159 RPCParameter[] params = par; 160 mc = new RPCMethodResponse( params ); 161 } else { 162 LOG.logError( "Fehler createRPCMEthodResponse in RPSFactory" ); 163 } 164 return mc; 165 } 166 167 /** 168 * creates a <tt>RPCParameter</tt> from its XML representation 169 * 170 * @param param 171 * element containing a RPC param 172 * @return created <tt>RPCParameter</tt> 173 */ 174 private static RPCParameter createRPCParam( Element param ) throws RPCException { 175 176 RPCParameter parameter = null; 177 try { 178 Element value = XMLTools.getChildElement( "value", null, param ); 179 Element child = XMLTools.getFirstChildElement( value ); 180 Object o = null; 181 Class cl = null; 182 if ( child.getNodeName().equals( "struct" ) ) { 183 o = createRPCStruct( child ); 184 cl = RPCStruct.class; 185 } else if ( child.getNodeName().equals( "string" ) ) { 186 o = XMLTools.getRequiredStringValue( "string", null, value ); 187 cl = String.class; 188 } else if ( child.getNodeName().equals( "int" ) ) { 189 double d = XMLTools.getRequiredNodeAsDouble( value, "./int", nsContext ); 190 o = new Integer( (int) d ); 191 cl = Integer.class; 192 } else if ( child.getNodeName().equals( "i4" ) ) { 193 double d = XMLTools.getRequiredNodeAsDouble( value, "./i4", nsContext ); 194 o = new Integer( (int) d ); 195 cl = Integer.class; 196 } else if ( child.getNodeName().equals( "double" ) ) { 197 double d = XMLTools.getRequiredNodeAsDouble( value, "./double", nsContext ); 198 o = new Double( d ); 199 cl = Double.class; 200 } else if ( child.getNodeName().equals( "boolean" ) ) { 201 o = Boolean.valueOf( child.getFirstChild().getNodeValue().equals( "1" ) ); 202 cl = Boolean.class; 203 } else if ( child.getNodeName().equals( "dateTime.iso8601" ) ) { 204 String s = XMLTools.getRequiredStringValue( "dateTime.iso8601", null, value ); 205 o = TimeTools.createCalendar( s ).getTime(); 206 cl = Date.class; 207 } else if ( child.getNodeName().equals( "base64" ) ) { 208 } else if ( child.getNodeName().equals( "array" ) ) { 209 o = createArray( child ); 210 cl = RPCParameter[].class; 211 } 212 parameter = new RPCParameter( cl, o ); 213 } catch (Exception e) { 214 LOG.logError( e.getMessage(), e ); 215 throw new RPCException( e.toString() ); 216 } 217 218 return parameter; 219 } 220 221 /** 222 * creates a RPC struture object from the passed <tt>Element</tt> 223 * 224 * @param struct 225 * element containing a RPC struct 226 * @return created <tt>RPCStruct</tt> 227 */ 228 private static RPCStruct createRPCStruct( Element struct ) throws RPCException { 229 230 RPCStruct structure = null; 231 try { 232 ElementList el = XMLTools.getChildElements( struct ); 233 RPCMember[] members = null; 234 if ( el != null ) { 235 members = new RPCMember[el.getLength()]; 236 for (int i = 0; i < el.getLength(); i++) { 237 members[i] = createRPCMember( el.item( i ) ); 238 } 239 } 240 structure = new RPCStruct( members ); 241 } catch (Exception e) { 242 LOG.logError( e.getMessage(), e ); 243 throw new RPCException( e.toString() ); 244 } 245 246 return structure; 247 } 248 249 /** 250 * creates a RPC struture member object from the passed <tt>Element</tt> 251 * 252 * @param member 253 * element containing a RPC member 254 * @return created <tt>RPCMember</tt> 255 */ 256 private static RPCMember createRPCMember( Element member ) throws RPCException { 257 258 RPCMember mem = null; 259 try { 260 String name = XMLTools.getRequiredStringValue( "name", null, member ); 261 Element value = XMLTools.getChildElement( "value", null, member ); 262 Element child = XMLTools.getFirstChildElement( value ); 263 Object o = null; 264 Class cl = null; 265 if ( child.getNodeName().equals( "struct" ) ) { 266 o = createRPCStruct( child ); 267 cl = RPCStruct.class; 268 } else if ( child.getNodeName().equals( "string" ) ) { 269 o = XMLTools.getRequiredStringValue( "string", null, value ); 270 cl = String.class; 271 } else if ( child.getNodeName().equals( "int" ) ) { 272 double d = XMLTools.getRequiredNodeAsDouble( value, "./int", nsContext ); 273 o = new Integer( (int) d ); 274 cl = Integer.class; 275 } else if ( child.getNodeName().equals( "i4" ) ) { 276 double d = XMLTools.getRequiredNodeAsDouble( value, "./i4", nsContext ); 277 o = new Integer( (int) d ); 278 cl = Integer.class; 279 } else if ( child.getNodeName().equals( "double" ) ) { 280 double d = XMLTools.getRequiredNodeAsDouble( value, "./double", nsContext ); 281 o = new Double( d ); 282 cl = Double.class; 283 } else if ( child.getNodeName().equals( "boolean" ) ) { 284 o = Boolean.valueOf( child.getFirstChild().getNodeValue().equals( "1" ) ); 285 cl = Boolean.class; 286 } else if ( child.getNodeName().equals( "dateTime.iso8601" ) ) { 287 String s = XMLTools.getRequiredStringValue( "dateTime.iso8601", null, value ); 288 o = TimeTools.createCalendar( s ).getTime(); 289 cl = Date.class; 290 } else if ( child.getNodeName().equals( "base64" ) ) { 291 } else if ( child.getNodeName().equals( "array" ) ) { 292 o = createArray( child ); 293 cl = RPCParameter[].class; 294 } 295 mem = new RPCMember( cl, o, name ); 296 } catch (Exception e) { 297 LOG.logError( e.getMessage(), e ); 298 throw new RPCException( e.toString() ); 299 } 300 301 return mem; 302 } 303 304 /** 305 * creates an <tt>ArrayList</tt> object from the passed <tt>Element</tt> 306 * 307 * @param array 308 * @return created <tt>ArrayList</tt> 309 */ 310 private static RPCParameter[] createArray( Element array ) throws RPCException { 311 312 RPCParameter[] param = null; 313 try { 314 Element data = XMLTools.getChildElement( "data", null, array ); 315 ElementList el = XMLTools.getChildElements( data ); 316 if ( el != null ) { 317 param = new RPCParameter[el.getLength()]; 318 for (int i = 0; i < el.getLength(); i++) { 319 Element child = XMLTools.getFirstChildElement( el.item( i ) ); 320 Object o = null; 321 Class cl = null; 322 if ( child.getNodeName().equals( "struct" ) ) { 323 o = createRPCStruct( child ); 324 cl = RPCStruct.class; 325 } else if ( child.getNodeName().equals( "string" ) ) { 326 o = XMLTools.getRequiredStringValue( "string", null, el.item( i ) ); 327 cl = String.class; 328 } else if ( child.getNodeName().equals( "int" ) ) { 329 double d = XMLTools.getRequiredNodeAsDouble( el.item( i ), "./int", nsContext ); 330 o = new Integer( (int) d ); 331 cl = Integer.class; 332 } else if ( child.getNodeName().equals( "i4" ) ) { 333 double d = XMLTools.getRequiredNodeAsDouble( el.item( i ), "./i4", nsContext ); 334 o = new Integer( (int) d ); 335 cl = Integer.class; 336 } else if ( child.getNodeName().equals( "double" ) ) { 337 double d = XMLTools.getRequiredNodeAsDouble( el.item( i ), "./double", 338 nsContext ); 339 o = new Double( d ); 340 cl = Double.class; 341 } else if ( child.getNodeName().equals( "boolean" ) ) { 342 o = Boolean.valueOf( child.getFirstChild().getNodeValue().equals( "1" ) ); 343 cl = Boolean.class; 344 } else if ( child.getNodeName().equals( "dateTime.iso8601" ) ) { 345 String s = XMLTools.getRequiredStringValue( "dateTime.iso8601", null, el 346 .item( i ) ); 347 o = TimeTools.createCalendar( s ).getTime(); 348 cl = Date.class; 349 } else if ( child.getNodeName().equals( "base64" ) ) { 350 } else if ( child.getNodeName().equals( "array" ) ) { 351 o = createArray( child ); 352 cl = RPCParameter[].class; 353 } 354 param[i] = new RPCParameter( cl, o ); 355 } 356 } 357 } catch (Exception e) { 358 LOG.logError( e.getMessage(), e ); 359 throw new RPCException( e.toString() ); 360 } 361 362 return param; 363 } 364 365 /** 366 * creates an <tt>RPCFault</tt> object from the passed <tt>Element</tt> 367 * 368 * @param fault 369 * fault element 370 * @return created <tt>RPCFault</tt> 371 */ 372 private static RPCFault createRPCFault( Element fault ) throws RPCException { 373 374 RPCFault rpcFault = null; 375 try { 376 Element value = XMLTools.getChildElement( "value", null, fault ); 377 Element child = XMLTools.getFirstChildElement( value ); 378 RPCStruct struct = createRPCStruct( child ); 379 String s1 = null; 380 String s2 = null; 381 Object o = struct.getMember( "faultCode" ).getValue(); 382 if ( o != null ) { 383 s1 = o.toString(); 384 } 385 o = struct.getMember( "faultString" ).getValue(); 386 if ( o != null ) { 387 s2 = o.toString(); 388 } 389 rpcFault = new RPCFault( s1, s2 ); 390 } catch (Exception e) { 391 LOG.logError( e.getMessage(), e ); 392 throw new RPCException( e.toString() ); 393 } 394 395 return rpcFault; 396 } 397 398 } 399 /* ******************************************************************** 400 Changes to this class. What the people have been up to: 401 $Log$ 402 Revision 1.13 2006/12/06 22:09:27 poth 403 *** empty log message *** 404 405 Revision 1.12 2006/10/05 09:33:09 mays 406 remove a bug: now every RPCMethodCall contains RPCParameters, even though they might be empty. 407 408 Revision 1.11 2006/07/29 08:49:25 poth 409 references to deprecated classes removed 410 411 Revision 1.10 2006/07/12 14:46:17 poth 412 comment footer added 413 414 ********************************************************************** */