View Javadoc
1   /*
2    * Portions of this software was developed by employees of the National Institute
3    * of Standards and Technology (NIST), an agency of the Federal Government and is
4    * being made available as a public service. Pursuant to title 17 United States
5    * Code Section 105, works of NIST employees are not subject to copyright
6    * protection in the United States. This software may be subject to foreign
7    * copyright. Permission in the United States and in foreign countries, to the
8    * extent that NIST may hold copyright, to use, copy, modify, create derivative
9    * works, and distribute this software and its documentation without fee is hereby
10   * granted on a non-exclusive basis, provided that this notice and disclaimer
11   * of warranty appears in all copies.
12   *
13   * THE SOFTWARE IS PROVIDED 'AS IS' WITHOUT ANY WARRANTY OF ANY KIND, EITHER
14   * EXPRESSED, IMPLIED, OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, ANY WARRANTY
15   * THAT THE SOFTWARE WILL CONFORM TO SPECIFICATIONS, ANY IMPLIED WARRANTIES OF
16   * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, AND FREEDOM FROM
17   * INFRINGEMENT, AND ANY WARRANTY THAT THE DOCUMENTATION WILL CONFORM TO THE
18   * SOFTWARE, OR ANY WARRANTY THAT THE SOFTWARE WILL BE ERROR FREE.  IN NO EVENT
19   * SHALL NIST BE LIABLE FOR ANY DAMAGES, INCLUDING, BUT NOT LIMITED TO, DIRECT,
20   * INDIRECT, SPECIAL OR CONSEQUENTIAL DAMAGES, ARISING OUT OF, RESULTING FROM,
21   * OR IN ANY WAY CONNECTED WITH THIS SOFTWARE, WHETHER OR NOT BASED UPON WARRANTY,
22   * CONTRACT, TORT, OR OTHERWISE, WHETHER OR NOT INJURY WAS SUSTAINED BY PERSONS OR
23   * PROPERTY OR OTHERWISE, AND WHETHER OR NOT LOSS WAS SUSTAINED FROM, OR AROSE OUT
24   * OF THE RESULTS OF, OR USE OF, THE SOFTWARE OR SERVICES PROVIDED HEREUNDER.
25   */
26  
27  package gov.nist.secauto.metaschema.core.model.xml;
28  
29  import gov.nist.secauto.metaschema.core.datatype.IDataTypeAdapter;
30  import gov.nist.secauto.metaschema.core.datatype.adapter.MetaschemaDataTypeProvider;
31  import gov.nist.secauto.metaschema.core.datatype.markup.MarkupLine;
32  import gov.nist.secauto.metaschema.core.datatype.markup.MarkupMultiline;
33  import gov.nist.secauto.metaschema.core.model.AbstractFlagInstance;
34  import gov.nist.secauto.metaschema.core.model.IFeatureInlinedDefinition;
35  import gov.nist.secauto.metaschema.core.model.IFlagContainer;
36  import gov.nist.secauto.metaschema.core.model.IFlagDefinition;
37  import gov.nist.secauto.metaschema.core.model.IFlagInstance;
38  import gov.nist.secauto.metaschema.core.model.IModule;
39  import gov.nist.secauto.metaschema.core.model.MetaschemaModelConstants;
40  import gov.nist.secauto.metaschema.core.model.ModuleScopeEnum;
41  import gov.nist.secauto.metaschema.core.model.constraint.IConstraint.ExternalModelSource;
42  import gov.nist.secauto.metaschema.core.model.constraint.IValueConstrained;
43  import gov.nist.secauto.metaschema.core.model.xml.xmlbeans.InlineFlagDefinitionType;
44  import gov.nist.secauto.metaschema.core.util.CollectionUtil;
45  import gov.nist.secauto.metaschema.core.util.ObjectUtils;
46  
47  import java.util.Map;
48  import java.util.Set;
49  
50  import javax.xml.namespace.QName;
51  
52  import edu.umd.cs.findbugs.annotations.NonNull;
53  import edu.umd.cs.findbugs.annotations.Nullable;
54  import nl.talsmasoftware.lazy4j.Lazy;
55  
56  class XmlInlineFlagDefinition
57      extends AbstractFlagInstance {
58    @NonNull
59    private final InlineFlagDefinitionType xmlFlag;
60    @NonNull
61    private final InternalFlagDefinition flagDefinition;
62    private final Lazy<IValueConstrained> constraints;
63  
64    /**
65     * Constructs a new Metaschema flag definition from an XML representation bound
66     * to Java objects.
67     *
68     * @param xmlFlag
69     *          the XML representation bound to Java objects
70     * @param parent
71     *          the parent definition, which must be a definition type that can
72     *          contain flags.
73     */
74    public XmlInlineFlagDefinition(@NonNull InlineFlagDefinitionType xmlFlag, @NonNull IFlagContainer parent) {
75      super(parent);
76      this.xmlFlag = xmlFlag;
77      this.flagDefinition = new InternalFlagDefinition();
78      this.constraints = Lazy.lazy(() -> {
79        IValueConstrained retval;
80        if (getXmlFlag().isSetConstraint()) {
81          retval = new ValueConstraintSupport(
82              ObjectUtils.notNull(getXmlFlag().getConstraint()),
83              ExternalModelSource.instance(
84                  ObjectUtils.requireNonNull(getContainingModule().getLocation())));
85        } else {
86          retval = new ValueConstraintSupport();
87        }
88        return retval;
89      });
90    }
91  
92    @Override
93    public InternalFlagDefinition getDefinition() {
94      return flagDefinition;
95    }
96  
97    @Override
98    public IModule getContainingModule() {
99      return getContainingDefinition().getContainingModule();
100   }
101 
102   // ----------------------------------------
103   // - Start Annotation driven code - CPD-OFF
104   // ----------------------------------------
105 
106   /**
107    * Get the underlying XML model.
108    *
109    * @return the XML model
110    */
111   protected final InlineFlagDefinitionType getXmlFlag() {
112     return xmlFlag;
113   }
114 
115   @Override
116   public String getFormalName() {
117     return getXmlFlag().isSetFormalName() ? getXmlFlag().getFormalName() : null;
118   }
119 
120   @SuppressWarnings("null")
121   @Override
122   public MarkupLine getDescription() {
123     return getXmlFlag().isSetDescription() ? MarkupStringConverter.toMarkupString(getXmlFlag().getDescription())
124         : null;
125   }
126 
127   @Override
128   public Map<QName, Set<String>> getProperties() {
129     return ModelFactory.toProperties(CollectionUtil.listOrEmpty(getXmlFlag().getPropList()));
130   }
131 
132   @SuppressWarnings("null")
133   @Override
134   public String getName() {
135     return getXmlFlag().getName();
136   }
137 
138   @Override
139   public boolean isRequired() {
140     return getXmlFlag().isSetRequired() ? getXmlFlag().getRequired() : MetaschemaModelConstants.DEFAULT_FLAG_REQUIRED;
141   }
142 
143   @SuppressWarnings("null")
144   @Override
145   public MarkupMultiline getRemarks() {
146     return getXmlFlag().isSetRemarks() ? MarkupStringConverter.toMarkupString(getXmlFlag().getRemarks()) : null;
147   }
148 
149   // --------------------------------------
150   // - End Annotation driven code - CPD-ON
151   // --------------------------------------
152 
153   @Override
154   public String getUseName() {
155     // flags cannot use a use-name
156     return null;
157   }
158 
159   @Override
160   public Object getValue(@NonNull Object parentValue) {
161     // there is no value
162     return null;
163   }
164 
165   /**
166    * The corresponding definition for the local flag instance.
167    */
168   private final class InternalFlagDefinition
169       implements IFlagDefinition,
170       IFeatureInlinedDefinition<IFlagInstance> {
171     @Nullable
172     private final Object defaultValue;
173 
174     private InternalFlagDefinition() {
175       Object defaultValue = null;
176       if (getXmlFlag().isSetDefault()) {
177         defaultValue = getJavaTypeAdapter().parse(ObjectUtils.requireNonNull(getXmlFlag().getDefault()));
178       }
179       this.defaultValue = defaultValue;
180     }
181 
182     // ----------------------------------------
183     // - Start annotation driven code - CPD-OFF
184     // ----------------------------------------
185 
186     @SuppressWarnings("null")
187     @Override
188     public IDataTypeAdapter<?> getJavaTypeAdapter() {
189       return getXmlFlag().isSetAsType() ? getXmlFlag().getAsType() : MetaschemaDataTypeProvider.DEFAULT_DATA_TYPE;
190     }
191 
192     // --------------------------------------
193     // - End annotation driven code - CPD-ON
194     // --------------------------------------
195 
196     @Override
197     public Object getDefaultValue() {
198       return defaultValue;
199     }
200 
201     @Override
202     public boolean isInline() {
203       return true;
204     }
205 
206     @Override
207     @NonNull
208     public IFlagInstance getInlineInstance() {
209       return XmlInlineFlagDefinition.this;
210     }
211 
212     @Override
213     public String getName() {
214       return XmlInlineFlagDefinition.this.getName();
215     }
216 
217     @Override
218     public String getUseName() {
219       // always use the name
220       return null;
221     }
222 
223     @Override
224     public ModuleScopeEnum getModuleScope() {
225       return ModuleScopeEnum.LOCAL;
226     }
227 
228     @Override
229     public String getFormalName() {
230       return XmlInlineFlagDefinition.this.getFormalName();
231     }
232 
233     @Override
234     public MarkupLine getDescription() {
235       return XmlInlineFlagDefinition.this.getDescription();
236     }
237 
238     @Override
239     public Map<QName, Set<String>> getProperties() {
240       return XmlInlineFlagDefinition.this.getProperties();
241     }
242 
243     /**
244      * Used to generate the instances for the constraints in a lazy fashion when the
245      * constraints are first accessed.
246      */
247     @SuppressWarnings("null")
248     @Override
249     public IValueConstrained getConstraintSupport() {
250       return constraints.get();
251     }
252 
253     @Override
254     public MarkupMultiline getRemarks() {
255       return XmlInlineFlagDefinition.this.getRemarks();
256     }
257 
258     @Override
259     public IModule getContainingModule() {
260       return XmlInlineFlagDefinition.super.getContainingDefinition().getContainingModule();
261     }
262   }
263 }