source: main/trunk/greenstone3/src/java/org/greenstone/gsdl3/util/GSXML.java@ 24393

Last change on this file since 24393 was 24393, checked in by sjm84, 13 years ago

Adding in the server-side code for the Document Maker as well as several other enhancements

  • Property svn:keywords set to Author Date Id Revision
File size: 33.9 KB
Line 
1/*
2* GSXML.java
3* Copyright (C) 2008 New Zealand Digital Library, http://www.nzdl.org
4*
5* This program is free software; you can redistribute it and/or modify
6* it under the terms of the GNU General Public License as published by
7* the Free Software Foundation; either version 2 of the License, or
8* (at your option) any later version.
9*
10* This program is distributed in the hope that it will be useful,
11* but WITHOUT ANY WARRANTY; without even the implied warranty of
12* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13* GNU General Public License for more details.
14*
15* You should have received a copy of the GNU General Public License
16* along with this program; if not, write to the Free Software
17* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18*/
19package org.greenstone.gsdl3.util;
20
21import org.w3c.dom.NamedNodeMap;
22import org.w3c.dom.Node;
23import org.w3c.dom.Element;
24import org.w3c.dom.NodeList;
25import org.w3c.dom.Document;
26import org.w3c.dom.Text;
27
28import javax.xml.transform.TransformerFactory;
29import javax.xml.transform.Transformer;
30import java.io.StringWriter;
31import javax.xml.transform.stream.StreamResult;
32import javax.xml.transform.dom.DOMSource;
33
34import java.util.Map;
35import java.util.Set;
36import java.util.HashMap;
37import java.util.Vector;
38import java.util.Iterator;
39import java.util.ArrayList;
40
41//import java.util.Locale;
42
43import org.apache.log4j.*;
44
45/** various functions for extracting info out of GS XML */
46public class GSXML {
47
48 static Logger logger = Logger.getLogger(org.greenstone.gsdl3.util.GSXML.class.getName());
49
50 // greenstone xml elements
51 public static final String MESSAGE_ELEM = "message";
52 public static final String REQUEST_ELEM = "request";
53 public static final String RESPONSE_ELEM = "response";
54 public static final String COLLECTION_ELEM = "collection";
55 public static final String SERVICE_ELEM = "service";
56 public static final String CLUSTER_ELEM = "serviceCluster";
57 public static final String SITE_ELEM = "site";
58 public static final String PARAM_ELEM = "param";
59 public static final String PARAM_OPTION_ELEM = "option";
60 public static final String CONTENT_ELEM = "content";
61 public static final String RESOURCE_ELEM = "resource";
62 public static final String DOCUMENT_ELEM = "document";
63 public static final String METADATA_ELEM = "metadata";
64 public static final String SERVICE_CLASS_ELEM = "serviceRack";
65 public static final String CLASSIFIER_ELEM = "classifier";
66 public static final String APPLET_ELEM = "applet";
67 public static final String APPLET_DATA_ELEM = "appletData";
68 public static final String CONFIGURE_ELEM = "configure";
69 public static final String STATUS_ELEM = "status";
70 public static final String ERROR_ELEM = "error";
71 public static final String DEFAULT_ELEM = "default";
72 public static final String STYLESHEET_ELEM = "format";//"stylesheet"; // any additional stylesheet stuff is carried in the message inside this elem
73 public static final String FORMAT_ELEM = "format"; // config files use format - should we use this instead of stylesheet??
74 public static final String TERM_ELEM = "term";
75 public static final String STOPWORD_ELEM = "stopword";
76 public static final String SYSTEM_ELEM = "system";
77 public static final String FORMAT_STRING_ELEM = "formatString";
78
79 //config file elems
80 public static final String COLLECTION_CONFIG_ELEM = "collectionConfig";
81 public static final String COLLECTION_BUILD_ELEM = "buildConfig";
82 public static final String COLLECTION_INIT_ELEM = "collectionInit";
83 public static final String RECOGNISE_ELEM = "recognise";
84 public static final String DOC_TYPE_ELEM = "docType";
85 public static final String SEARCH_ELEM = "search";
86 public static final String INFODB_ELEM = "infodb";
87 public static final String INDEX_ELEM = "index";
88 public static final String INDEX_STEM_ELEM = "indexStem";
89 public static final String INDEX_OPTION_ELEM = "indexOption";
90 public static final String BROWSE_ELEM = "browse";
91 public static final String DISPLAY_ELEM = "display";
92 public static final String LEVEL_ELEM = "level";
93
94 public static final String DBINFO_ELEM = "dbInfo";
95 public static final String DBNAME_ATT = "dbname";
96 public static final String DBPATH_ATT = "dbpath";
97 public static final String SQLSTATE_ATT = "sqlstate";
98 public static final String DATABASE_TYPE_ELEM = "databaseType";
99 public static final String SHORTNAME_ATT = "shortname";
100 public static final String NOTIFY_ELEM = "notify";
101 public static final String NOTIFY_HOST_ATT = "host";
102
103 //doc.xml file elems
104 public static final String DOCXML_SECTION_ELEM = "Section";
105 public static final String DOCXML_DESCRIPTION_ELEM = "Description";
106 public static final String DOCXML_METADATA_ELEM = "Metadata";
107 public static final String DOCXML_CONTENT_ELEM = "Content";
108
109 // elems for the pages to be processed by xslt
110 public final static String PAGE_ELEM = "page";
111 public final static String CONFIGURATION_ELEM = "config";
112 public final static String PAGE_REQUEST_ELEM = "pageRequest";
113 public final static String PAGE_RESPONSE_ELEM = "pageResponse";
114 public final static String PAGE_EXTRA_ELEM = "pageExtra";
115
116 //public final static String DESCRIPTION_ELEM = "description";
117
118 public static final String ACTION_ELEM = "action";
119 public static final String SUBACTION_ELEM = "subaction";
120
121 // add on to another elem type to get a list of that type
122 public static final String LIST_MODIFIER = "List";
123
124 // greenstone xml attributes
125 public static final String COLLECTION_ATT = "collection";
126 public static final String NAME_ATT = "name";
127 public static final String TO_ATT = "to";
128 public static final String USER_ID_ATT = "uid";
129 public static final String FROM_ATT = "from";
130 public static final String LANG_ATT = "lang";
131 public static final String TYPE_ATT = "type";
132 public static final String DB_TYPE_ATT = "dbType";
133 public static final String VALUE_ATT = "value";
134 public static final String DEFAULT_ATT = "default";
135 public static final String INFO_ATT = "info";
136 public static final String ACTION_ATT = "action";
137 public static final String SUBACTION_ATT = "subaction";
138 public static final String OUTPUT_ATT = "output";
139 public static final String ADDRESS_ATT = "address";
140 public static final String LOCAL_SITE_ATT = "localSite";
141 public static final String LOCAL_SITE_NAME_ATT = "localSiteName";
142 public static final String STATUS_ERROR_CODE_ATT = "code";
143 public static final String STATUS_PROCESS_ID_ATT = "pid";
144 public static final String PARAM_SHORTNAME_ATT = "shortname";
145 public static final String PARAM_IGNORE_POS_ATT = "ignore";
146 public static final String CLASSIFIER_CONTENT_ATT = "content";
147 public static final String ERROR_TYPE_ATT = "type";
148 public static final String COLLECT_TYPE_ATT = "ct";
149 public static final String HIDDEN_ATT = "hidden";
150
151 // document stuff
152 public static final String DOC_TYPE_ATT = "docType";
153 public static final String DOC_NODE_ELEM = "documentNode";
154 public static final String NODE_CONTENT_ELEM = "nodeContent";
155 public static final String NODE_STRUCTURE_ELEM = "nodeStructure";
156 public static final String NODE_ID_ATT = "nodeID";
157 public static final String NODE_NAME_ATT = "nodeName";
158 public static final String NODE_TYPE_ATT = "nodeType";
159 public static final String NODE_RANK_ATT = "rank";
160 public static final String NODE_TYPE_ROOT = "root";
161 public static final String NODE_TYPE_INTERNAL = "internal";
162 public static final String NODE_TYPE_LEAF = "leaf";
163
164 public static final String DOC_TYPE_SIMPLE = "simple";
165 public static final String DOC_TYPE_PAGED = "paged";
166 public static final String DOC_TYPE_HIERARCHY = "hierarchy";
167
168 public static final String SESSION_EXPIRATION = "session_expiration";
169 public static final String USER_SESSION_CACHE_ATT = "user_session_cache";
170
171 // classifier stuff
172 public static final String CLASS_NODE_ELEM = "classifierNode";
173 public static final String CLASS_NODE_ORIENTATION_ATT = "orientation";
174
175 // parameter types
176 public static final String PARAM_TYPE_INTEGER = "integer";
177 public static final String PARAM_TYPE_BOOLEAN = "boolean";
178 public static final String PARAM_TYPE_ENUM_START = "enum";
179 public static final String PARAM_TYPE_ENUM_SINGLE = "enum_single";
180 public static final String PARAM_TYPE_ENUM_MULTI = "enum_multi";
181 public static final String PARAM_TYPE_STRING = "string";
182 public static final String PARAM_TYPE_TEXT = "text";
183 public static final String PARAM_TYPE_MULTI = "multi";
184 public static final String PARAM_TYPE_FILE = "file";
185 public static final String PARAM_TYPE_INVISIBLE = "invisible";
186 // stuff for text strings
187 public static final String DISPLAY_TEXT_ELEM = "displayItem";
188 // the following are used for the name attributes
189 public static final String DISPLAY_TEXT_NAME = "name";
190 public static final String DISPLAY_TEXT_SUBMIT = "submit";
191 public static final String DISPLAY_TEXT_DESCRIPTION = "description";
192
193 // request types
194 // get the module description
195 public static final String REQUEST_TYPE_DESCRIBE = "describe";
196 // startup a process
197 public static final String REQUEST_TYPE_PROCESS = "process";
198 // get the status of an ongoing process
199 public static final String REQUEST_TYPE_STATUS = "status";
200 // system type request - eg reload a collection
201 public static final String REQUEST_TYPE_SYSTEM = "system";
202 // page requests to the Receptionist/Actions
203 public static final String REQUEST_TYPE_PAGE = "page"; // used to be cgi
204 // get any format info for a service
205 public static final String REQUEST_TYPE_FORMAT = "format";
206 // modify the requests
207 public static final String REQUEST_TYPE_MESSAGING = "messaging";
208 // save the format string
209 public static final String REQUEST_TYPE_FORMAT_STRING = "formatString";
210
211 // service types
212 public static final String SERVICE_TYPE_QUERY = "query";
213 public static final String SERVICE_TYPE_RETRIEVE = "retrieve";
214 public static final String SERVICE_TYPE_BROWSE = "browse";
215 public static final String SERVICE_TYPE_APPLET = "applet";
216 public static final String SERVICE_TYPE_PROCESS = "process";
217 public static final String SERVICE_TYPE_ENRICH = "enrich";
218 public static final String SERVICE_TYPE_OAI = "oai";
219 public static final String FLAX_PAGE = "flaxPage";
220 public static final String FLAX_PAGE_GENERATION = "FlaxPageGeneration";
221
222 // system command types and attributes
223 public static final String SYSTEM_TYPE_CONFIGURE = "configure";
224 public static final String SYSTEM_TYPE_ACTIVATE = "activate";
225 public static final String SYSTEM_TYPE_DEACTIVATE = "deactivate";
226
227 public static final String SYSTEM_SUBSET_ATT = "subset";
228 public static final String SYSTEM_MODULE_TYPE_ATT = "moduleType";
229 public static final String SYSTEM_MODULE_NAME_ATT = "moduleName";
230
231 // communicator types
232 public static final String COMM_TYPE_SOAP_JAVA = "soap";
233
234 // error types
235 public static final String ERROR_TYPE_SYNTAX = "syntax";
236 public static final String ERROR_TYPE_SYSTEM = "system";
237 public static final String ERROR_TYPE_INVALID_ID = "invalid_id";
238 public static final String ERROR_TYPE_OTHER = "other";
239
240 // some system wide param names
241 public static final String SUBSET_PARAM = "subset";
242
243 //for plugin
244 public static final String PLUGIN_ELEM = "plugin";
245 public static final String IMPORT_ELEM = "import";
246
247 //for authentication
248 public static final String AUTHEN_NODE_ELEM="authenticationNode";
249 public static final String USER_NODE_ELEM="userNode";
250
251 //for configure action results
252 public static final String SUCCESS = "success";
253 public static final String ERROR = "error";
254
255 /** takes a list of elements, and returns an array of strings
256* of the values of attribute att_name */
257 public static String [] getAttributeValuesFromList(Element list,
258 String att_name) {
259
260 NodeList children = list.getChildNodes();
261
262 int num_nodes = children.getLength();
263 String []ids = new String[num_nodes];
264 for (int i=0; i<num_nodes; i++) {
265 Element e = (Element)children.item(i);
266 String id = e.getAttribute(att_name);
267 ids[i] = id;
268 }
269
270 return ids;
271 }
272
273 public static HashMap extractParams(Element xml, boolean deep) {
274 return extractParams(xml, deep, null);
275 }
276
277 /** takes a paramList element, and gets a HashMap of name-value pairs
278* if deep=true, extracts embedded params, otherwise just top level
279* params*/
280 public static HashMap extractParams(Element xml, boolean deep, String toFind) {
281
282 if (!xml.getNodeName().equals(PARAM_ELEM+LIST_MODIFIER)) {
283 logger.error("paramList element should have been passed to extractParams, instead it was "+xml.getNodeName());
284 return null;
285 }
286
287 NodeList params = null;
288 if (deep) { // get all the nested ones
289 params = xml.getElementsByTagName(PARAM_ELEM);
290 } else { // just get the top level ones
291 params = xml.getChildNodes();
292 }
293 HashMap param_map = new HashMap();
294 for (int i=0; i<params.getLength(); i++) {
295 if (params.item(i).getNodeName().equals(PARAM_ELEM)) {
296 Element param = (Element)params.item(i);
297 String name=param.getAttribute(NAME_ATT);
298 String value=getValue(param); //att or content
299
300 // For only one parameter
301 if(toFind != null && name.equals(toFind)) {
302 param_map.put(name, value);
303 return param_map;
304 }
305 else if(toFind != null)
306 continue;
307
308 int pos = name.indexOf('.');
309 if (pos == -1) { // a base param
310 param_map.put(name, value);
311 } else { // a namespaced param
312
313 String namespace = name.substring(0, pos);
314 name = name.substring(pos+1);
315 HashMap map = (HashMap)param_map.get(namespace);
316 if (map == null) {
317 map = new HashMap();
318 param_map.put(namespace, map);
319 }
320 map.put(name, value);
321 }
322 }
323 }
324 return param_map;
325 }
326
327 /** gets the value att or the text content */
328 public static String getValue(Element e) {
329 String val = e.getAttribute(VALUE_ATT);
330 if (val ==null || val.equals("")) {
331 // have to get it out of the text
332 val=getNodeText(e);
333
334 } else {
335 // unescape the xml stuff
336 val = unXmlSafe(val);
337 }
338 return val;
339 }
340
341 /** extracts the text out of a node */
342 public static Node getNodeTextNode(Element param) {
343 param.normalize();
344 Node n = param.getFirstChild();
345 while (n!=null && n.getNodeType() !=Node.TEXT_NODE) {
346 n=n.getNextSibling();
347 }
348 return n;
349 }
350
351 /** extracts the text out of a node */
352 public static String getNodeText(Element param) {
353 Node text_node = getNodeTextNode(param);
354 if (text_node == null) {
355 return "";
356 }
357 return text_node.getNodeValue();
358 }
359
360 public static void setNodeText(Element elem, String text) {
361 Node old_text_node = getNodeTextNode(elem);
362 if (old_text_node != null) {
363 elem.removeChild(old_text_node);
364 }
365 Text t = elem.getOwnerDocument().createTextNode(text);
366 elem.appendChild(t);
367 }
368
369 /** add text to a document/subsection element */
370 public static boolean addDocText(Document owner, Element doc, String text) {
371
372 Element content = owner.createElement(NODE_CONTENT_ELEM);
373 Text t = owner.createTextNode(text);
374 content.appendChild(t);
375 doc.appendChild(content);
376 return true;
377 }
378
379 /** add an error message, unknown error type */
380 public static boolean addError(Document owner, Element doc, String text) {
381 return addError(owner, doc, text, ERROR_TYPE_OTHER);
382 }
383 /** add an error message */
384 public static boolean addError(Document owner, Element doc, String text,
385 String error_type) {
386
387 Element content = owner.createElement(ERROR_ELEM);
388 content.setAttribute(ERROR_TYPE_ATT, error_type);
389 Text t = owner.createTextNode(text);
390 content.appendChild(t);
391 doc.appendChild(content);
392 return true;
393 }
394
395 /** add an error message */
396 public static boolean addError(Document owner, Element doc, Throwable error) {
397 return addError(owner, doc, error, ERROR_TYPE_OTHER);
398 }
399
400 /** add an error message */
401 public static boolean addError(Document owner, Element doc,
402 Throwable error, String error_type) {
403 error.printStackTrace();
404 return addError(owner, doc, error.toString(), error_type);
405 }
406
407 public static Element createMetadataParamList(Document owner, Vector meta_values) {
408
409 Element meta_param_list = owner.createElement(PARAM_ELEM+LIST_MODIFIER);
410 Iterator i = meta_values.iterator();
411 while(i.hasNext()) {
412 String next = (String)i.next();
413 Element meta_param = owner.createElement(PARAM_ELEM);
414 meta_param_list.appendChild(meta_param);
415 meta_param.setAttribute(NAME_ATT, "metadata");
416 meta_param.setAttribute(VALUE_ATT, next);
417 }
418 return meta_param_list;
419 }
420
421 /** adds a metadata elem to a list */
422 public static boolean addMetadata(Document owner, Element list,
423 String meta_name, String meta_value) {
424 if (meta_value==null || meta_value.equals("")) {
425 return false;
426 }
427 Element data = owner.createElement(METADATA_ELEM);
428 data.setAttribute(NAME_ATT, meta_name);
429 Text t = owner.createTextNode(meta_value);
430 data.appendChild(t);
431 list.appendChild(data);
432 return true;
433
434 }
435
436 /** copies the metadata out of the metadataList of 'from' into
437* the metadataList of 'to' */
438 public static boolean mergeMetadataLists(Node to, Node from) {
439 Node from_meta = getChildByTagName(from, METADATA_ELEM+LIST_MODIFIER);
440 if (from_meta == null) { // nothing to copy
441 return true;
442 }
443 return mergeMetadataFromList(to, from_meta);
444 }
445
446
447 /** copies the metadata out of the meta_list metadataList into
448* the metadataList of 'to' */
449 public static boolean mergeMetadataFromList(Node to, Node meta_list) {
450 if (meta_list == null) return false;
451 Node to_meta = getChildByTagName(to, METADATA_ELEM+LIST_MODIFIER);
452 Document to_owner = to.getOwnerDocument();
453 if (to_meta == null) {
454 to.appendChild(to_owner.importNode(meta_list, true));
455 return true;
456 }
457 // copy individual metadata elements
458 NodeList meta_items = ((Element)meta_list).getElementsByTagName(METADATA_ELEM);
459 for (int i=0; i<meta_items.getLength(); i++) {
460 to_meta.appendChild(to_owner.importNode(meta_items.item(i),true));
461 }
462 return true;
463 }
464
465 /** copies all the children from from to to */
466 public static boolean mergeElements(Element to, Element from) {
467
468 Document owner = to.getOwnerDocument();
469 Node child = from.getFirstChild();
470 while (child != null) {
471 to.appendChild(owner.importNode(child, true));
472 child = child.getNextSibling();
473 }
474 return true;
475 }
476 /** returns the (first) element child of the node n */
477 public static Element getFirstElementChild(Node n) {
478
479 Node child = n.getFirstChild();
480 while (child!=null) {
481 if (child.getNodeType() == Node.ELEMENT_NODE) {
482 return (Element)child;
483 }
484 child = child.getNextSibling();
485 }
486 return null; //no element child found
487 }
488 /** returns the (first) child element with the given name */
489 public static Node getChildByTagName(Node n, String name) {
490 if(n != null) { // this line is an attempted solution to the NullPointerException mentioned
491 // in trac bug ticket #225. If n is null can't do n.getFirstChild() below. As per bug #225:
492 // GSXML.getNodeByPath() is called by GS2BrowseAction, which then calls this method.
493 // If n is null, null will be returned which GS2BrowseAction already checks for. It's here
494 // that the NullPointerException was thrown.
495
496 Node child = n.getFirstChild();
497 while (child!=null) {
498 if (child.getNodeName().equals(name)) {
499 return child;
500 }
501 child = child.getNextSibling();
502 }
503 }
504 return null; //not found
505 }
506
507 /** returns the (nth) child element with the given name
508* index numbers start at 0 */
509 public static Node getChildByTagNameIndexed(Node n, String name, int index) {
510 if (index == -1) {
511 return getChildByTagName(n, name);
512 }
513 int count = 0;
514 Node child = n.getFirstChild();
515 while (child!=null) {
516 if (child.getNodeName().equals(name)) {
517 if (count == index) {
518 return child;
519 } else {
520 count++;
521 }
522 }
523 child = child.getNextSibling();
524 }
525 return null; //not found
526 }
527
528 /** takes an xpath type expression of the form name/name/...
529* and returns the first node that matches, or null if not found */
530 public static Node getNodeByPath(Node n, String path) {
531
532 String link = GSPath.getFirstLink(path);
533 path = GSPath.removeFirstLink(path);
534 while (!link.equals("")) {
535 n = getChildByTagName(n, link);
536 if (n==null) {
537 return null;
538 }
539 link = GSPath.getFirstLink(path);
540 path = GSPath.removeFirstLink(path);
541 }
542 return n;
543 }
544
545 /** takes an xpath type expression of the form name/name/...
546* and returns the first node that matches, or null if not found
547* can include [i] indices. index numbers start at 0 */
548 public static Node getNodeByPathIndexed(Node n, String path) {
549
550 String link = GSPath.getFirstLink(path);
551 int index = GSPath.getIndex(link);
552 if (index != -1) {
553 link = GSPath.removeIndex(link);
554 }
555 path = GSPath.removeFirstLink(path);
556 while (!link.equals("")) {
557 n = getChildByTagNameIndexed(n, link, index);
558 if (n==null) {
559 return null;
560 }
561 link = GSPath.getFirstLink(path);
562 index = GSPath.getIndex(link);
563 if (index != -1) {
564 link = GSPath.removeIndex(link);
565 }
566 path = GSPath.removeFirstLink(path);
567 }
568 return n;
569 }
570
571 public static HashMap getChildrenMap(Node n) {
572
573 HashMap map= new HashMap();
574 Node child = n.getFirstChild();
575 while (child!=null) {
576 String name = child.getNodeName();
577 map.put(name, child);
578 child = child.getNextSibling();
579 }
580 return map;
581 }
582
583 public static NodeList getChildrenByTagName(Node n, String name) {
584 MyNodeList node_list = new MyNodeList();
585 Node child = n.getFirstChild();
586 while (child!=null) {
587 if (child.getNodeName().equals(name)) {
588 node_list.addNode(child);
589 }
590 child = child.getNextSibling();
591 }
592 return node_list;
593 }
594
595
596 /** Duplicates an element, but gives it a new name */
597 public static Element duplicateWithNewName(Document owner, Element element,
598 String element_name, boolean with_attributes) {
599 return duplicateWithNewNameNS(owner, element, element_name, null, with_attributes);
600 }
601
602 /** Duplicates an element, but gives it a new name */
603 public static Element duplicateWithNewNameNS(Document owner,
604 Element element,
605 String element_name,
606 String namespace_uri,
607 boolean with_attributes) {
608 Element duplicate;
609 if (namespace_uri == null) {
610 duplicate = owner.createElement(element_name);
611 } else {
612 duplicate = owner.createElementNS(namespace_uri, element_name);
613 }
614 // Copy element attributes
615 if (with_attributes) {
616 NamedNodeMap attributes = element.getAttributes();
617 for (int i = 0; i < attributes.getLength(); i++) {
618 Node attribute = attributes.item(i);
619 duplicate.setAttribute(attribute.getNodeName(), attribute.getNodeValue());
620 }
621 }
622
623 // Copy element children
624 NodeList children = element.getChildNodes();
625 for (int i = 0; i < children.getLength(); i++) {
626 Node child = children.item(i);
627 duplicate.appendChild(owner.importNode(child, true));
628 }
629
630 return duplicate;
631 }
632
633 public static void copyAllChildren(Element to, Element from) {
634
635 Document to_doc = to.getOwnerDocument();
636 Node child = from.getFirstChild();
637 while (child != null) {
638 to.appendChild(to_doc.importNode(child, true));
639 child = child.getNextSibling();
640 }
641 }
642 /** returns a basic request message */
643 public static Element createBasicRequest(Document owner,
644 String request_type, String to,
645 String lang,
646 String uid) {
647 Element request = owner.createElement(REQUEST_ELEM);
648 request.setAttribute(TYPE_ATT, request_type);
649 request.setAttribute(LANG_ATT, lang);
650 request.setAttribute(TO_ATT, to);
651 request.setAttribute(USER_ID_ATT, uid);
652 return request;
653 }
654
655 public static Element createBasicResponse(Document owner, String from)
656 {
657 Element response = owner.createElement(GSXML.RESPONSE_ELEM);
658 response.setAttribute(GSXML.FROM_ATT, from);
659 response.setAttribute(GSXML.TYPE_ATT, GSXML.REQUEST_TYPE_PROCESS);
660 return response;
661 }
662
663 public static Element createMetadataElement(Document owner, String name, String value)
664 {
665 Element metaElem = owner.createElement(GSXML.METADATA_ELEM);
666 metaElem.setAttribute(GSXML.NAME_ATT, name);
667 metaElem.setAttribute(GSXML.VALUE_ATT, value);
668 return metaElem;
669 }
670
671 public static Element createTextElement(Document owner, String elem_name,
672 String text) {
673 Element e = owner.createElement(elem_name);
674 Text t = owner.createTextNode(text);
675 e.appendChild(t);
676 return e;
677
678 }
679
680 public static Element createTextElement(Document owner, String elem_name,
681 String text, String att_name, String att_value) {
682 Element e = owner.createElement(elem_name);
683 e.setAttribute(att_name, att_value);
684 Text t = owner.createTextNode(text);
685 e.appendChild(t);
686 return e;
687
688 }
689
690 public static Element createDisplayTextElement(Document owner,
691 String text_name,
692 String text) {
693 Element e = owner.createElement(DISPLAY_TEXT_ELEM);
694 e.setAttribute(NAME_ATT, text_name);
695 Text t = owner.createTextNode(text);
696 e.appendChild(t);
697 return e;
698
699 }
700
701
702 public static Element createParameter(Document owner, String name,
703 String value) {
704 Element param = owner.createElement(PARAM_ELEM);
705 param.setAttribute(NAME_ATT, name);
706 param.setAttribute(VALUE_ATT, value);
707 return param;
708 }
709
710 public static void addParametersToList(Document owner, Element param_list,
711 HashMap params) {
712 if (params == null)
713 {
714 return;
715 }
716
717 Set items = params.entrySet();
718 Iterator i = items.iterator();
719 while(i.hasNext()) {
720 Map.Entry m = (Map.Entry)i.next();
721 param_list.appendChild(createParameter(owner, (String)m.getKey(), (String)m.getValue()));
722 }
723
724 }
725
726 public static Element createParameterDescription(Document owner,
727 String id,
728 String display_name,
729 String type,
730 String default_value,
731 String []option_ids,
732 String []option_names) {
733
734
735 Element p = owner.createElement(PARAM_ELEM);
736 p.setAttribute(NAME_ATT, id);
737 p.setAttribute(TYPE_ATT, type);
738 p.appendChild(createDisplayTextElement(owner, GSXML.DISPLAY_TEXT_NAME, display_name));
739
740 if (default_value != null) {
741 p.setAttribute(DEFAULT_ATT, default_value);
742 }
743 if (option_ids!=null && option_names!=null) {
744 for (int i=0; i<option_ids.length; i++) {
745 Element e = owner.createElement(PARAM_OPTION_ELEM);
746 e.setAttribute(NAME_ATT, option_ids[i]);
747 e.appendChild(createDisplayTextElement(owner, GSXML.DISPLAY_TEXT_NAME, option_names[i]));
748 p.appendChild(e);
749 }
750 }
751 return p;
752 }
753 public static Element createParameterDescription2(Document owner,
754 String id,
755 String display_name,
756 String type,
757 String default_value,
758 ArrayList option_ids,
759 ArrayList option_names) {
760
761
762 Element p = owner.createElement(PARAM_ELEM);
763 p.setAttribute(NAME_ATT, id);
764 p.setAttribute(TYPE_ATT, type);
765 p.appendChild(createDisplayTextElement(owner, GSXML.DISPLAY_TEXT_NAME, display_name));
766 if (default_value != null) {
767 p.setAttribute(DEFAULT_ATT, default_value);
768 }
769 if (option_ids!=null && option_names!=null) {
770 for (int i=0; i<option_ids.size(); i++) {
771 Element e = owner.createElement(PARAM_OPTION_ELEM);
772 e.setAttribute(NAME_ATT, (String)option_ids.get(i));
773 e.appendChild(createDisplayTextElement(owner, GSXML.DISPLAY_TEXT_NAME, (String)option_names.get(i)));
774 p.appendChild(e);
775 }
776 }
777 return p;
778 }
779
780
781 /** returns the element parent/node_name[@attribute_name='attribute_value']
782*/
783 public static Element getNamedElement(Element parent, String node_name,
784 String attribute_name,
785 String attribute_value) {
786
787 NodeList children = parent.getChildNodes();
788 for (int i=0; i<children.getLength(); i++) {
789 Node child = children.item(i);
790 if (child.getNodeName().equals(node_name)) {
791 if (((Element)child).getAttribute(attribute_name).equals(attribute_value))
792 return (Element)child;
793 }
794 }
795 // not found
796 return null;
797 }
798 /** returns a NodeList of elements: ancestor/node_name[@attribute_name='attribute_value']
799*/
800 public static NodeList getNamedElements(Element ancestor, String node_name, String attribute_name, String attribute_value) {
801 MyNodeList node_list = new MyNodeList();
802 NodeList children = ancestor.getElementsByTagName(node_name);
803
804 if(children != null && children.getLength() > 0) {
805
806 for (int i=0; i<children.getLength(); i++) {
807 Node child = children.item(i);
808 if (child.getNodeName().equals(node_name)) {
809 if (((Element)child).getAttribute(attribute_name).equals(attribute_value))
810 node_list.addNode(child);
811 }
812 }
813 }
814 return node_list;
815 }
816
817 public static int SORT_TYPE_STRING = 0;
818 public static int SORT_TYPE_INT = 1;
819 public static int SORT_TYPE_FLOAT = 2;
820
821 // sort type:
822 public static Element insertIntoOrderedList(Element parent_node,
823 String node_name,
824 Element start_from_elem,
825 Element new_elem, String sort_att,
826 boolean descending) {
827 if (new_elem == null) return null;
828 Element cloned_elem = (Element)parent_node.getOwnerDocument().importNode(new_elem, true);
829 if (start_from_elem == null) {
830 parent_node.appendChild(cloned_elem);
831 return cloned_elem;
832 }
833
834 Node current_node = start_from_elem;
835 String insert_att = cloned_elem.getAttribute(sort_att);
836 String list_att = start_from_elem.getAttribute(sort_att);
837 while ((!descending && list_att.compareTo(insert_att)<0) || (descending && list_att.compareTo(insert_att)>0)) {
838 current_node = current_node.getNextSibling();
839 if (current_node == null) break; // end of the list
840 if (!current_node.getNodeName().equals(node_name)) {
841 continue; // not a valid node
842 }
843 list_att = ((Element)current_node).getAttribute(sort_att);
844 }
845
846 parent_node.insertBefore(cloned_elem, current_node);
847 return cloned_elem;
848 }
849
850
851 /** Returns the appropriate language element from a display elem,
852* display is the containing element, name is the name of the element to
853* look for, lang is the preferred language, lang_default is the fall back
854* lang if neither lang is found, will return the first one it finds*/
855 public static String getDisplayText(Element display, String name,
856 String lang, String lang_default) {
857
858 String def = null;
859 String first = null;
860 NodeList elems = display.getElementsByTagName(DISPLAY_TEXT_ELEM);
861 if (elems.getLength() == 0) return "";
862 for (int i=0; i<elems.getLength(); i++) {
863 Element e = (Element)elems.item(i);
864 String n = e.getAttribute(NAME_ATT);
865 if (name.equals(n)) {
866 String l = e.getAttribute(LANG_ATT);
867 if (lang.equals(l)) {
868 return getNodeText(e);
869 } else if (lang_default.equals(l)) {
870 def = getNodeText(e);
871 } else if (first == null) {
872 first = getNodeText(e);
873 }
874 } else {
875 continue;
876 }
877 }
878
879 if (def != null) {
880 return def;
881 }
882 if (first != null) {
883 return first;
884 }
885 return "";
886 }
887
888 // replaces < > " ' & in the original with their entities
889 public static String xmlSafe(String original) {
890
891 StringBuffer filtered = new StringBuffer(original.length());
892 char c;
893 for (int i=0; i<original.length(); i++) {
894 c = original.charAt(i);
895 if (c == '>') {
896 filtered.append("&gt;");
897 } else if (c == '<') {
898 filtered.append("&lt;");
899 } else if (c == '"') {
900 filtered.append("&quot;");
901 } else if (c == '&') {
902 filtered.append("&amp;");
903 } else if (c == '\'') {
904 filtered.append("&apos;");
905 } else {
906 filtered.append(c);
907 }
908 }
909 return filtered.toString();
910 }
911
912
913 // replaces < > " ' & entities with their originals
914 public static String unXmlSafe(String original) {
915
916 StringBuffer filtered = new StringBuffer(original.length());
917 char c;
918 for (int i=0; i<original.length(); i++) {
919 c = original.charAt(i);
920 if (c == '&') {
921 int pos = original.indexOf(";", i);
922 String entity = original.substring(i+1, pos);
923 if (entity.equals("gt")) {
924 filtered.append(">");
925 } else if (entity.equals("lt")) {
926 filtered.append("<");
927 } else if (entity.equals("apos")) {
928 filtered.append("'");
929 } else if (entity.equals("amp")) {
930 filtered.append("&");
931 } else if (entity.equals("quot")) {
932 filtered.append("\"");
933 } else {
934 filtered.append("&"+entity+";");
935 }
936 i = pos;
937 } else {
938 filtered.append(c);
939 }
940 }
941 return filtered.toString();
942 }
943
944 public static void printXMLNode(Node e, boolean printText) {
945 printXMLNode(e, 0, printText) ;
946 }
947
948 public static String xmlNodeToString(Node e){
949 StringBuffer sb = new StringBuffer("");
950 xmlNodeToString(sb,e,0);
951 return sb.toString();
952 }
953
954 private static void xmlNodeToString(StringBuffer sb, Node e, int depth){
955
956 for (int i=0 ; i<depth ; i++)
957 sb.append(' ') ;
958
959 if (e.getNodeType() == Node.TEXT_NODE){
960 sb.append("text") ;
961 return ;
962 }
963
964 sb.append('<');
965 sb.append(e.getNodeName());
966 NamedNodeMap attrs = e.getAttributes();
967 if(attrs != null)
968 {
969 for (int i = 0; i < attrs.getLength(); i++) {
970 Node attr = attrs.item(i);
971 sb.append(' ');
972 sb.append(attr.getNodeName());
973 sb.append("=\"");
974 sb.append(attr.getNodeValue());
975 sb.append('"');
976 }
977 }
978
979 NodeList children = e.getChildNodes();
980
981 if (children == null || children.getLength() == 0)
982 sb.append("/>\n") ;
983 else {
984
985 sb.append(">\n") ;
986
987 int len = children.getLength();
988 for (int i = 0; i < len; i++) {
989 xmlNodeToString(sb,children.item(i), depth + 1);
990 }
991
992 for (int i=0 ; i<depth ; i++)
993 sb.append(' ') ;
994
995 sb.append("</" + e.getNodeName() + ">\n");
996 }
997
998
999 }
1000
1001 public static void printXMLNode(Node e, int depth, boolean printText) { //recursive method call using DOM API...
1002
1003 if(e == null){return;}
1004
1005 for (int i=0 ; i<depth ; i++)
1006 System.out.print(' ') ;
1007
1008 if (e.getNodeType() == Node.TEXT_NODE){
1009 if(printText){
1010 System.out.println(e.getNodeValue());
1011 }
1012 else {
1013 System.out.println("text");
1014 }
1015 return ;
1016 }
1017
1018 System.out.print('<');
1019 System.out.print(e.getNodeName());
1020 NamedNodeMap attrs = e.getAttributes();
1021
1022 if (attrs != null)
1023 {
1024 for (int i = 0; i < attrs.getLength(); i++) {
1025 Node attr = attrs.item(i);
1026 System.out.print(' ');
1027 System.out.print(attr.getNodeName());
1028 System.out.print("=\"");
1029 System.out.print(attr.getNodeValue());
1030 System.out.print('"');
1031 }
1032 }
1033
1034 NodeList children = e.getChildNodes();
1035
1036 if (children == null || children.getLength() == 0)
1037 System.out.println("/>") ;
1038 else {
1039
1040 System.out.println('>') ;
1041
1042 int len = children.getLength();
1043 for (int i = 0; i < len; i++) {
1044 printXMLNode(children.item(i), depth + 1, printText);
1045 }
1046
1047 for (int i=0 ; i<depth ; i++)
1048 System.out.print(' ') ;
1049
1050 System.out.println("</" + e.getNodeName() + ">");
1051 }
1052 }
1053
1054 public static void elementToLogAsString(Element e) {
1055 try {
1056 TransformerFactory tf = TransformerFactory.newInstance();
1057 Transformer trans = tf.newTransformer();
1058 StringWriter sw = new StringWriter();
1059 trans.transform(new DOMSource(e), new StreamResult(sw));
1060 System.err.println( sw.toString() );
1061 } catch( Exception ex ) {
1062 System.err.println( "couldn't write " + e + " to log" );
1063 }
1064 }
1065}
Note: See TracBrowser for help on using the repository browser.