source: trunk/gli/src/org/greenstone/gatherer/cdm/Argument.java@ 11130

Last change on this file since 11130 was 10345, checked in by mdewsnip, 19 years ago

Removed some more crap out of the Utility class.

  • Property svn:keywords set to Author Date Id Revision
File size: 21.1 KB
Line 
1/**
2 *#########################################################################
3 *
4 * A component of the Greenstone Librarian Interface (GLI) application,
5 * part of the Greenstone digital library software suite from the New
6 * Zealand Digital Library Project at the University of Waikato,
7 * New Zealand.
8 *
9 * Author: John Thompson
10 * Greenstone Project, New Zealand Digital Library
11 * University of Waikato
12 * http://www.nzdl.org
13 *
14 * Copyright (C) 2004 New Zealand Digital Library, University of Waikato
15 *
16 * This program is free software; you can redistribute it and/or modify
17 * it under the terms of the GNU General Public License as published by
18 * the Free Software Foundation; either version 2 of the License, or
19 * (at your option) any later version.
20 *
21 * This program is distributed in the hope that it will be useful,
22 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 * GNU General Public License for more details.
25 *
26 * You should have received a copy of the GNU General Public License
27 * along with this program; if not, write to the Free Software
28 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29 *########################################################################
30 */
31
32package org.greenstone.gatherer.cdm;
33
34import java.io.*;
35import java.util.*;
36import org.greenstone.gatherer.Configuration;
37import org.greenstone.gatherer.DebugStream;
38import org.greenstone.gatherer.Gatherer;
39import org.greenstone.gatherer.collection.Collection;
40import org.greenstone.gatherer.collection.CollectionManager;
41import org.greenstone.gatherer.metadata.MetadataElement;
42import org.greenstone.gatherer.metadata.MetadataTools;
43import org.greenstone.gatherer.util.StaticStrings;
44import org.greenstone.gatherer.util.XMLTools;
45import org.w3c.dom.*;
46
47/** This class contains all the details about a single argument that can be passed to this plugin, including option lists if the parameters are restricted.
48 * @author John Thompson, Greenstone Project, New Zealand Digital Library, University of Waikato
49 * @version 2.41 final
50 */
51public class Argument
52 implements Comparable, Serializable {
53 /** An element of the argument type enumeration specifying a combobox control. */
54 static final public byte ENUM = 0;
55 /** An element of the argument type enumeration specifying a checkbox control. */
56 static final public byte FLAG = 1;
57 /** An element of the argument type enumeration specifying a tree control. */
58 static final public byte HIERARCHY = 2;
59 /** An element of the argument type enumeration specifying a spinner control. */
60 static final public byte INTEGER = 3;
61 /** An element of the argument type enumeration specifying a language combobox control. */
62 static final public byte LANGUAGE = 4;
63 /** An element of the argument type enumeration specifying a list control. */
64 static final public byte METADATA = 5;
65 /** An element of the argument type enumeration specifying a metadata combobox control. */
66 static final public byte METADATUM = 6;
67 /** An element of the argument type enumeration specifying a text field. */
68 static final public byte STRING = 7;
69 /** An element of the argument type enumeration specifying a regular expression text field. */
70 static final public byte REGEXP = 8;
71 /** true if this argument should actually be hidden within the GLI. This is iportant for arguments such as import dir or other location critical arguments. */
72 private boolean hidden_gli = false;
73 /** <i>true</i> if this argument is required for the applicable script to work properly, <i>false</i> otherwise. */
74 private boolean required = false;
75 /** The type of this argument. Used to be an int, but bytes are cheaper. */
76 private byte type = STRING;
77 /** The maximum value an integer based control can have. */
78 private int maximum = Integer.MAX_VALUE;
79 /** The minimum value an integer based control can have. */
80 private int minimum = Integer.MIN_VALUE;
81 /** Every argument has a detail mode level at which it becomes available to the user to edit.
82 * @see org.greenstone.gatherer.Configuration
83 */
84 private int mode_level = Configuration.LIBRARIAN_MODE;
85 /** The DOM element this argument is built around, if any. */
86 private Element element;
87 /** If the argument is of type ENUM then this map holds all the various options. Each entry is an &lt;option value&gt; -&gt; &lt;description&gt; mapping. */
88 private HashMap list = null;
89 /** A default value for parameter-type arguments. May be a Perl pattern. */
90 private String default_value = null;
91 /** The text description of this argument parsed from the pluginfo output. */
92 private String description = null;
93 /** The argument flag as it appears in the command. Also used as the unique identifier of an argument. */
94 private String name = null;
95 /** The plugin that owns this argument, for the purposes of visualising inheritance. */
96 private String owner = null;
97
98 /** Default Constructor. */
99 public Argument() {
100 }
101
102 /** Another constructor but this one is a little more interesting as it takes a DOM element.
103 * @param element the Element this argument is based around
104 */
105 public Argument(Element element) {
106 this.element = element;
107 }
108
109 /** Method to add an element to the option list.
110 * @param name the name value of the option as a String
111 * @param desc the description of this options as a String
112 */
113 public void addOption(String name, String desc) {
114 if(type == ENUM && name != null) {
115 if(desc == null) {
116 desc = "";
117 }
118 if(list == null) {
119 list = new HashMap();
120 }
121 list.put(name, desc);
122 }
123 }
124
125 /** Method to compare two arguments for ordering.
126 * @param object the argument we are comparing to, as an Object
127 * @return an int specifying the argument order, using values as set out in String
128 * @see org.greenstone.gatherer.cdm.Argument
129 */
130 public int compareTo(Object object) {
131 if(object instanceof Argument) {
132 return getName().compareTo(((Argument)object).getName());
133 }
134 else {
135 return toString().compareTo(object.toString());
136 }
137 }
138
139 /** Create a copy of this argument.
140 * @return a newly created Argument with the same details as this one
141 */
142 public Argument copy() {
143 Argument copy = new Argument();
144 copy.setDefaultValue(default_value);
145 copy.setDescription(description);
146 copy.setOptions(list);
147 copy.setOwner(owner);
148 copy.setName(name);
149 copy.setRequired(required);
150 copy.setType(type);
151 copy.setMinimum(minimum);
152 copy.setMaximum(maximum);
153 copy.setModeLevel(mode_level);
154 return copy;
155 }
156
157 /** Method to determine if two arguments are equal.
158 * @param object the argument to test against, as an Object
159 * @return true if the arguments names match, false otherwise
160 */
161 public boolean equals(Object object) {
162 return (compareTo(object) == 0);
163 }
164
165 /** Method to retrieve the value of default_value.
166 * @return a String containing the default value
167 */
168 public String getDefaultValue() {
169 return default_value;
170 }
171
172 /** Method to retrieve this arguments description.
173 * @return a String containing the description
174 */
175 public String getDescription() {
176 return description;
177 }
178
179 /** Method to retrieve the description of a certain list option value.
180 * @param key the String whose description we are searching for
181 * @return the description of the desired key as a String which may be empty if no such key exists
182 */
183 public String getDescription(String key) {
184 if(list.containsKey(key)) {
185 return (String)list.get(key);
186 }
187 return "";
188 }
189
190 /** Retrieve the upper bound of a range based argument.
191 * @return the maximum as an int
192 */
193 public int getMaximum() {
194 return maximum;
195 }
196
197 /** Retrieve the lower bound of a range based argument.
198 * @return the minimum as an int
199 */
200 public int getMinimum() {
201 return minimum;
202 }
203
204 /** Retrieves the mode level at which this argument should become available. Any higher levels should also see this argument.
205 * @return the mode level as an int
206 */
207 public int getModeLevel() {
208 return mode_level;
209 }
210
211 /** Method to retrieve the value of name.
212 * @return a String containing the argument name
213 * @see org.greenstone.gatherer.util.StaticStrings#NAME_ATTRIBUTE
214 */
215 public String getName() {
216 if(name == null && element != null) {
217 name = element.getAttribute(StaticStrings.NAME_ATTRIBUTE);
218 }
219 return name;
220 }
221
222 /** Method to retrieve the option list for this argument.
223 * @return a HashMap containing &lt;option value&gt; -&gt; &lt;description&gt; entries
224 */
225 public HashMap getOptions() {
226 return list;
227 }
228
229 /** Retrieve the name of the owner of this argument.
230 * @return the owners name as a String
231 */
232 public String getOwner() {
233 return owner;
234 }
235
236 /** Method to determine the type of this argument.
237 * @return a byte specifying the type
238 */
239 public byte getType() {
240 return type;
241 }
242
243 /** Method to retrieve the value of value.
244 * @return the value of value as a String
245 * @see org.greenstone.gatherer.Gatherer#c_man
246 * @see org.greenstone.gatherer.collection.CollectionManager#getCollection
247 */
248 public String getValue()
249 {
250 // Only assigned arguments have values.
251 if (element == null) {
252 return null;
253 }
254
255 return XMLTools.getValue(element);
256 }
257
258
259 /** Method to determine if this argument has been assigned.
260 * @return true if it has, false otherwise
261 * @see org.greenstone.gatherer.util.StaticStrings#ASSIGNED_ATTRIBUTE
262 * @see org.greenstone.gatherer.util.StaticStrings#TRUE_STR
263 */
264 public boolean isAssigned() {
265 return (element != null && element.getAttribute(StaticStrings.ASSIGNED_ATTRIBUTE).equals(StaticStrings.TRUE_STR));
266 }
267
268 /** Determine if this is a custom argument ie one that has been parsed from the config file but doesn't have a matching entry in the argument library.
269 * @return true if this argument is a custom, false otherwise
270 * @see org.greenstone.gatherer.util.StaticStrings#CUSTOM_ATTRIBUTE
271 * @see org.greenstone.gatherer.util.StaticStrings#TRUE_STR
272 */
273 public boolean isCustomArgument() {
274 return (element != null && element.getAttribute(StaticStrings.CUSTOM_ATTRIBUTE).equals(StaticStrings.TRUE_STR));
275 }
276
277 /** Determine if this argument is hidden in GLI
278 * @return true if the argument is hidden, false otherwise
279 */
280 public boolean isHiddenGLI() {
281 return hidden_gli;
282 }
283
284 /** Method to determine of this argument is required for the associated script to work.
285 * @return true if this argument is required, false otherwise
286 */
287 public boolean isRequired() {
288 return required;
289 }
290
291 /** Method to allow for the activation of arguments that might never have their setValue() method called.
292 * @param assigned the desired state as a boolean
293 * @see org.greenstone.gatherer.util.StaticStrings#ASSIGNED_ATTRIBUTE
294 * @see org.greenstone.gatherer.util.StaticStrings#FALSE_STR
295 * @see org.greenstone.gatherer.util.StaticStrings#TRUE_STR
296 */
297 public void setAssigned(boolean assigned) {
298 if(element != null) {
299 element.setAttribute(StaticStrings.ASSIGNED_ATTRIBUTE, (assigned ? StaticStrings.TRUE_STR : StaticStrings.FALSE_STR));
300 }
301 }
302
303 /** Set the custom argument flag.
304 * @param custom true to make this argument custom, false otherwise
305 * @see org.greenstone.gatherer.util.StaticStrings#CUSTOM_ATTRIBUTE
306 * @see org.greenstone.gatherer.util.StaticStrings#FALSE_STR
307 * @see org.greenstone.gatherer.util.StaticStrings#TRUE_STR
308 */
309 public void setCustomArgument(boolean custom) {
310 if(element != null) {
311 element.setAttribute(StaticStrings.CUSTOM_ATTRIBUTE, (custom ? StaticStrings.TRUE_STR : StaticStrings.FALSE_STR));
312 }
313 }
314
315 /** Sets the value of default_value.
316 * @param default_value The new value for default_value as a <strong>String</strong>.
317 */
318 public void setDefaultValue(String default_value) {
319 this.default_value = default_value;
320 }
321
322 /** Set the value of desc.
323 * @param description the new value of desc as a String
324 */
325 public void setDescription(String description) {
326 this.description = description;
327 }
328
329 /** Set the element this argument should be based upon.
330 * @param element the Element
331 */
332 public void setElement(Element element) {
333 this.element = element;
334 }
335
336 /** Mark this argument as being hidden in GLI. */
337 public void setHiddenGLI() {
338 hidden_gli = true;
339 }
340
341 /** Set the upper bound for a range type argument.
342 * @param maximum the maximum as an int
343 */
344 public void setMaximum(int maximum) {
345 this.maximum = maximum;
346 }
347
348 /** Set the lower bound for a range type argument.
349 * @param minimum the minimum as an int
350 */
351 public void setMinimum(int minimum) {
352 this.minimum = minimum;
353 }
354
355 /** Set the detail mode level where this argument will become available.
356 * @param mode_level the mode level as an int
357 */
358 public void setModeLevel(int mode_level) {
359 this.mode_level = mode_level;
360 }
361
362 /** Set the value of name.
363 * @param name the new value of name as a String
364 */
365 public void setName(String name) {
366 this.name = name;
367 }
368
369 /** Sets the value of the options list.
370 * @param list the new options list as a HashMap
371 */
372 public void setOptions(HashMap list) {
373 this.list = list;
374 }
375
376 /** Set the owner of this argument.
377 * @param owner the name of the owner of this argument as a String
378 */
379 public void setOwner(String owner) {
380 this.owner = owner;
381 }
382
383 /** Set the value of required.
384 * @param required the new value of required as a boolean
385 */
386 public void setRequired(boolean required) {
387 this.required = required;
388 }
389
390 /** Set the value of type.
391 * @param type the new value of type as an byte
392 */
393 public void setType(byte type) {
394 this.type = type;
395 }
396
397 /** Set the value of type, by matching a type to the given string.
398 * @param new_type a String which contains the name of a certain argument type
399 * @see org.greenstone.gatherer.util.StaticStrings#ENUM_STR
400 * @see org.greenstone.gatherer.util.StaticStrings#FLAG_STR
401 * @see org.greenstone.gatherer.util.StaticStrings#HIERARCHY_STR
402 * @see org.greenstone.gatherer.util.StaticStrings#INT_STR
403 * @see org.greenstone.gatherer.util.StaticStrings#LANGUAGE_STR
404 * @see org.greenstone.gatherer.util.StaticStrings#METADATA_TYPE_STR
405 * @see org.greenstone.gatherer.util.StaticStrings#METADATUM_TYPE_STR
406 * @see org.greenstone.gatherer.util.StaticStrings#REGEXP_STR
407 */
408 public void setType(String new_type) {
409 if(new_type.equalsIgnoreCase(StaticStrings.ENUM_STR)) {
410 this.type = ENUM;
411 list = new HashMap();
412 }
413 else if(new_type.equalsIgnoreCase(StaticStrings.FLAG_STR)) {
414 this.type = FLAG;
415 }
416 else if(new_type.equalsIgnoreCase(StaticStrings.HIERARCHY_STR)) {
417 this.type = HIERARCHY;
418 }
419 else if(new_type.equalsIgnoreCase(StaticStrings.INT_STR)) {
420 this.type = INTEGER;
421 }
422 else if(new_type.equalsIgnoreCase(StaticStrings.LANGUAGE_STR)) {
423 this.type = LANGUAGE;
424 }
425 else if(new_type.equalsIgnoreCase(StaticStrings.METADATA_TYPE_STR)) {
426 this.type = METADATA;
427 }
428 else if(new_type.equalsIgnoreCase(StaticStrings.METADATUM_TYPE_STR)) {
429 this.type = METADATUM;
430 }
431 else if(new_type.equalsIgnoreCase(StaticStrings.REGEXP_STR)) {
432 this.type = REGEXP;
433 }
434 else {
435 this.type = STRING;
436 }
437 }
438
439 /** Method to set the value of this argument.
440 * @param value the new value for the argument
441 * @see org.greenstone.gatherer.Gatherer#println
442 */
443 public void setValue(String value) {
444 if(element != null) {
445 XMLTools.setValue(element, value);
446 }
447 else {
448 DebugStream.println("Argument.setValue(" + value + ") called on a base Argument.");
449 }
450 }
451
452 /** Set the values vector to the given values. Currently I just assign the new values, whereas I may later want to implement a deep clone.
453 * @param values an ArrayList of values
454 * @see org.greenstone.gatherer.Gatherer#println
455 */
456 public void setValues(ArrayList values) {
457 if(element != null) {
458 StringBuffer value = new StringBuffer();
459 int value_length = values.size();
460 for(int i = 0; i < value_length; i++) {
461 value.append(values.get(i));
462 value.append(StaticStrings.COMMA_CHARACTER);
463 }
464 value.deleteCharAt(value.length() - 1); // Remove last ','
465 XMLTools.setValue(element, value.toString());
466 }
467 else {
468 DebugStream.println("Argument.setValues([" + values.size() + " items]) called on a base Argument.");
469 }
470 }
471
472 /** Method for translating the data of this class into a string.
473 * @return a String containing a fragment of the total arguments string
474 * @see org.greenstone.gatherer.Gatherer#c_man
475 * @see org.greenstone.gatherer.collection.CollectionManager#getCollection
476 * @see org.greenstone.gatherer.util.StaticStrings#COMMA_CHARACTER
477 * @see org.greenstone.gatherer.util.StaticStrings#NAME_ATTRIBUTE
478 * @see org.greenstone.gatherer.util.StaticStrings#SPACE_CHARACTER
479 * @see org.greenstone.gatherer.util.StaticStrings#SPEECH_CHARACTER
480 */
481 public String toString()
482 {
483 StringBuffer text = new StringBuffer("-");
484
485 if (element == null) {
486 return text.toString();
487 }
488
489 if (name == null) {
490 name = element.getAttribute(StaticStrings.NAME_ATTRIBUTE);
491 }
492 text.append(name);
493
494 String value = XMLTools.getValue(element);
495 if (value.length() == 0) {
496 return text.toString();
497 }
498
499 text.append(StaticStrings.SPACE_CHARACTER);
500
501// // Handle metadata elements specially
502// if (type == METADATA || type == METADATUM) {
503// // Tokenize the string
504// StringTokenizer tokenizer = new StringTokenizer(value, ",");
505// while (tokenizer.hasMoreTokens()) {
506// String token = tokenizer.nextToken();
507
508// MetadataElement metadata_element = MetadataTools.getMetadataElementWithDisplayName(token);
509// if (metadata_element != null) {
510// text.append(metadata_element.getFullName());
511// }
512// else {
513// text.append(token);
514// }
515
516// if (tokenizer.hasMoreTokens()) {
517// text.append(StaticStrings.COMMA_CHARACTER);
518// }
519// }
520// return text.toString();
521// }
522
523 // If the value contains a space, add speech marks
524 // (Except for metadata elements, which won't have spaces when written out to collect.cfg)
525 if (value.indexOf(StaticStrings.SPACE_CHARACTER) != -1 && !(type == METADATUM || type == METADATA)) {
526 value = StaticStrings.SPEECH_CHARACTER + value + StaticStrings.SPEECH_CHARACTER;
527 }
528
529 text.append(value);
530 return text.toString();
531 }
532
533 /** parse the <Option> XML from eg import.pl -xml or pluginfo.pl -xml */
534 public void parseXML(Element option) {
535
536 for(Node node = option.getFirstChild(); node != null; node = node.getNextSibling()) {
537 String node_name = node.getNodeName();
538 if(node_name.equals("Name")) {
539 setName(XMLTools.getValue(node));
540 }
541 else if(node_name.equals("Desc")) {
542 setDescription(XMLTools.getValue(node));
543 }
544 else if(node_name.equals("Type")) {
545 setType(XMLTools.getValue(node));
546 }
547 else if(node_name.equals("Default")) {
548 setDefaultValue(XMLTools.getValue(node));
549 }
550 else if(node_name.equals("Required")) {
551 String v = XMLTools.getValue(node);
552 if(v != null && v.equals("yes")) {
553 setRequired(true);
554 }
555 }
556 else if(node_name.equals("List")) {
557 // Two final loops are required to parse lists.
558 for(Node value = node.getFirstChild(); value != null; value = value.getNextSibling()) {
559 if(value.getNodeName().equals("Value")) {
560 String key = null;
561 String desc = "";
562 for(Node subvalue = value.getFirstChild(); subvalue != null; subvalue = subvalue.getNextSibling()) {
563 node_name = subvalue.getNodeName();
564 if(node_name.equals("Name")) {
565 key = XMLTools.getValue(subvalue);
566 }
567 else if(node_name.equals("Desc")) {
568 desc = XMLTools.getValue(subvalue);
569 }
570 }
571 if(key != null) {
572 addOption(key, desc);
573 }
574 }
575 }
576 }
577 else if(node_name.equals("Range")) {
578 String range_raw = XMLTools.getValue(node);
579 int index = -1;
580 if((index = range_raw.indexOf(StaticStrings.COMMA_CHARACTER)) != -1) {
581 if(index > 0) {
582 try {
583 String first_number = range_raw.substring(0, index);
584 setMinimum(Integer.parseInt(first_number));
585 first_number = null;
586 }
587 catch(Exception exception) {
588 }
589 }
590
591 if(index + 1 < range_raw.length()) {
592 try {
593 String second_number = range_raw.substring(index + 1);
594 setMaximum(Integer.parseInt(second_number));
595 second_number = null;
596 }
597 catch(Exception exception) {
598 }
599 }
600 }
601 // Else it wasn't a valid range anyway, so ignore it
602 }
603 else if(node_name.equals("HiddenGLI")) {
604 setHiddenGLI();
605 }
606 else if(node_name.equals("ModeGLI")) {
607 String mode_level_str = XMLTools.getValue(node);
608 try {
609 int mode_level = Integer.parseInt(mode_level_str);
610 setModeLevel(mode_level);
611 }
612 catch(Exception exception) {
613 DebugStream.println("Exception in Argument.parseXML() - Unexpected but non-fatal");
614 DebugStream.printStackTrace(exception);
615 }
616 }
617
618 } // for each option
619
620 } // parseXML
621}
Note: See TracBrowser for help on using the repository browser.