001 //$HeadURL: svn+ssh://rbezema@svn.wald.intevation.org/deegree/base/branches/2.2_testing/src/org/deegree/enterprise/control/RPCFactory.java $
002 /*---------------- FILE HEADER ------------------------------------------
003
004 This file is part of deegree.
005 Copyright (C) 2001-2008 by:
006 EXSE, Department of Geography, University of Bonn
007 http://www.giub.uni-bonn.de/deegree/
008 lat/lon GmbH
009 http://www.lat-lon.de
010
011 This library is free software; you can redistribute it and/or
012 modify it under the terms of the GNU Lesser General Public
013 License as published by the Free Software Foundation; either
014 version 2.1 of the License, or (at your option) any later version.
015
016 This library is distributed in the hope that it will be useful,
017 but WITHOUT ANY WARRANTY; without even the implied warranty of
018 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
019 Lesser General Public License for more details.
020
021 You should have received a copy of the GNU Lesser General Public
022 License along with this library; if not, write to the Free Software
023 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
024
025 Contact:
026
027 Andreas Poth
028 lat/lon GmbH
029 Aennchenstr. 19
030 53115 Bonn
031 Germany
032 E-Mail: poth@lat-lon.de
033
034 Prof. Dr. Klaus Greve
035 Department of Geography
036 University of Bonn
037 Meckenheimer Allee 166
038 53115 Bonn
039 Germany
040 E-Mail: greve@giub.uni-bonn.de
041
042
043 ---------------------------------------------------------------------------*/
044 package org.deegree.enterprise.control;
045
046 import java.io.Reader;
047 import java.util.Date;
048
049 import org.deegree.framework.log.ILogger;
050 import org.deegree.framework.log.LoggerFactory;
051 import org.deegree.framework.util.TimeTools;
052 import org.deegree.framework.xml.ElementList;
053 import org.deegree.framework.xml.NamespaceContext;
054 import org.deegree.framework.xml.XMLTools;
055 import org.deegree.ogcbase.CommonNamespaces;
056 import org.w3c.dom.Document;
057 import org.w3c.dom.Element;
058
059 /**
060 * Factory class for creating RPC methodCall and methodResponse objects from their XML
061 * representation
062 *
063 * @author <a href="mailto:poth@lat-lon.de">Andreas Poth</a>
064 * @version $Revision: 9338 $ $Date: 2007-12-27 13:31:31 +0100 (Do, 27 Dez 2007) $
065 */
066 public class RPCFactory {
067
068 private static final ILogger LOG = LoggerFactory.getLogger( RPCFactory.class );
069
070 private static NamespaceContext nsContext = CommonNamespaces.getNamespaceContext();
071
072 /**
073 * creates an instance of <tt>RPCMethodCall</tt> from an XML document that can be accessed
074 * through the passed <tt>Reader</tt>
075 *
076 * @param reader
077 * reader to access an XML document
078 * @return an RPCMethodCall
079 */
080 public static RPCMethodCall createRPCMethodCall( Reader reader ) throws RPCException {
081
082 Document doc = null;
083 try {
084 doc = XMLTools.parse( reader );
085 } catch (Exception e) {
086 LOG.logError( e.getMessage(), e );
087 throw new RPCException( e.toString() );
088 }
089
090 return createRPCMethodCall( doc );
091 }
092
093 /**
094 * creates an instance of <tt>RPCMethodCall</tt> from the XML document passed
095 *
096 * @param doc
097 * XML document containing a RPC method call
098 * @return an RPCMethodCall
099 */
100 public static RPCMethodCall createRPCMethodCall( Document doc ) throws RPCException {
101
102 RPCMethodCall mc = null;
103 try {
104 Element root = doc.getDocumentElement();
105 // get methode name - mandatory
106 String methodName = XMLTools.getRequiredStringValue( "methodName", null, root );
107
108 Element params = XMLTools.getChildElement( "params", null, root );
109
110 RPCParameter[] parameters = null;
111 if ( params != null ) {
112 ElementList el = XMLTools.getChildElements( params );
113 if ( el != null ) {
114 parameters = new RPCParameter[el.getLength()];
115 for (int i = 0; i < el.getLength(); i++) {
116 parameters[i] = createRPCParam( el.item( i ) );
117 }
118 }
119 } else {
120 parameters = new RPCParameter[0];
121 }
122
123 mc = new RPCMethodCall( methodName, parameters );
124 } catch (Exception e) {
125 LOG.logError( e.getMessage(), e );
126 throw new RPCException( e.toString() );
127 }
128
129 return mc;
130 }
131
132 /**
133 * creates an instance of <tt>RPCMethodResponse</tt> from an XML document that can be accessed
134 * through the passed <tt>Reader</tt>
135 *
136 * @param reader
137 * reader to access an XML document
138 * @return created <tt>RPCMethodResponse</tt>
139 */
140 public static RPCMethodResponse createRPCMethodResponse( Reader reader ) throws RPCException {
141
142 Document doc = null;
143 try {
144 doc = XMLTools.parse( reader );
145 } catch (Exception e) {
146 LOG.logError( e.getMessage(), e );
147 throw new RPCException( e.toString() );
148 }
149
150 return createRPCMethodResponse( doc );
151 }
152
153 /**
154 * creates an instance of <tt>RPCMethodResponse</tt> from the XML document passed
155 *
156 * @param doc
157 * XML document containing a RPC method call
158 * @return created <tt>RPCMethodResponse</tt>
159 */
160 public static RPCMethodResponse createRPCMethodResponse( Document doc ) throws RPCException {
161
162 RPCMethodResponse mc = null;
163 try {
164 Element root = doc.getDocumentElement();
165
166 Element params = XMLTools.getChildElement( "params", null, root );
167
168 if ( params != null ) {
169 ElementList el = XMLTools.getChildElements( params );
170 RPCParameter[] parameters = null;
171 if ( el != null ) {
172 parameters = new RPCParameter[el.getLength()];
173 for (int i = 0; i < el.getLength(); i++) {
174 parameters[i] = createRPCParam( el.item( i ) );
175 }
176 }
177 mc = new RPCMethodResponse( parameters );
178 } else {
179 // a fault is contained instead of the expected result
180 Element fault = XMLTools.getChildElement( "fault", null, root );
181 RPCFault rpcFault = createRPCFault( fault );
182 mc = new RPCMethodResponse( rpcFault );
183 }
184
185 } catch (Exception e) {
186 LOG.logError( e.getMessage(), e );
187 throw new RPCException( e.toString() );
188 }
189
190 return mc;
191 }
192
193 /**
194 * @param par
195 * @return
196 * @throws RPCException
197 */
198 public static RPCMethodResponse createRPCMethodResponse( RPCParameter[] par ) {
199 RPCMethodResponse mc = null;
200 if ( par != null ) {
201 RPCParameter[] params = par;
202 mc = new RPCMethodResponse( params );
203 } else {
204 LOG.logError( "Fehler createRPCMEthodResponse in RPSFactory" );
205 }
206 return mc;
207 }
208
209 /**
210 * creates a <tt>RPCParameter</tt> from its XML representation
211 *
212 * @param param
213 * element containing a RPC param
214 * @return created <tt>RPCParameter</tt>
215 */
216 private static RPCParameter createRPCParam( Element param ) throws RPCException {
217
218 RPCParameter parameter = null;
219 try {
220 Element value = XMLTools.getChildElement( "value", null, param );
221 Element child = XMLTools.getFirstChildElement( value );
222 Object o = null;
223 Class cl = null;
224 if ( child.getNodeName().equals( "struct" ) ) {
225 o = createRPCStruct( child );
226 cl = RPCStruct.class;
227 } else if ( child.getNodeName().equals( "string" ) ) {
228 o = XMLTools.getRequiredStringValue( "string", null, value );
229 cl = String.class;
230 } else if ( child.getNodeName().equals( "int" ) ) {
231 double d = XMLTools.getRequiredNodeAsDouble( value, "./int", nsContext );
232 o = new Integer( (int) d );
233 cl = Integer.class;
234 } else if ( child.getNodeName().equals( "i4" ) ) {
235 double d = XMLTools.getRequiredNodeAsDouble( value, "./i4", nsContext );
236 o = new Integer( (int) d );
237 cl = Integer.class;
238 } else if ( child.getNodeName().equals( "double" ) ) {
239 double d = XMLTools.getRequiredNodeAsDouble( value, "./double", nsContext );
240 o = new Double( d );
241 cl = Double.class;
242 } else if ( child.getNodeName().equals( "boolean" ) ) {
243 o = Boolean.valueOf( child.getFirstChild().getNodeValue().equals( "1" ) );
244 cl = Boolean.class;
245 } else if ( child.getNodeName().equals( "dateTime.iso8601" ) ) {
246 String s = XMLTools.getRequiredStringValue( "dateTime.iso8601", null, value );
247 o = TimeTools.createCalendar( s ).getTime();
248 cl = Date.class;
249 } else if ( child.getNodeName().equals( "base64" ) ) {
250 } else if ( child.getNodeName().equals( "array" ) ) {
251 o = createArray( child );
252 cl = RPCParameter[].class;
253 }
254 parameter = new RPCParameter( cl, o );
255 } catch (Exception e) {
256 LOG.logError( e.getMessage(), e );
257 throw new RPCException( e.toString() );
258 }
259
260 return parameter;
261 }
262
263 /**
264 * creates a RPC struture object from the passed <tt>Element</tt>
265 *
266 * @param struct
267 * element containing a RPC struct
268 * @return created <tt>RPCStruct</tt>
269 */
270 private static RPCStruct createRPCStruct( Element struct ) throws RPCException {
271
272 RPCStruct structure = null;
273 try {
274 ElementList el = XMLTools.getChildElements( struct );
275 RPCMember[] members = null;
276 if ( el != null ) {
277 members = new RPCMember[el.getLength()];
278 for (int i = 0; i < el.getLength(); i++) {
279 members[i] = createRPCMember( el.item( i ) );
280 }
281 }
282 structure = new RPCStruct( members );
283 } catch (Exception e) {
284 LOG.logError( e.getMessage(), e );
285 throw new RPCException( e.toString() );
286 }
287
288 return structure;
289 }
290
291 /**
292 * creates a RPC struture member object from the passed <tt>Element</tt>
293 *
294 * @param member
295 * element containing a RPC member
296 * @return created <tt>RPCMember</tt>
297 */
298 private static RPCMember createRPCMember( Element member ) throws RPCException {
299
300 RPCMember mem = null;
301 try {
302 String name = XMLTools.getRequiredStringValue( "name", null, member );
303 Element value = XMLTools.getChildElement( "value", null, member );
304 Element child = XMLTools.getFirstChildElement( value );
305 Object o = null;
306 Class cl = null;
307 if ( child.getNodeName().equals( "struct" ) ) {
308 o = createRPCStruct( child );
309 cl = RPCStruct.class;
310 } else if ( child.getNodeName().equals( "string" ) ) {
311 o = XMLTools.getRequiredStringValue( "string", null, value );
312 cl = String.class;
313 } else if ( child.getNodeName().equals( "int" ) ) {
314 double d = XMLTools.getRequiredNodeAsDouble( value, "./int", nsContext );
315 o = new Integer( (int) d );
316 cl = Integer.class;
317 } else if ( child.getNodeName().equals( "i4" ) ) {
318 double d = XMLTools.getRequiredNodeAsDouble( value, "./i4", nsContext );
319 o = new Integer( (int) d );
320 cl = Integer.class;
321 } else if ( child.getNodeName().equals( "double" ) ) {
322 double d = XMLTools.getRequiredNodeAsDouble( value, "./double", nsContext );
323 o = new Double( d );
324 cl = Double.class;
325 } else if ( child.getNodeName().equals( "boolean" ) ) {
326 o = Boolean.valueOf( child.getFirstChild().getNodeValue().equals( "1" ) );
327 cl = Boolean.class;
328 } else if ( child.getNodeName().equals( "dateTime.iso8601" ) ) {
329 String s = XMLTools.getRequiredStringValue( "dateTime.iso8601", null, value );
330 o = TimeTools.createCalendar( s ).getTime();
331 cl = Date.class;
332 } else if ( child.getNodeName().equals( "base64" ) ) {
333 } else if ( child.getNodeName().equals( "array" ) ) {
334 o = createArray( child );
335 cl = RPCParameter[].class;
336 }
337 mem = new RPCMember( cl, o, name );
338 } catch (Exception e) {
339 LOG.logError( e.getMessage(), e );
340 throw new RPCException( e.toString() );
341 }
342
343 return mem;
344 }
345
346 /**
347 * creates an <tt>ArrayList</tt> object from the passed <tt>Element</tt>
348 *
349 * @param array
350 * @return created <tt>ArrayList</tt>
351 */
352 private static RPCParameter[] createArray( Element array ) throws RPCException {
353
354 RPCParameter[] param = null;
355 try {
356 Element data = XMLTools.getChildElement( "data", null, array );
357 ElementList el = XMLTools.getChildElements( data );
358 if ( el != null ) {
359 param = new RPCParameter[el.getLength()];
360 for (int i = 0; i < el.getLength(); i++) {
361 Element child = XMLTools.getFirstChildElement( el.item( i ) );
362 Object o = null;
363 Class cl = null;
364 if ( child.getNodeName().equals( "struct" ) ) {
365 o = createRPCStruct( child );
366 cl = RPCStruct.class;
367 } else if ( child.getNodeName().equals( "string" ) ) {
368 o = XMLTools.getRequiredStringValue( "string", null, el.item( i ) );
369 cl = String.class;
370 } else if ( child.getNodeName().equals( "int" ) ) {
371 double d = XMLTools.getRequiredNodeAsDouble( el.item( i ), "./int", nsContext );
372 o = new Integer( (int) d );
373 cl = Integer.class;
374 } else if ( child.getNodeName().equals( "i4" ) ) {
375 double d = XMLTools.getRequiredNodeAsDouble( el.item( i ), "./i4", nsContext );
376 o = new Integer( (int) d );
377 cl = Integer.class;
378 } else if ( child.getNodeName().equals( "double" ) ) {
379 double d = XMLTools.getRequiredNodeAsDouble( el.item( i ), "./double",
380 nsContext );
381 o = new Double( d );
382 cl = Double.class;
383 } else if ( child.getNodeName().equals( "boolean" ) ) {
384 o = Boolean.valueOf( child.getFirstChild().getNodeValue().equals( "1" ) );
385 cl = Boolean.class;
386 } else if ( child.getNodeName().equals( "dateTime.iso8601" ) ) {
387 String s = XMLTools.getRequiredStringValue( "dateTime.iso8601", null, el
388 .item( i ) );
389 o = TimeTools.createCalendar( s ).getTime();
390 cl = Date.class;
391 } else if ( child.getNodeName().equals( "base64" ) ) {
392 } else if ( child.getNodeName().equals( "array" ) ) {
393 o = createArray( child );
394 cl = RPCParameter[].class;
395 }
396 param[i] = new RPCParameter( cl, o );
397 }
398 }
399 } catch (Exception e) {
400 LOG.logError( e.getMessage(), e );
401 throw new RPCException( e.toString() );
402 }
403
404 return param;
405 }
406
407 /**
408 * creates an <tt>RPCFault</tt> object from the passed <tt>Element</tt>
409 *
410 * @param fault
411 * fault element
412 * @return created <tt>RPCFault</tt>
413 */
414 private static RPCFault createRPCFault( Element fault ) throws RPCException {
415
416 RPCFault rpcFault = null;
417 try {
418 Element value = XMLTools.getChildElement( "value", null, fault );
419 Element child = XMLTools.getFirstChildElement( value );
420 RPCStruct struct = createRPCStruct( child );
421 String s1 = null;
422 String s2 = null;
423 Object o = struct.getMember( "faultCode" ).getValue();
424 if ( o != null ) {
425 s1 = o.toString();
426 }
427 o = struct.getMember( "faultString" ).getValue();
428 if ( o != null ) {
429 s2 = o.toString();
430 }
431 rpcFault = new RPCFault( s1, s2 );
432 } catch (Exception e) {
433 LOG.logError( e.getMessage(), e );
434 throw new RPCException( e.toString() );
435 }
436
437 return rpcFault;
438 }
439
440 }