1 17 package org.eclipse.emf.ecore.util; 18 19 20 import java.util.ArrayList ; 21 import java.util.Collection ; 22 import java.util.HashMap ; 23 import java.util.Iterator ; 24 import java.util.List ; 25 import java.util.ListIterator ; 26 import java.util.Map ; 27 28 import java.math.BigDecimal ; 29 30 import org.eclipse.emf.common.util.BasicDiagnostic; 31 import org.eclipse.emf.common.util.Diagnostic; 32 import org.eclipse.emf.common.util.DiagnosticChain; 33 34 import org.eclipse.emf.ecore.EValidator; 35 36 import org.eclipse.emf.ecore.EAttribute; 37 import org.eclipse.emf.ecore.EObject; 38 import org.eclipse.emf.ecore.EClass; 39 import org.eclipse.emf.ecore.EcorePackage; 40 import org.eclipse.emf.ecore.EDataType; 41 import org.eclipse.emf.ecore.EPackage; 42 import org.eclipse.emf.ecore.EStructuralFeature; 43 44 import org.eclipse.emf.ecore.plugin.EcorePlugin; 45 46 import org.eclipse.emf.ecore.resource.Resource; 47 import org.eclipse.emf.ecore.resource.ResourceSet; 48 49 import org.eclipse.emf.ecore.xml.type.util.XMLTypeUtil; 50 51 52 55 public class EObjectValidator implements EValidator 56 { 57 public static final EObjectValidator INSTANCE = new EObjectValidator(); 58 59 public static final String DIAGNOSTIC_SOURCE = "org.eclipse.emf.ecore"; 60 61 public static final int EOBJECT__EVERY_MULTIPCITY_CONFORMS = 1; 62 public static final int EOBJECT__EVERY_DATA_VALUE_CONFORMS = 2; 63 public static final int EOBJECT__EVERY_REFERENCE_IS_CONTAINED = 3; 64 public static final int EOBJECT__EVERY_PROXY_RESOLVES = 4; 65 public static final int DATA_VALUE__VALUE_IN_RANGE = 5; 66 public static final int DATA_VALUE__LENGTH_IN_RANGE = 6; 67 public static final int DATA_VALUE__TYPE_CORRECT = 7; 68 public static final int DATA_VALUE__VALUE_IN_ENUMERATION = 8; 69 public static final int DATA_VALUE__MATCHES_PATTERN = 9; 70 public static final int DATA_VALUE__TOTAL_DIGITS_IN_RANGE = 10; 71 public static final int DATA_VALUE__FRACTION_DIGITS_IN_RANGE = 11; 72 73 76 public static String getObjectLabel(EObject eObject, Map context) 77 { 78 if (context != null) 79 { 80 SubstitutionLabelProvider substitutionlabelProvider = (SubstitutionLabelProvider)context.get(SubstitutionLabelProvider.class); 81 if (substitutionlabelProvider != null) 82 { 83 return substitutionlabelProvider.getObjectLabel(eObject); 84 } 85 } 86 return EcoreUtil.getIdentification(eObject); 87 } 88 89 92 public static String getFeatureLabel(EStructuralFeature eStructuralFeature, Map context) 93 { 94 if (context != null) 95 { 96 SubstitutionLabelProvider substitutionlabelProvider = (SubstitutionLabelProvider)context.get(SubstitutionLabelProvider.class); 97 if (substitutionlabelProvider != null) 98 { 99 return substitutionlabelProvider.getFeatureLabel(eStructuralFeature); 100 } 101 } 102 return eStructuralFeature.getName(); 103 } 104 105 108 public static String getValueLabel(EDataType eDataType, Object value, Map context) 109 { 110 if (context != null) 111 { 112 SubstitutionLabelProvider substitutionlabelProvider = (SubstitutionLabelProvider)context.get(SubstitutionLabelProvider.class); 113 if (substitutionlabelProvider != null) 114 { 115 return substitutionlabelProvider.getValueLabel(eDataType, value); 116 } 117 } 118 return EcoreUtil.convertToString(eDataType, value); 119 } 120 121 public EObjectValidator() 122 { 123 } 124 125 protected EPackage getEPackage() 126 { 127 return EcorePackage.eINSTANCE; 128 } 129 130 protected EValidator getRootEValidator(Map context) 131 { 132 if (context != null) 133 { 134 EValidator result = (EValidator)context.get(EValidator.class); 135 if (result != null) 136 { 137 return result; 138 } 139 } 140 141 return Diagnostician.INSTANCE; 142 } 143 144 150 public boolean validate(EObject eObject, DiagnosticChain diagnostics, Map context) 151 { 152 return validate(eObject.eClass(), eObject, diagnostics, context); 153 } 154 155 public boolean validate(EClass eClass, EObject eObject, DiagnosticChain diagnostics, Map context) 156 { 157 if (eClass.eContainer() == getEPackage()) 158 { 159 return validate(eClass.getClassifierID(), eObject, diagnostics, context); 160 } 161 else 162 { 163 List eSuperTypes = eClass.getESuperTypes(); 164 return 165 eSuperTypes.isEmpty() ? 166 validate_EveryDefaultConstraint(eObject, diagnostics, context) : 167 validate((EClass)eSuperTypes.get(0), eObject, diagnostics, context); 168 } 169 } 170 171 protected boolean validate(int classifierID, Object object, DiagnosticChain diagnostics, Map context) 172 { 173 return classifierID != EcorePackage.EOBJECT || validate_EveryDefaultConstraint((EObject)object, diagnostics, context); 174 } 175 176 public boolean validate_EveryDefaultConstraint(EObject object, DiagnosticChain theDiagnostics, Map context) 177 { 178 boolean result = validate_EveryMultiplicityConforms(object, theDiagnostics, context); 179 if (result || theDiagnostics != null) 180 { 181 result &= validate_EveryProxyResolves(object, theDiagnostics, context); 182 } 183 if (result || theDiagnostics != null) 184 { 185 result &= validate_EveryReferenceIsContained(object, theDiagnostics, context); 186 } 187 if (result || theDiagnostics != null) 188 { 189 result &= validate_EveryDataValueConforms(object, theDiagnostics, context); 190 } 191 return result; 192 } 193 194 public boolean validate_EveryMultiplicityConforms(EObject eObject, DiagnosticChain diagnostics, Map context) 195 { 196 boolean result = true; 197 EClass eClass = eObject.eClass(); 198 for (int i = 0, size = eClass.getFeatureCount(); i < size; ++i) 199 { 200 result &= validate_MultiplicityConforms(eObject, eClass.getEStructuralFeature(i), diagnostics, context); 201 if (!result && diagnostics == null) 202 { 203 return false; 204 } 205 } 206 return result; 207 } 208 209 protected boolean validate_MultiplicityConforms 210 (EObject eObject, EStructuralFeature eStructuralFeature, DiagnosticChain diagnostics, Map context) 211 { 212 boolean result = true; 213 if (eStructuralFeature.isMany()) 214 { 215 int lowerBound = eStructuralFeature.getLowerBound(); 216 if (lowerBound > 0) 217 { 218 int size = ((List )eObject.eGet(eStructuralFeature)).size(); 219 if (size < lowerBound) 220 { 221 result = false; 222 if (diagnostics != null) 223 { 224 diagnostics.add 225 (new BasicDiagnostic 226 (Diagnostic.ERROR, 227 DIAGNOSTIC_SOURCE, 228 EOBJECT__EVERY_MULTIPCITY_CONFORMS, 229 EcorePlugin.INSTANCE.getString 230 ("_UI_FeatureHasTooFewValues_diagnostic", 231 new Object [] 232 { 233 getFeatureLabel(eStructuralFeature, context), 234 getObjectLabel(eObject, context), 235 new Integer (size), 236 new Integer (lowerBound) 237 }), 238 new Object [] { eObject, eStructuralFeature })); 239 } 240 } 241 int upperBound = eStructuralFeature.getUpperBound(); 242 if (upperBound > 0 && size > upperBound) 243 { 244 result = false; 245 if (diagnostics != null) 246 { 247 diagnostics.add 248 (new BasicDiagnostic 249 (Diagnostic.ERROR, 250 DIAGNOSTIC_SOURCE, 251 EOBJECT__EVERY_MULTIPCITY_CONFORMS, 252 EcorePlugin.INSTANCE.getString 253 ("_UI_FeatureHasTooManyValues_diagnostic", 254 new Object [] 255 { 256 getFeatureLabel(eStructuralFeature, context), 257 getObjectLabel(eObject, context), 258 new Integer (size), 259 new Integer (upperBound) 260 }), 261 new Object [] { eObject, eStructuralFeature })); 262 } 263 } 264 } 265 else 266 { 267 int upperBound = eStructuralFeature.getUpperBound(); 268 if (upperBound > 0) 269 { 270 int size = ((List )eObject.eGet(eStructuralFeature)).size(); 271 if (size > upperBound) 272 { 273 result = false; 274 if (diagnostics != null) 275 { 276 diagnostics.add 277 (new BasicDiagnostic 278 (Diagnostic.ERROR, 279 DIAGNOSTIC_SOURCE, 280 EOBJECT__EVERY_MULTIPCITY_CONFORMS, 281 EcorePlugin.INSTANCE.getString 282 ("_UI_FeatureHasTooManyValues_diagnostic", 283 new Object [] 284 { 285 getFeatureLabel(eStructuralFeature, context), 286 getObjectLabel(eObject, context), 287 new Integer (size), 288 new Integer (upperBound) 289 }), 290 new Object [] { eObject, eStructuralFeature })); 291 } 292 } 293 } 294 } 295 } 296 else if (eStructuralFeature.isRequired()) 297 { 298 if (!eObject.eIsSet(eStructuralFeature)) 299 { 300 result = false; 301 if (diagnostics != null) 302 { 303 diagnostics.add 304 (new BasicDiagnostic 305 (Diagnostic.ERROR, 306 DIAGNOSTIC_SOURCE, 307 EOBJECT__EVERY_MULTIPCITY_CONFORMS, 308 EcorePlugin.INSTANCE.getString 309 ("_UI_RequiredFeatureMustBeSet_diagnostic", 310 new Object [] { getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context) }), 311 new Object [] { eObject, eStructuralFeature })); 312 } 313 } 314 } 315 316 return result; 317 } 318 319 public boolean validate_EveryProxyResolves(EObject eObject, DiagnosticChain diagnostics, Map context) 320 { 321 boolean result = true; 322 for (EContentsEList.FeatureIterator i = (EContentsEList.FeatureIterator)eObject.eCrossReferences().iterator(); i.hasNext(); ) 323 { 324 EObject eCrossReferenceObject = (EObject)i.next(); 325 if (eCrossReferenceObject.eIsProxy()) 326 { 327 result = false; 328 if (diagnostics != null) 329 { 330 diagnostics.add 331 (new BasicDiagnostic 332 (Diagnostic.ERROR, 333 DIAGNOSTIC_SOURCE, 334 EOBJECT__EVERY_PROXY_RESOLVES, 335 EcorePlugin.INSTANCE.getString 336 ("_UI_UnresolvedProxy_diagnostic", 337 new Object [] 338 { 339 getFeatureLabel(i.feature(), context), 340 getObjectLabel(eObject, context), 341 getObjectLabel(eCrossReferenceObject, context) 342 }), 343 new Object [] { eObject, i.feature(), eCrossReferenceObject })); 344 } 345 else 346 { 347 break; 348 } 349 } 350 } 351 return result; 352 } 353 354 public boolean validate_EveryReferenceIsContained(EObject eObject, DiagnosticChain diagnostics, Map context) 355 { 356 boolean result = true; 357 for (EContentsEList.FeatureIterator i = (EContentsEList.FeatureIterator)eObject.eCrossReferences().iterator(); i.hasNext(); ) 358 { 359 EObject eCrossReferenceObject = (EObject)i.next(); 360 if (eCrossReferenceObject.eResource() == null && !eCrossReferenceObject.eIsProxy() && !i.feature().isTransient()) 361 { 362 result = false; 363 if (diagnostics != null) 364 { 365 diagnostics.add 366 (new BasicDiagnostic 367 (Diagnostic.ERROR, 368 DIAGNOSTIC_SOURCE, 369 EOBJECT__EVERY_REFERENCE_IS_CONTAINED, 370 EcorePlugin.INSTANCE.getString 371 ("_UI_DanglingReference_diagnostic", 372 new Object [] 373 { 374 getFeatureLabel(i.feature(), context), 375 getObjectLabel(eObject, context), 376 getObjectLabel(eCrossReferenceObject, context) 377 }), 378 new Object [] { eObject, i.feature(), eCrossReferenceObject })); 379 } 380 else 381 { 382 break; 383 } 384 } 385 } 386 return result; 387 } 388 389 public boolean validate_EveryDataValueConforms(EObject eObject, DiagnosticChain diagnostics, Map context) 390 { 391 boolean result = true; 392 for (Iterator i = eObject.eClass().getEAllAttributes().iterator(); i.hasNext(); ) 393 { 394 result &= validate_DataValueConforms(eObject, (EAttribute)i.next(), diagnostics, context); 395 if (!result && diagnostics == null) 396 { 397 return false; 398 } 399 } 400 return result; 401 } 402 403 protected boolean validate_DataValueConforms 404 (EObject eObject, EAttribute eAttribute, DiagnosticChain diagnostics, Map context) 405 { 406 if (!eObject.eIsSet(eAttribute)) 407 { 408 return true; 409 } 410 boolean result = true; 411 EDataType eDataType = eAttribute.getEAttributeType(); 412 EValidator rootValidator = getRootEValidator(context); 413 Object value = eObject.eGet(eAttribute); 414 if (FeatureMapUtil.isFeatureMap(eAttribute)) 415 { 416 Collection featureMap = (Collection )value; 417 EClass eClass = eObject.eClass(); 418 Map entryFeatureToDiagnosticChainMap = null; 419 for (Iterator i = featureMap.iterator(); i.hasNext() && (result || diagnostics != null); ) 420 { 421 FeatureMap.Entry entry = (FeatureMap.Entry)i.next(); 422 EStructuralFeature entryFeature = entry.getEStructuralFeature(); 423 if (entryFeature instanceof EAttribute && 424 ExtendedMetaData.INSTANCE.getAffiliation(eClass, entryFeature) == eAttribute) 425 { 426 EDataType entryType = (EDataType)entryFeature.getEType(); 427 Object entryValue = entry.getValue(); 428 boolean entryIsValid = rootValidator.validate(entryType, entryValue, null, context); 429 if (!entryIsValid) 430 { 431 result = false; 432 if (diagnostics != null) 433 { 434 if (entryFeatureToDiagnosticChainMap == null) 435 { 436 entryFeatureToDiagnosticChainMap = new HashMap (); 437 } 438 DiagnosticChain entryFeatureDiagnostic = (DiagnosticChain)entryFeatureToDiagnosticChainMap.get(entryFeature); 439 if (entryFeatureDiagnostic == null) 440 { 441 entryFeatureDiagnostic = createBadDataValueDiagnostic(eObject, (EAttribute)entryFeature, diagnostics, context); 442 entryFeatureToDiagnosticChainMap.put(entryFeature, entryFeatureDiagnostic); 443 } 444 rootValidator.validate(entryType, entryValue, entryFeatureDiagnostic, context); 445 } 446 } 447 } 448 } 449 } 450 else if (eAttribute.isMany()) 451 { 452 for (Iterator i = ((List )value).iterator(); i.hasNext() && result; ) 453 { 454 result &= rootValidator.validate(eDataType, i.next(), null, context); 455 } 456 457 if (!result && diagnostics != null) 458 { 459 DiagnosticChain diagnostic = createBadDataValueDiagnostic(eObject, eAttribute, diagnostics, context); 460 for (Iterator i = ((List )value).iterator(); i.hasNext(); ) 461 { 462 rootValidator.validate(eDataType, i.next(), diagnostic, context); 463 } 464 } 465 } 466 else if (value != null) 467 { 468 result = rootValidator.validate(eDataType, value, null, context); 469 if (!result && diagnostics != null) 470 { 471 DiagnosticChain diagnostic = createBadDataValueDiagnostic(eObject, eAttribute, diagnostics, context); 472 rootValidator.validate(eDataType, value, diagnostic, context); 473 } 474 } 475 476 return result; 477 } 478 479 protected DiagnosticChain createBadDataValueDiagnostic 480 (EObject eObject, EAttribute eAttribute, DiagnosticChain diagnostics, Map context) 481 { 482 BasicDiagnostic diagnostic = 483 new BasicDiagnostic 484 (Diagnostic.ERROR, 485 DIAGNOSTIC_SOURCE, 486 EOBJECT__EVERY_DATA_VALUE_CONFORMS, 487 EcorePlugin.INSTANCE.getString 488 ("_UI_BadDataValue_diagnostic", 489 new Object [] 490 { 491 getFeatureLabel(eAttribute, context), 492 getObjectLabel(eObject, context) 493 }), 494 new Object [] { eObject, eAttribute }); 495 diagnostics.add(diagnostic); 496 return diagnostic; 497 } 498 499 protected boolean validatePattern 500 (EDataType eDataType, Object value, PatternMatcher [][] patterns, DiagnosticChain diagnostics, Map context) 501 { 502 String literal = EcoreUtil.convertToString(eDataType, value); 503 for (int i = 0; i < patterns.length; ++i) 504 { 505 PatternMatcher [] children = patterns[i]; 506 boolean matches = false; 507 for (int j = 0; j < children.length; ++j) 508 { 509 if (children[j].matches(literal)) 510 { 511 matches = true; 512 break; 513 } 514 } 515 if (!matches) 516 { 517 if (diagnostics != null) 518 { 519 reportDataValuePatternViolation(eDataType, value, children, diagnostics, context); 520 } 521 return false; 522 } 523 } 524 return true; 525 } 526 527 public class DynamicEDataTypeValidator 528 { 529 protected List effectiveEnumeration; 530 protected PatternMatcher [][] effectivePattern; 531 protected int effectiveTotalDigits = -1; 532 protected int effectiveFractionDigits = -1; 533 protected int effectiveMinLength = -1; 534 protected int effectiveMaxLength = -1; 535 protected Object effectiveMin; 536 protected boolean effectiveMinIsInclusive; 537 protected int effectiveTotalDigitsMin = -1; 538 protected Object effectiveMax; 539 protected boolean effectiveMaxIsInclusive; 540 protected int effectiveTotalDigitsMax = -1; 541 protected EDataType itemType; 542 protected List memberTypes; 543 544 public DynamicEDataTypeValidator(EDataType eDataType) 545 { 546 ExtendedMetaData extendedMetaData = ExtendedMetaData.INSTANCE; 547 Resource resource = eDataType.eResource(); 548 if (resource != null) 549 { 550 ResourceSet resourceSet = resource.getResourceSet(); 551 if (resourceSet != null) 552 { 553 extendedMetaData = new BasicExtendedMetaData(resourceSet.getPackageRegistry()); 554 } 555 } 556 557 List patterns = null; 558 559 for (;;) 560 { 561 if (effectiveEnumeration == null) 562 { 563 List enumeration = extendedMetaData.getEnumerationFacet(eDataType); 564 if (!enumeration.isEmpty()) 565 { 566 effectiveEnumeration = new ArrayList (); 567 for (Iterator i = enumeration.iterator(); i.hasNext(); ) 568 { 569 effectiveEnumeration.add(EcoreUtil.createFromString(eDataType, (String )i.next())); 570 } 571 } 572 } 573 574 List pattern = extendedMetaData.getPatternFacet(eDataType); 575 if (!pattern.isEmpty()) 576 { 577 if (patterns == null) 578 { 579 patterns = new ArrayList (); 580 } 581 PatternMatcher [] children = new PatternMatcher [pattern.size()]; 582 patterns.add(children); 583 for (ListIterator i = pattern.listIterator(); i.hasNext(); ) 584 { 585 PatternMatcher patternMatcher = XMLTypeUtil.createPatternMatcher((String )i.next()); 586 children[i.previousIndex()] = patternMatcher; 587 } 588 } 589 590 if (effectiveTotalDigits == -1) 591 { 592 effectiveTotalDigits = extendedMetaData.getTotalDigitsFacet(eDataType); 593 } 594 if (effectiveFractionDigits == -1) 595 { 596 effectiveFractionDigits = extendedMetaData.getFractionDigitsFacet(eDataType); 597 } 598 if (effectiveMinLength == -1) 599 { 600 effectiveMinLength = extendedMetaData.getLengthFacet(eDataType); 601 if (effectiveMinLength == -1) 602 { 603 effectiveMinLength = extendedMetaData.getMinLengthFacet(eDataType); 604 } 605 } 606 if (effectiveMaxLength == -1) 607 { 608 effectiveMaxLength = extendedMetaData.getLengthFacet(eDataType); 609 if (effectiveMaxLength == -1) 610 { 611 effectiveMaxLength = extendedMetaData.getMaxLengthFacet(eDataType); 612 } 613 } 614 if (effectiveMin == null) 615 { 616 effectiveMin = extendedMetaData.getMinExclusiveFacet(eDataType); 617 if (effectiveMin == null) 618 { 619 effectiveMin = extendedMetaData.getMinInclusiveFacet(eDataType); 620 if (effectiveMin != null) 621 { 622 effectiveMin = EcoreUtil.createFromString(eDataType, (String )effectiveMin); 623 effectiveMinIsInclusive = true; 624 } 625 } 626 else 627 { 628 effectiveMin = EcoreUtil.createFromString(eDataType, (String )effectiveMin); 629 effectiveMinIsInclusive = false; 630 } 631 } 632 if (effectiveMax == null) 633 { 634 effectiveMax = extendedMetaData.getMaxExclusiveFacet(eDataType); 635 if (effectiveMax == null) 636 { 637 effectiveMax = extendedMetaData.getMaxInclusiveFacet(eDataType); 638 if (effectiveMax != null) 639 { 640 effectiveMax = EcoreUtil.createFromString(eDataType, (String )effectiveMax); 641 effectiveMaxIsInclusive = true; 642 } 643 } 644 else 645 { 646 effectiveMax = EcoreUtil.createFromString(eDataType, (String )effectiveMax); 647 effectiveMaxIsInclusive = false; 648 } 649 } 650 651 EDataType baseType = extendedMetaData.getBaseType(eDataType); 652 if (baseType != null) 653 { 654 eDataType = baseType; 655 continue; 656 } 657 else 658 { 659 itemType = extendedMetaData.getItemType(eDataType); 660 memberTypes = extendedMetaData.getMemberTypes(eDataType); 661 break; 662 } 663 } 664 665 if (patterns != null) 666 { 667 effectivePattern = new PatternMatcher [patterns.size()][]; 668 patterns.toArray(effectivePattern); 669 } 670 671 if (effectiveTotalDigits != -1 && eDataType.getInstanceClassName() != "java.math.BigDecimal") 672 { 673 StringBuffer digits = new StringBuffer ("1"); 674 for (int i = effectiveTotalDigits; i > 0; --i) 675 { 676 digits.append("0"); 677 } 678 Object upperBound = EcoreUtil.createFromString(eDataType, digits.toString()); 679 Object lowerBound = EcoreUtil.createFromString(eDataType, "-" + digits.toString()); 680 681 if (effectiveMin == null || 682 (effectiveMinIsInclusive ? 683 ((Comparable )effectiveMin).compareTo(lowerBound) <= 0: 684 ((Comparable )effectiveMin).compareTo(lowerBound) < 0)) 685 { 686 effectiveMinIsInclusive = false; 687 effectiveMin = lowerBound; 688 effectiveTotalDigitsMin = effectiveTotalDigits; 689 } 690 691 if (effectiveMax == null || 692 (effectiveMaxIsInclusive ? 693 ((Comparable )effectiveMax).compareTo(upperBound) >= 0: 694 ((Comparable )effectiveMax).compareTo(upperBound) > 0)) 695 { 696 effectiveMaxIsInclusive = false; 697 effectiveMax = upperBound; 698 effectiveTotalDigitsMax = effectiveTotalDigits; 699 } 700 effectiveTotalDigits = -1; 701 } 702 703 if (effectiveFractionDigits != -1 && eDataType.getInstanceClassName() != "java.math.BigDecimal") 704 { 705 effectiveFractionDigits = -1; 706 } 707 } 708 709 public boolean validate(EDataType eDataType, Object value, DiagnosticChain diagnostics, Map context) 710 { 711 boolean result = true; 712 if (effectiveEnumeration != null) 713 { 714 if (!effectiveEnumeration.contains(value)) 715 { 716 if (diagnostics != null) reportEnumerationViolation(eDataType, value, effectiveEnumeration, diagnostics, context); 717 result = false; 718 } 719 } 720 721 if (effectivePattern != null) 722 { 723 result = validatePattern(eDataType, value, effectivePattern, diagnostics, context); 724 } 725 726 if (effectiveMin != null) 727 { 728 if (effectiveMinIsInclusive ? 729 ((Comparable )effectiveMin).compareTo(value) > 0: 730 ((Comparable )effectiveMin).compareTo(value) >= 0) 731 { 732 if (diagnostics != null) 733 { 734 if (effectiveTotalDigitsMin != -1) 735 { 736 reportTotalDigitsViolation(eDataType, value, effectiveTotalDigitsMin, diagnostics, context); 737 } 738 else 739 { 740 reportMinViolation(eDataType, value, effectiveMin, effectiveMinIsInclusive, diagnostics, context); 741 } 742 } 743 result = false; 744 } 745 } 746 747 if (effectiveMax != null) 748 { 749 if (effectiveMaxIsInclusive ? 750 ((Comparable )effectiveMax).compareTo(value) < 0: 751 ((Comparable )effectiveMax).compareTo(value) <= 0) 752 { 753 if (diagnostics != null) 754 { 755 if (effectiveTotalDigitsMax != -1) 756 { 757 reportTotalDigitsViolation(eDataType, value, effectiveTotalDigitsMax, diagnostics, context); 758 } 759 else 760 { 761 reportMaxViolation(eDataType, value, effectiveMax, effectiveMaxIsInclusive, diagnostics, context); 762 } 763 } 764 result = false; 765 } 766 } 767 768 if (effectiveMinLength != -1) 769 { 770 int length = 771 value instanceof String ? 772 ((String )value).length() : 773 value instanceof Object [] ? 774 ((Object [])value).length : 775 ((Collection )value).size(); 776 if (length < effectiveMinLength) 777 { 778 if (diagnostics != null) reportMinLengthViolation(eDataType, value, length, effectiveMinLength, diagnostics, context); 779 result = false; 780 } 781 } 782 783 if (effectiveMaxLength != -1) 784 { 785 int length = 786 value instanceof String ? 787 ((String )value).length() : 788 value instanceof Object [] ? 789 ((Object [])value).length : 790 ((Collection )value).size(); 791 if (length > effectiveMaxLength) 792 { 793 if (diagnostics != null) reportMaxLengthViolation(eDataType, value, length, effectiveMaxLength, diagnostics, context); 794 result = false; 795 } 796 } 797 798 if (effectiveTotalDigits != -1) 799 { 800 if (value instanceof BigDecimal && ((BigDecimal )value).unscaledValue().abs().toString().length() > effectiveTotalDigits) 801 { 802 if (diagnostics != null) reportTotalDigitsViolation(eDataType, value, effectiveTotalDigits, diagnostics, context); 803 result = false; 804 } 805 } 806 807 if (effectiveFractionDigits != -1) 808 { 809 if (value instanceof BigDecimal && ((BigDecimal )value).scale() > effectiveFractionDigits) 810 { 811 if (diagnostics != null) reportFractionDigitsViolation(eDataType, value, effectiveFractionDigits, diagnostics, context); 812 result = false; 813 } 814 } 815 816 if (itemType != null) 817 { 818 EValidator rootValidator = getRootEValidator(context); 819 for (Iterator i = ((List )value).iterator(); i.hasNext() && (result || diagnostics != null); ) 820 { 821 result &= rootValidator.validate(itemType, i.next(), diagnostics, context); 822 } 823 return result; 824 } 825 else if (!memberTypes.isEmpty()) 826 { 827 EValidator rootValidator = getRootEValidator(context); 828 for (Iterator i = memberTypes.iterator(); i.hasNext(); ) 829 { 830 EDataType memberType = (EDataType)i.next(); 831 if (rootValidator.validate(memberType, value, null, context)) 832 { 833 return true; 834 } 835 } 836 for (Iterator i = memberTypes.iterator(); i.hasNext(); ) 837 { 838 EDataType memberType = (EDataType)i.next(); 839 if (memberType.isInstance(value)) 840 { 841 return rootValidator.validate(memberType, value, diagnostics, context); 842 } 843 } 844 return false; 845 } 846 else 847 { 848 return result; 849 } 850 } 851 } 852 853 public boolean validate(EDataType eDataType, Object value, DiagnosticChain diagnostics, Map context) 854 { 855 if (!eDataType.isInstance(value)) 856 { 857 if (value == null) 858 { 859 return true; 860 } 861 else 862 { 863 if (diagnostics != null) reportDataValueTypeViolation(eDataType, value, diagnostics, context); 864 return false; 865 } 866 } 867 868 if (eDataType.eContainer() == getEPackage()) 869 { 870 return validate(eDataType.getClassifierID(), value, diagnostics, context); 871 } 872 else 873 { 874 return 875 new DynamicEDataTypeValidator(eDataType) 876 { 877 }.validate(eDataType, value, diagnostics, context); 878 } 879 } 880 881 protected void reportMinViolation 882 (EDataType eDataType, Object value, Object bound, boolean isInclusive, DiagnosticChain diagnostics, Map context) 883 { 884 diagnostics.add 885 (new BasicDiagnostic 886 (Diagnostic.ERROR, 887 DIAGNOSTIC_SOURCE, 888 DATA_VALUE__VALUE_IN_RANGE, 889 EcorePlugin.INSTANCE.getString 890 (isInclusive ? "_UI_MinInclusiveConstraint_diagnostic" : "_UI_MinExclusiveConstraint_diagnostic", 891 new Object [] 892 { 893 getValueLabel(eDataType, value, context), 894 isInclusive ? ">=" : ">", 895 getValueLabel(eDataType, bound, context) 896 }), 897 new Object [] { value, bound, isInclusive ? Boolean.TRUE : Boolean.FALSE })); 898 } 899 900 protected void reportMaxViolation 901 (EDataType eDataType, Object value, Object bound, boolean isInclusive, DiagnosticChain diagnostics, Map context) 902 { 903 diagnostics.add 904 (new BasicDiagnostic 905 (Diagnostic.ERROR, 906 DIAGNOSTIC_SOURCE, 907 DATA_VALUE__VALUE_IN_RANGE, 908 EcorePlugin.INSTANCE.getString 909 (isInclusive ? "_UI_MaxInclusiveConstraint_diagnostic" : "_UI_MaxExclusiveConstraint_diagnostic", 910 new Object [] 911 { 912 getValueLabel(eDataType, value, context), 913 "<", 914 getValueLabel(eDataType, bound, context) 915 }), 916 new Object [] { value, bound, isInclusive ? Boolean.TRUE : Boolean.FALSE })); 917 } 918 919 protected void reportMinLengthViolation 920 (EDataType eDataType, Object value, int length, int bound, DiagnosticChain diagnostics, Map context) 921 { 922 diagnostics.add 923 (new BasicDiagnostic 924 (Diagnostic.ERROR, 925 DIAGNOSTIC_SOURCE, 926 DATA_VALUE__LENGTH_IN_RANGE, 927 EcorePlugin.INSTANCE.getString 928 ("_UI_MinLengthConstraint_diagnostic", 929 new Object [] 930 { 931 getValueLabel(eDataType, value, context), 932 Integer.toString(length), 933 Integer.toString(bound) 934 }), 935 new Object [] { value, eDataType, new Integer (length), new Integer (bound) })); 936 } 937 938 protected void reportMaxLengthViolation 939 (EDataType eDataType, Object value, int length, int bound, DiagnosticChain diagnostics, Map context) 940 { 941 diagnostics.add 942 (new BasicDiagnostic 943 (Diagnostic.ERROR, 944 DIAGNOSTIC_SOURCE, 945 DATA_VALUE__LENGTH_IN_RANGE, 946 EcorePlugin.INSTANCE.getString 947 ("_UI_MaxLengthConstraint_diagnostic", 948 new Object [] 949 { 950 getValueLabel(eDataType, value, context), 951 Integer.toString(length), 952 Integer.toString(bound) 953 }), 954 new Object [] { value, eDataType, new Integer (length), new Integer (bound) })); 955 } 956 957 protected void reportTotalDigitsViolation 958 (EDataType eDataType, Object value, int totalDigits, DiagnosticChain diagnostics, Map context) 959 { 960 diagnostics.add 961 (new BasicDiagnostic 962 (Diagnostic.ERROR, 963 DIAGNOSTIC_SOURCE, 964 DATA_VALUE__TOTAL_DIGITS_IN_RANGE, 965 EcorePlugin.INSTANCE.getString 966 ("_UI_TotalDigitsConstraint_diagnostic", 967 new Object [] 968 { 969 getValueLabel(eDataType, value, context), 970 new Integer (totalDigits) 971 }), 972 new Object [] { value, eDataType, new Integer (totalDigits) })); 973 } 974 975 protected void reportFractionDigitsViolation 976 (EDataType eDataType, Object value, int fractionDigits, DiagnosticChain diagnostics, Map context) 977 { 978 diagnostics.add 979 (new BasicDiagnostic 980 (Diagnostic.ERROR, 981 DIAGNOSTIC_SOURCE, 982 DATA_VALUE__TOTAL_DIGITS_IN_RANGE, 983 EcorePlugin.INSTANCE.getString 984 ("_UI_FractionDigitsConstraint_diagnostic", 985 new Object [] 986 { 987 getValueLabel(eDataType, value, context), 988 new Integer (fractionDigits) 989 }), 990 new Object [] { value, eDataType, new Integer (fractionDigits) })); 991 } 992 993 protected void reportEnumerationViolation 994 (EDataType eDataType, Object value, Collection values, DiagnosticChain diagnostics, Map context) 995 { 996 String valueLiterals = ""; 997 Iterator i = values.iterator(); 998 if (i.hasNext()) 999 { 1000 valueLiterals = 1001 EcorePlugin.INSTANCE.getString("_UI_ListHead_composition", new Object [] { getValueLabel(eDataType, i.next(), context) }); 1002 while (i.hasNext()) 1003 { 1004 valueLiterals = 1005 EcorePlugin.INSTANCE.getString 1006 ("_UI_ListTail_composition", 1007 new Object [] { valueLiterals, getValueLabel(eDataType, i.next(), context) }); 1008 } 1009 } 1010 diagnostics.add 1011 (new BasicDiagnostic 1012 (Diagnostic.ERROR, 1013 DIAGNOSTIC_SOURCE, 1014 DATA_VALUE__VALUE_IN_ENUMERATION, 1015 EcorePlugin.INSTANCE.getString 1016 ("_UI_EnumerationConstraint_diagnostic", 1017 new Object [] 1018 { 1019 getValueLabel(eDataType, value, context), 1020 valueLiterals 1021 }), 1022 new Object [] { value, eDataType, values })); 1023 } 1024 1025 protected void reportDataValuePatternViolation 1026 (EDataType eDataType, Object value, PatternMatcher [] patterns, DiagnosticChain diagnostics, Map context) 1027 { 1028 String patternLiterals = ""; 1029 if (patterns.length > 0) 1030 { 1031 patternLiterals = EcorePlugin.INSTANCE.getString("_UI_ListHead_composition", new Object [] { patterns[0] }); 1032 for (int i = 1; i < patterns.length; ++i) 1033 { 1034 patternLiterals = EcorePlugin.INSTANCE.getString("_UI_ListTail_composition", new Object [] { patternLiterals, patterns[i] }); 1035 } 1036 } 1037 1038 diagnostics.add 1039 (new BasicDiagnostic 1040 (Diagnostic.ERROR, 1041 DIAGNOSTIC_SOURCE, 1042 DATA_VALUE__MATCHES_PATTERN, 1043 EcorePlugin.INSTANCE.getString 1044 ("_UI_PatternConstraint_diagnostic", 1045 new Object [] 1046 { 1047 getValueLabel(eDataType, value, context), 1048 patternLiterals 1049 }), 1050 new Object [] { value, eDataType, patterns })); 1051 } 1052 1053 protected void reportDataValueTypeViolation 1054 (EDataType eDataType, Object value, DiagnosticChain diagnostics, Map context) 1055 { 1056 diagnostics.add 1057 (new BasicDiagnostic 1058 (Diagnostic.ERROR, 1059 DIAGNOSTIC_SOURCE, 1060 DATA_VALUE__TYPE_CORRECT, 1061 EcorePlugin.INSTANCE.getString 1062 ("_UI_BadDataValueType_diagnostic", 1063 new Object [] 1064 { 1065 getValueLabel(eDataType, value, context), 1066 value == null ? "<null>" : value.getClass().getName(), 1067 eDataType.getInstanceClass().getName() 1068 }), 1069 new Object [] { value, eDataType })); 1070 } 1071 1072 protected static Collection wrapEnumerationValues(Object [] values) 1073 { 1074 return java.util.Arrays.asList(values); 1075 } 1076} 1077 | Popular Tags |