View Javadoc

1   /* ValueConstraint
2    *
3    * $Id: Constraint.java 5387 2007-08-09 16:46:13Z gojomo $
4    *
5    * Created on Mar 29, 2004
6    *
7    * Copyright (C) 2004 Internet Archive.
8    *
9    * This file is part of the Heritrix web crawler (crawler.archive.org).
10   *
11   * Heritrix is free software; you can redistribute it and/or modify
12   * it under the terms of the GNU Lesser Public License as published by
13   * the Free Software Foundation; either version 2.1 of the License, or
14   * any later version.
15   *
16   * Heritrix is distributed in the hope that it will be useful,
17   * but WITHOUT ANY WARRANTY; without even the implied warranty of
18   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19   * GNU Lesser Public License for more details.
20   *
21   * You should have received a copy of the GNU Lesser Public License
22   * along with Heritrix; if not, write to the Free Software
23   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
24   */
25  package org.archive.crawler.settings;
26  
27  import java.io.Serializable;
28  import java.text.MessageFormat;
29  import java.util.ArrayList;
30  import java.util.logging.Level;
31  
32  
33  /***
34   * Superclass for constraints that can be set on attribute definitions.
35   * <p>
36   * Constraints will be checked against attribute values. If a constraint check
37   * fails, an object of type FailedCheck is returned containing information that
38   * can be used to build meaningful information to the user.
39   * <p>
40   * A constraint has one of three levels:
41   * <ul>
42   * <li>{@link java.util.logging.Level#SEVERE}The attribute could not be set
43   * whatsoever.
44   * <li>{@link java.util.logging.Level#WARNING}The attribute is illegal i
45   * CrawlJobs, but could be set in profiles. Mostly used as holder value for
46   * settings that should be changed for every entity running a crawl.
47   * <li>{@link java.util.logging.Level#INFO}The attribute has a legal value,
48   * but is outside the bounds of what are considered a reasonable value. The user
49   * could be warned that she should investigate if the value actally is what she
50   * wants it be.
51   * </ul>
52   *
53   * @author John Erik Halse
54   */
55  public abstract class Constraint 
56  implements Comparable<Constraint>, Serializable {
57      static final long serialVersionUID = -646814290764700497L;
58      
59      private final Level severity;
60      private final String msg;
61  
62      /*** Constructs a new Constraint.
63       *
64       * @param level the level for this constraint.
65       * @param msg default message to return if the check fails.
66       */
67      public Constraint(Level level, String msg) {
68          if (level != Level.SEVERE && level != Level.WARNING
69                  && level != Level.INFO) {
70              throw new IllegalArgumentException("Illegal level: "
71                      + level.getName());
72          }
73          this.severity = level;
74          this.msg = msg;
75      }
76  
77      /***
78       * Run the check.
79       *
80       * @param owner the ComplexType owning the attribute to check.
81       * @param definition the definition to check the attribute against.
82       * @param value the value to check.
83       * @return null if ok, or an instance of {@link FailedCheck}if the check
84       *         failed.
85       */
86      public final FailedCheck check(CrawlerSettings settings, ComplexType owner,
87              Type definition, Object value) {
88          return innerCheck(settings, owner, definition, value);
89      }
90  
91      /*** The method all subclasses should implement to do the actual checking.
92       *
93       * @param owner the ComplexType owning the attribute to check.
94       * @param definition the definition to check the attribute against.
95       * @param value the value to check.
96       * @return null if ok, or an instance of {@link FailedCheck}if the check
97       *         failed.
98       */
99      public abstract FailedCheck innerCheck(CrawlerSettings settings,
100             ComplexType owner, Type definition, Object value);
101 
102     /*** Get the default message to return if a check fails.
103      *
104      * @return the default message to return if a check fails.
105      */
106     protected String getDefaultMessage() {
107         return msg;
108     }
109 
110     /*** Objects of this class represents failed constraint checks.
111      *
112      * @author John Erik Halse
113      */
114     public class FailedCheck {
115         private final String msg;
116         private final CrawlerSettings settings;
117         private final ComplexType owner;
118         private final Type definition;
119         private final Object value;
120         protected final ArrayList<Object> messageArguments
121          = new ArrayList<Object>();
122 
123         /***
124          * Construct a new FailedCheck object.
125          *
126          * @param settings the CrawlerSettings object for which this check was
127          *            executed.
128          * @param owner the ComplexType owning the attribute to check.
129          * @param definition the definition to check the attribute against.
130          * @param value the value to check.
131          * @param msg a message describing what went wrong and possibly hints to
132          *            the user on how to fix it.
133          */
134         public FailedCheck(CrawlerSettings settings, ComplexType owner,
135                 Type definition, Object value, String msg) {
136             this.msg = msg;
137             this.settings = settings;
138             this.owner = owner;
139             this.definition = definition;
140             this.value = value;
141             this.messageArguments.add(definition.getName());
142             this.messageArguments.add(value);
143             this.messageArguments.add(owner.getName());
144         }
145 
146         /***
147          * Construct a new FailedCheck object using the constraints default
148          * message.
149          *
150          * @param settings the CrawlerSettings object for which this check was
151          *            executed.
152          * @param owner the ComplexType owning the attribute to check.
153          * @param definition the definition to check the attribute against.
154          * @param value the value to check.
155          */
156         public FailedCheck(CrawlerSettings settings, ComplexType owner,
157                 Type definition, Object value) {
158             this(settings, owner, definition, value, getDefaultMessage());
159         }
160 
161         /*** Get the error message.
162          *
163          * @return the error message.
164          */
165         public String getMessage() {
166             return MessageFormat.format(msg, messageArguments.toArray());
167         }
168 
169         /*** Get the severity level.
170          *
171          * @return the severity level.
172          */
173         public Level getLevel() {
174             return severity;
175         }
176 
177         /*** Get the definition for the checked attribute.
178          *
179          * @return the definition for the checked attribute.
180          */
181         public Type getDefinition() {
182             return definition;
183         }
184 
185         /*** Get the value of the checked attribute.
186          *
187          * @return the value of the checked attribute.
188          */
189         public Object getValue() {
190             return value;
191         }
192 
193         /*** Get the {@link ComplexType} owning the checked attribute.
194          *
195          * @return the {@link ComplexType} owning the checked attribute.
196          */
197         public ComplexType getOwner() {
198             return owner;
199         }
200 
201         /*** Get the {@link CrawlerSettings} for the checked attribute.
202          *
203          * @return the {@link CrawlerSettings} for the checked attribute.
204          */
205         public CrawlerSettings getSettings() {
206             return settings;
207         }
208 
209         /*** Returns a human readeable string for the failed check.
210          * Returns the same as {@link #getMessage()}
211          *
212          * @return A human readeable string for the failed check.
213          */
214         public String toString() {
215             return getMessage();
216         }
217     }
218 
219     /*** Compare this constraints level to another constraint.
220      * This method is implemented to let constraints be sorted with the highest
221      * level first.
222      *
223      * @param o a Constraint to compare to.
224      */
225     public int compareTo(Constraint o) {
226         Constraint c = (Constraint) o;
227         return c.severity.intValue() - severity.intValue();
228     }
229 
230 }