View Javadoc

1   /*
2    AbstractOptionArgument.java
3    Creation date : 2/06/2010
4    Copyright © Benjamin Croizet (graffity2199@yahoo.fr)
5   
6    This program is free software; you can redistribute it and/or
7    modify it under the terms of the GNU General Public License
8    or GNU Lesser General Public License as published by the
9    Free Software Foundation; either version 3 of the License,
10   or (at your option) any later version.
11  
12   This program is distributed in the hope that it will be useful,
13   but WITHOUT ANY WARRANTY; without even the implied warranty of
14   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15   GNU General Public License for more details.
16  
17   You should have received copies of the GNU General Public License
18   and GNU Lesser General Public License along with this program;
19   if not, write to the Free Software Foundation, Inc.,
20   51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21   http://www.fsf.org/licensing/licenses/gpl.html
22   http://www.gnu.org/licenses/lgpl.html
23   */
24  
25  package net.sourceforge.plantumldependency.commoncli.option.argument;
26  
27  import static java.util.logging.Level.SEVERE;
28  import static java.util.logging.Logger.getLogger;
29  import static net.sourceforge.plantumldependency.common.constants.CharacterConstants.LEFT_BRACKET_CHAR;
30  import static net.sourceforge.plantumldependency.common.constants.CharacterConstants.RIGHT_BRACKET_CHAR;
31  import static net.sourceforge.plantumldependency.common.constants.CommonConstants.HASHCODE_PRIME_NUMBER1;
32  import static net.sourceforge.plantumldependency.common.constants.CommonConstants.HASHCODE_PRIME_NUMBER2;
33  import static net.sourceforge.plantumldependency.common.constants.log.ErrorConstants.UNEXPECTED_ERROR;
34  import static net.sourceforge.plantumldependency.common.utils.check.ParameterCheckerUtils.checkNull;
35  import static net.sourceforge.plantumldependency.common.utils.comparable.ComparableResult.AFTER;
36  import static net.sourceforge.plantumldependency.common.utils.comparable.ComparableResult.BEFORE;
37  import static net.sourceforge.plantumldependency.common.utils.comparable.ComparableResult.EQUAL;
38  import static net.sourceforge.plantumldependency.commoncli.constants.log.ErrorConstants.FULL_USAGE_DESCRIPTION_NULL_ERROR;
39  
40  import java.util.logging.Logger;
41  
42  /**
43   * The abstract implementation of the {@link OptionArgument} interface, providing common behaviors.
44   *
45   * @param <A>
46   *            the argument type to parse.
47   * @author Benjamin Croizet (<a href="mailto:graffity2199@yahoo.fr>graffity2199@yahoo.fr</a>)
48   * @since 1.3.0
49   * @version 1.3.0
50   */
51  public abstract class AbstractOptionArgument < A > implements OptionArgument < A > {
52  
53      /** The class logger. */
54      private static final transient Logger LOGGER = getLogger(AbstractOptionArgument.class.getName());
55  
56      /** Serial version UID. */
57      private static final long serialVersionUID = -9201749588723279692L;
58  
59      /** The boolean telling if the argument is mandatory or not. */
60      private boolean mandatory;
61  
62      /**
63       * The full argument usage description, explaining what the argument does (used for helping
64       * message).
65       */
66      private StringBuilder fullUsageDescription;
67  
68      /**
69       * Default constructor.
70       *
71       * @param optionArgumentIsMandatory
72       *            <code>true</code> if the argument is mandatory, <code>false</code> otherwise.
73       * @param fullArgumentDescription
74       *            the full argument usage description, explaining what the argument does (used for
75       *            helping message). <i>Note : a new {@link StringBuilder} is created.</i>
76       * @since 1.3.0
77       */
78      protected AbstractOptionArgument(final boolean optionArgumentIsMandatory,
79              final StringBuilder fullArgumentDescription) {
80          setMandatory(optionArgumentIsMandatory);
81          setFullUsageDescription(new StringBuilder(fullArgumentDescription));
82      }
83  
84      /**
85       * {@inheritDoc}
86       *
87       * @since 1.3.0
88       */
89      @Override
90      public int compareTo(final OptionArgument < A > o) {
91          final int comparison;
92  
93          if (this == o) {
94              comparison = EQUAL.getResult();
95          } else {
96              if (mandatory == o.isMandatory()) {
97                  comparison = fullUsageDescription.toString().compareTo(o.getFullUsageDescription().toString());
98              } else if (mandatory) {
99                  comparison = AFTER.getResult();
100             } else {
101                 comparison = BEFORE.getResult();
102             }
103         }
104 
105         return comparison;
106     }
107 
108     /**
109      * {@inheritDoc}
110      *
111      * @since 1.3.0
112      */
113     @Override
114     public OptionArgument < A > deepClone() {
115         AbstractOptionArgument < A > a = null;
116 
117         try {
118             a = (AbstractOptionArgument < A >) super.clone();
119             a.fullUsageDescription = new StringBuilder(getFullUsageDescription());
120         } catch (final CloneNotSupportedException cnse) {
121             LOGGER.log(SEVERE, UNEXPECTED_ERROR, cnse);
122         }
123 
124         return a;
125     }
126 
127     /**
128      * {@inheritDoc}
129      *
130      * @since 1.3.0
131      */
132     @Override
133     public boolean equals(final Object obj) {
134         if (this == obj) {
135             return true;
136         }
137         if (obj == null) {
138             return false;
139         }
140         if (getClass() != obj.getClass()) {
141             return false;
142         }
143         final AbstractOptionArgument < ? > other = (AbstractOptionArgument < ? >) obj;
144         if (fullUsageDescription == null) {
145             if (other.fullUsageDescription != null) {
146                 return false;
147             }
148         } else if (other.fullUsageDescription == null) {
149             return true;
150         } else if (!fullUsageDescription.toString().equals(other.fullUsageDescription.toString())) {
151             return false;
152         }
153         if (mandatory != other.mandatory) {
154             return false;
155         }
156         return true;
157     }
158 
159     /**
160      * {@inheritDoc}
161      *
162      * @since 1.3.0
163      */
164     @Override
165     public StringBuilder getFullUsageDescription() {
166         return fullUsageDescription;
167     }
168 
169     /**
170      * {@inheritDoc}
171      *
172      * @since 1.3.0
173      */
174     @Override
175     public StringBuilder getMainUsage() {
176         StringBuilder buffer = null;
177 
178         if (isMandatory()) {
179             buffer = new StringBuilder(getMainUsageDescription());
180         } else {
181             buffer = new StringBuilder(LEFT_BRACKET_CHAR);
182             buffer.append(getMainUsageDescription());
183             buffer.append(RIGHT_BRACKET_CHAR);
184         }
185 
186         return buffer;
187     }
188 
189     /**
190      * Get the main argument usage constant.
191      *
192      * @return the main argument usage constant, as a String.
193      * @since 1.3.0
194      */
195     protected abstract String getMainUsageDescription();
196 
197     /**
198      * {@inheritDoc}
199      *
200      * @since 1.3.0
201      */
202     @Override
203     public int hashCode() {
204         final int prime = 31;
205         int result = 1;
206         result = prime * result + ((fullUsageDescription == null) ? 0 : fullUsageDescription.toString().hashCode());
207         result = prime * result + (mandatory ? HASHCODE_PRIME_NUMBER1 : HASHCODE_PRIME_NUMBER2);
208         return result;
209     }
210 
211     /**
212      * {@inheritDoc}
213      *
214      * @since 1.3.0
215      */
216     @Override
217     public boolean isMandatory() {
218         return mandatory;
219     }
220 
221     /**
222      * Sets the value of <code>fullUsageDescription</code>.
223      *
224      * @param value
225      *            the <code>fullUsageDescription</code> to set, can be <code>null</code>.
226      * @see #getFullUsageDescription()
227      * @since 1.3.0
228      */
229     private void setFullUsageDescription(final StringBuilder value) {
230         checkNull(value, FULL_USAGE_DESCRIPTION_NULL_ERROR);
231 
232         fullUsageDescription = value;
233     }
234 
235     /**
236      * Sets the value of <code>mandatory</code>.
237      *
238      * @param value
239      *            the <code>mandatory</code> to set, can be <code>null</code>.
240      * @see #isMandatory()
241      * @since 1.3.0
242      */
243     private void setMandatory(final boolean value) {
244         mandatory = value;
245     }
246 
247     /**
248      * {@inheritDoc}
249      *
250      * @since 1.3.0
251      */
252     @Override
253     public String toString() {
254         return getClass().getSimpleName() + " [fullUsageDescription=" + fullUsageDescription + ", mandatory="
255                 + mandatory + "]";
256     }
257 }