View Javadoc

1   // Copyright 2006-2007, by the California Institute of Technology.
2   // ALL RIGHTS RESERVED. United States Government Sponsorship acknowledged.
3   // Any commercial use must be negotiated with the Office of Technology Transfer
4   // at the California Institute of Technology.
5   //
6   // This software is subject to U. S. export control laws and regulations
7   // (22 C.F.R. 120-130 and 15 C.F.R. 730-774). To the extent that the software
8   // is subject to U.S. export control laws and regulations, the recipient has
9   // the responsibility to obtain export licenses or other export authority as
10  // may be required before exporting such information to foreign countries or
11  // providing access to foreign nationals.
12  //
13  // $Id: ObjectValidator.java 2610 2007-04-19 15:36:49Z pramirez $ 
14  //
15  
16  package gov.nasa.pds.tools.label.validate;
17  
18  import gov.nasa.pds.tools.dict.Dictionary;
19  import gov.nasa.pds.tools.dict.ElementDefinition;
20  import gov.nasa.pds.tools.dict.ObjectDefinition;
21  import gov.nasa.pds.tools.dict.type.UnsupportedTypeException;
22  import gov.nasa.pds.tools.label.AttributeStatement;
23  import gov.nasa.pds.tools.label.ObjectStatement;
24  import gov.nasa.pds.tools.logging.ToolsLogRecord;
25  
26  import java.util.Collections;
27  import java.util.Iterator;
28  import java.util.List;
29  import java.util.logging.Level;
30  import java.util.logging.Logger;
31  
32  /***
33   * @author pramirez
34   * @version $Revision: 2610 $
35   * 
36   */
37  public class ObjectValidator {
38      private static Logger log = Logger.getLogger(ObjectValidator.class.getName());
39      
40      public static boolean isValid(Dictionary dictionary, ObjectStatement object) throws 
41         DefinitionNotFoundException {
42          boolean valid = true;
43          
44          //Find definition then validate
45          ObjectDefinition definition = dictionary.findObjectClassDefinition(object.getIdentifier());
46          if (definition == null)
47              throw new DefinitionNotFoundException("Could not find object definition for " +
48                      object.getIdentifier());
49          
50          //First check that required elements are captured in object
51          for (Iterator i = definition.getRequiredElements().iterator(); i.hasNext();) {
52              String required = (String) i.next();
53              //First check to see if attribute is found by its identifier or as a pointer
54              if (!object.hasAttribute(required) && !object.hasPointer(required)) {
55                  boolean foundAlias = false;
56                  //Next check to see if the attribute is present as an alias
57                  //Lookup definition for required element
58                  ElementDefinition elementDefinition = dictionary.getElementDefinition(required);
59                  //Now loop through aliases to see if the element appears
60                  for (Iterator a = elementDefinition.getAliases().iterator(); a.hasNext() && !foundAlias;) {
61                      //All element aliases take the form <object_identifier>.<element_identifier>
62                      String [] identifier = a.next().toString().split("//.");
63                      if (identifier[0].equals(definition.getIdentifier()) && object.hasAttribute(identifier[1]))
64                          foundAlias = true;
65                  }
66                  //Didn't find anything time to log
67                  if (!foundAlias) {
68                      valid = false;
69                      log.log(new ToolsLogRecord(Level.SEVERE, "Object " + object.getIdentifier() + 
70                              " does not contain required element " + required, object.getFilename(), 
71                              object.getContext(), object.getLineNumber()));
72                  }
73              }
74          }
75          
76          //Run through and validate all attributes
77          List attributes = object.getAttributes();
78          Collections.sort(attributes);
79          for (Iterator i = object.getAttributes().iterator(); i.hasNext();) {
80              AttributeStatement attribute = (AttributeStatement) i.next();
81              //Check to make sure element is allowed within this definition
82              if (!definition.isElementPossible(attribute.getIdentifier())) {
83                  //Next check to see if the attribute is allowed as an alias
84                  //Lookup definition for element by its alias
85                  ElementDefinition elementDefinition = dictionary.getElementDefinition(attribute.getIdentifier());
86                  if (elementDefinition == null || !definition.isElementPossible(elementDefinition.getIdentifier())) {
87                      valid = false;
88                      log.log(new ToolsLogRecord(Level.SEVERE, "Object " + object.getIdentifier() +  " contains the element " +
89                              attribute.getIdentifier() + " which is neither required nor optional.", attribute.getFilename(),
90                              attribute.getContext(), attribute.getLineNumber()));
91                  }
92              }
93              //Validate attribute
94              boolean elementValid = false;
95              try {
96                  elementValid = ElementValidator.isValid(dictionary, definition.getIdentifier(), attribute);
97              } catch (UnsupportedTypeException ute) {
98                  log.log(new ToolsLogRecord(Level.SEVERE, ute.getMessage(), attribute.getFilename(), 
99                          attribute.getContext(), attribute.getLineNumber()));
100             } catch (DefinitionNotFoundException dnfe) {
101                 log.log(new ToolsLogRecord(Level.SEVERE, dnfe.getMessage(), attribute.getFilename(), 
102                         attribute.getContext(), attribute.getLineNumber()));
103             }
104             if (!elementValid)
105                 valid = false;
106         }
107         
108         //Check to make sure that all required objects are present
109         for (Iterator i = definition.getRequiredObjects().iterator(); i.hasNext();) {
110             String required = (String) i.next();
111             //First see if object is present
112             if (!object.hasObject(required)) {
113                 boolean foundAlias = false;
114                 //Next check to see if the object is present as an alias
115                 //Lookup definition for required object
116                 ObjectDefinition objectDefinition = dictionary.getObjectDefinition(required);
117                 //Now loop through aliases to see if the object appears
118                 for (Iterator a = objectDefinition.getAliases().iterator(); a.hasNext() && !foundAlias;) {
119                     String alias = a.next().toString();
120                     if (object.hasObject(alias))
121                         foundAlias = true;
122                 }
123                 //Didn't find anything time to log
124                 if (!foundAlias) {
125                     valid = false;
126                     log.log(new ToolsLogRecord(Level.SEVERE, "Object " + object.getIdentifier() + 
127                             " does not contain required object " + required, object.getFilename(), 
128                             object.getContext(), object.getLineNumber()));
129                 }
130             }
131         }
132         
133         //Run through nested objects and check them
134         List objects = object.getObjects();
135         Collections.sort(objects);
136         for (Iterator i = objects.iterator(); i.hasNext();) {
137             ObjectStatement obj = (ObjectStatement) i.next();
138             //Check to make sure object is allowed within this definition
139             if (!definition.isObjectPossible(obj.getIdentifier())) {
140                 //Next check to see if the object is allowed as an alias
141                 //Lookup definition object by its alias
142                 ObjectDefinition objectDefinition = dictionary.getObjectDefinition(obj.getIdentifier());
143                 if (objectDefinition == null || !definition.isObjectPossible(objectDefinition.getIdentifier())) {
144                     valid = false;
145                     log.log(new ToolsLogRecord(Level.SEVERE, "Object " + object.getIdentifier() +  " contains the element " +
146                             obj.getIdentifier() + " which is neither required nor optional.", obj.getFilename(), 
147                             obj.getContext(), obj.getLineNumber()));
148                 }
149             }
150             //Validate nested object
151             boolean objValid = false;
152             try {
153                 objValid = ObjectValidator.isValid(dictionary, obj);
154             } catch (DefinitionNotFoundException dnfe) {
155                 log.log(new ToolsLogRecord(Level.SEVERE, dnfe.getMessage(), obj.getFilename(), 
156                         obj.getContext(), obj.getLineNumber()));
157             }
158             if (!objValid)
159                 valid = false;
160         }
161         
162         return valid;
163     }
164     
165 }