1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package com.helger.schematron.pure.model;
18
19 import java.util.Map;
20
21 import javax.annotation.Nonnull;
22 import javax.annotation.Nullable;
23 import javax.annotation.concurrent.NotThreadSafe;
24
25 import com.helger.commons.ValueEnforcer;
26 import com.helger.commons.annotation.Nonempty;
27 import com.helger.commons.annotation.ReturnsMutableCopy;
28 import com.helger.commons.collection.CollectionHelper;
29 import com.helger.commons.collection.ext.CommonsArrayList;
30 import com.helger.commons.collection.ext.CommonsLinkedHashMap;
31 import com.helger.commons.collection.ext.ICommonsList;
32 import com.helger.commons.collection.ext.ICommonsOrderedMap;
33 import com.helger.commons.regex.RegExHelper;
34 import com.helger.commons.string.StringHelper;
35 import com.helger.commons.string.ToStringGenerator;
36 import com.helger.schematron.CSchematron;
37 import com.helger.schematron.CSchematronXML;
38 import com.helger.schematron.pure.errorhandler.IPSErrorHandler;
39 import com.helger.xml.microdom.IMicroElement;
40 import com.helger.xml.microdom.MicroElement;
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62 @NotThreadSafe
63 public class PSAssertReport implements
64 IPSElement,
65 IPSHasFlag,
66 IPSHasForeignElements,
67 IPSHasMixedContent,
68 IPSHasID,
69 IPSHasRichGroup,
70 IPSHasLinkableGroup
71 {
72 private final boolean m_bIsAssert;
73 private String m_sTest;
74 private String m_sFlag;
75 private String m_sID;
76 private ICommonsList <String> m_aDiagnostics;
77 private PSRichGroup m_aRich;
78 private PSLinkableGroup m_aLinkable;
79 private final ICommonsList <Object> m_aContent = new CommonsArrayList <> ();
80 private ICommonsOrderedMap <String, String> m_aForeignAttrs;
81 private ICommonsList <IMicroElement> m_aForeignElements;
82
83 public PSAssertReport (final boolean bIsAssert)
84 {
85 m_bIsAssert = bIsAssert;
86 }
87
88 public boolean isValid (@Nonnull final IPSErrorHandler aErrorHandler)
89 {
90 for (final Object aContent : m_aContent)
91 if (aContent instanceof IPSElement)
92 if (!((IPSElement) aContent).isValid (aErrorHandler))
93 return false;
94 if (StringHelper.hasNoText (m_sTest))
95 {
96 aErrorHandler.error (this, (m_bIsAssert ? "<assert>" : "<report>") + " has no 'test'");
97 return false;
98 }
99 return true;
100 }
101
102 public void validateCompletely (@Nonnull final IPSErrorHandler aErrorHandler)
103 {
104 for (final Object aContent : m_aContent)
105 if (aContent instanceof IPSElement)
106 ((IPSElement) aContent).validateCompletely (aErrorHandler);
107 if (StringHelper.hasNoText (m_sTest))
108 aErrorHandler.error (this, (m_bIsAssert ? "<assert>" : "<report>") + " has no 'test'");
109 }
110
111 public boolean isMinimal ()
112 {
113 if (!m_bIsAssert)
114 return false;
115 for (final Object aContent : m_aContent)
116 if (aContent instanceof IPSElement)
117 if (!((IPSElement) aContent).isMinimal ())
118 return false;
119 return true;
120 }
121
122 public void addForeignElement (@Nonnull final IMicroElement aForeignElement)
123 {
124 ValueEnforcer.notNull (aForeignElement, "ForeignElement");
125 if (aForeignElement.hasParent ())
126 throw new IllegalArgumentException ("ForeignElement already has a parent!");
127 if (m_aForeignElements == null)
128 m_aForeignElements = new CommonsArrayList <> ();
129 m_aForeignElements.add (aForeignElement);
130 }
131
132 public boolean hasForeignElements ()
133 {
134 return m_aForeignElements != null && m_aForeignElements.isNotEmpty ();
135 }
136
137 @Nonnull
138 @ReturnsMutableCopy
139 public ICommonsList <IMicroElement> getAllForeignElements ()
140 {
141 return new CommonsArrayList <> (m_aForeignElements);
142 }
143
144 public void addForeignAttribute (@Nonnull final String sAttrName, @Nonnull final String sAttrValue)
145 {
146 ValueEnforcer.notNull (sAttrName, "AttrName");
147 ValueEnforcer.notNull (sAttrValue, "AttrValue");
148 if (m_aForeignAttrs == null)
149 m_aForeignAttrs = new CommonsLinkedHashMap <> ();
150 m_aForeignAttrs.put (sAttrName, sAttrValue);
151 }
152
153 public boolean hasForeignAttributes ()
154 {
155 return m_aForeignAttrs != null && m_aForeignAttrs.isNotEmpty ();
156 }
157
158 @Nonnull
159 @ReturnsMutableCopy
160 public ICommonsOrderedMap <String, String> getAllForeignAttributes ()
161 {
162 return new CommonsLinkedHashMap <> (m_aForeignAttrs);
163 }
164
165 public boolean isAssert ()
166 {
167 return m_bIsAssert;
168 }
169
170 public boolean isReport ()
171 {
172 return !m_bIsAssert;
173 }
174
175 public void setTest (@Nullable final String sTest)
176 {
177 m_sTest = sTest;
178 }
179
180 @Nullable
181 public String getTest ()
182 {
183 return m_sTest;
184 }
185
186 public void setFlag (@Nullable final String sFlag)
187 {
188 m_sFlag = sFlag;
189 }
190
191 @Nullable
192 public String getFlag ()
193 {
194 return m_sFlag;
195 }
196
197 public void setID (@Nullable final String sID)
198 {
199 m_sID = sID;
200 }
201
202 @Nullable
203 public String getID ()
204 {
205 return m_sID;
206 }
207
208
209
210
211
212
213
214
215 public void setDiagnostics (@Nullable final String sDiagnostics)
216 {
217 if (StringHelper.hasText (sDiagnostics))
218 setDiagnostics (RegExHelper.getSplitToList (sDiagnostics.trim (), "\\s+"));
219 else
220 m_aDiagnostics = null;
221 }
222
223
224
225
226
227
228
229
230 public void setDiagnostics (@Nullable final ICommonsList <String> aDiagnostics)
231 {
232 m_aDiagnostics = aDiagnostics;
233 }
234
235
236
237
238 @Nonnull
239 @ReturnsMutableCopy
240 public ICommonsList <String> getAllDiagnostics ()
241 {
242
243 return new CommonsArrayList <> (m_aDiagnostics);
244 }
245
246 public void setRich (@Nullable final PSRichGroup aRich)
247 {
248 m_aRich = aRich;
249 }
250
251 @Nullable
252 public PSRichGroup getRich ()
253 {
254 return m_aRich;
255 }
256
257 public void setLinkable (@Nullable final PSLinkableGroup aLinkable)
258 {
259 m_aLinkable = aLinkable;
260 }
261
262 @Nullable
263 public PSLinkableGroup getLinkable ()
264 {
265 return m_aLinkable;
266 }
267
268 public void addText (@Nonnull @Nonempty final String sText)
269 {
270 ValueEnforcer.notEmpty (sText, "Text");
271 m_aContent.add (sText);
272 }
273
274 public boolean hasAnyText ()
275 {
276 return m_aContent.containsAny (e -> e instanceof String);
277 }
278
279 @Nonnull
280 @ReturnsMutableCopy
281 public ICommonsList <String> getAllTexts ()
282 {
283 return m_aContent.getAllInstanceOf (String.class);
284 }
285
286 public void addName (@Nonnull final PSName aName)
287 {
288 ValueEnforcer.notNull (aName, "Name");
289 m_aContent.add (aName);
290 }
291
292 @Nonnull
293 @ReturnsMutableCopy
294 public ICommonsList <PSName> getAllNames ()
295 {
296 return m_aContent.getAllInstanceOf (PSName.class);
297 }
298
299 public void addValueOf (@Nonnull final PSValueOf aValueOf)
300 {
301 ValueEnforcer.notNull (aValueOf, "ValueOf");
302 m_aContent.add (aValueOf);
303 }
304
305 @Nonnull
306 @ReturnsMutableCopy
307 public ICommonsList <PSValueOf> getAllValueOfs ()
308 {
309 return m_aContent.getAllInstanceOf (PSValueOf.class);
310 }
311
312 public void addEmph (@Nonnull final PSEmph aEmph)
313 {
314 ValueEnforcer.notNull (aEmph, "Emph");
315 m_aContent.add (aEmph);
316 }
317
318 @Nonnull
319 @ReturnsMutableCopy
320 public ICommonsList <PSEmph> getAllEmphs ()
321 {
322 return m_aContent.getAllInstanceOf (PSEmph.class);
323 }
324
325 public void addDir (@Nonnull final PSDir aDir)
326 {
327 ValueEnforcer.notNull (aDir, "Dir");
328 m_aContent.add (aDir);
329 }
330
331 @Nonnull
332 @ReturnsMutableCopy
333 public ICommonsList <PSDir> getAllDirs ()
334 {
335 return m_aContent.getAllInstanceOf (PSDir.class);
336 }
337
338 public void addSpan (@Nonnull final PSSpan aSpan)
339 {
340 ValueEnforcer.notNull (aSpan, "Span");
341 m_aContent.add (aSpan);
342 }
343
344 @Nonnull
345 @ReturnsMutableCopy
346 public ICommonsList <PSSpan> getAllSpans ()
347 {
348 return m_aContent.getAllInstanceOf (PSSpan.class);
349 }
350
351
352
353
354
355 @Nonnull
356 @ReturnsMutableCopy
357 public ICommonsList <Object> getAllContentElements ()
358 {
359 return m_aContent.getClone ();
360 }
361
362 @Nonnull
363 public IMicroElement getAsMicroElement ()
364 {
365 final IMicroElement ret = new MicroElement (CSchematron.NAMESPACE_SCHEMATRON,
366 m_bIsAssert ? CSchematronXML.ELEMENT_ASSERT
367 : CSchematronXML.ELEMENT_REPORT);
368 ret.setAttribute (CSchematronXML.ATTR_ID, m_sID);
369 ret.setAttribute (CSchematronXML.ATTR_FLAG, m_sFlag);
370 ret.setAttribute (CSchematronXML.ATTR_TEST, m_sTest);
371 if (CollectionHelper.isNotEmpty (m_aDiagnostics))
372 ret.setAttribute (CSchematronXML.ATTR_DIAGNOSTICS, StringHelper.getImploded (' ', m_aDiagnostics));
373 if (m_aRich != null)
374 m_aRich.fillMicroElement (ret);
375 if (m_aLinkable != null)
376 m_aLinkable.fillMicroElement (ret);
377 if (m_aForeignElements != null)
378 for (final IMicroElement aForeignElement : m_aForeignElements)
379 ret.appendChild (aForeignElement.getClone ());
380 for (final Object aContent : m_aContent)
381 if (aContent instanceof String)
382 ret.appendText ((String) aContent);
383 else
384 ret.appendChild (((IPSElement) aContent).getAsMicroElement ());
385 if (m_aForeignAttrs != null)
386 for (final Map.Entry <String, String> aEntry : m_aForeignAttrs.entrySet ())
387 ret.setAttribute (aEntry.getKey (), aEntry.getValue ());
388 return ret;
389 }
390
391 @Override
392 public String toString ()
393 {
394 return new ToStringGenerator (this).append ("isAssert", m_bIsAssert)
395 .appendIfNotNull ("test", m_sTest)
396 .appendIfNotNull ("flag", m_sFlag)
397 .appendIfNotNull ("id", m_sID)
398 .appendIfNotNull ("diagnostics", m_aDiagnostics)
399 .appendIfNotNull ("rich", m_aRich)
400 .appendIfNotNull ("linkable", m_aLinkable)
401 .appendIf ("content", m_aContent, CollectionHelper::isNotEmpty)
402 .appendIf ("foreignAttrs", m_aForeignAttrs, CollectionHelper::isNotEmpty)
403 .appendIf ("foreignElements", m_aForeignElements, CollectionHelper::isNotEmpty)
404 .getToString ();
405 }
406 }