Some Eclipse Foundation services are deprecated, or will be soon. Please ensure you've read this important communication.
View | Details | Raw Unified | Return to bug 255786 | Differences between
and this patch

Collapse All | Expand All

(-)plugin.xml (+1 lines)
Lines 10-15 Link Here
10
   <extension-point id="content_handler" name="%_UI_ContentHandlerRegistry_extensionpoint" schema="schema/content_handler.exsd"/>
10
   <extension-point id="content_handler" name="%_UI_ContentHandlerRegistry_extensionpoint" schema="schema/content_handler.exsd"/>
11
   <extension-point id="uri_mapping" name="%_UI_URIMappingRegistry_extensionpoint" schema="schema/uri_mapping.exsd"/>
11
   <extension-point id="uri_mapping" name="%_UI_URIMappingRegistry_extensionpoint" schema="schema/uri_mapping.exsd"/>
12
   <extension-point id="package_registry_implementation" name="%_UI_PackageRegistryImplementation_extensionpoint" schema="schema/package_registry_implementation.exsd"/>
12
   <extension-point id="package_registry_implementation" name="%_UI_PackageRegistryImplementation_extensionpoint" schema="schema/package_registry_implementation.exsd"/>
13
   <extension-point id="constraints_delegator_registry" name="%_UI_ConstraintsDelegatorRegistry_extensionpoint" schema="schema/constraints_delegator_registry.exsd"/>
13
14
14
   <extension point="org.eclipse.emf.ecore.generated_package">
15
   <extension point="org.eclipse.emf.ecore.generated_package">
15
      <package
16
      <package
(-)plugin.properties (+2 lines)
Lines 114-119 Link Here
114
_UI_ContentHandler_extensionpoint = Content Handler Registry
114
_UI_ContentHandler_extensionpoint = Content Handler Registry
115
_UI_URIMappingRegistry_extensionpoint = URI Converter Mapping Registry
115
_UI_URIMappingRegistry_extensionpoint = URI Converter Mapping Registry
116
_UI_PackageRegistryImplementation_extensionpoint = Ecore Package Registry Implementation
116
_UI_PackageRegistryImplementation_extensionpoint = Ecore Package Registry Implementation
117
_UI_ConstraintsDelegatorRegistry_extensionpoint = Constraints Delegator Registry
118
117
119
118
_UI_GenericInvariant_diagnostic = The ''{0}'' invariant is violated on ''{1}''
120
_UI_GenericInvariant_diagnostic = The ''{0}'' invariant is violated on ''{1}''
119
_UI_GenericConstraint_diagnostic = The ''{0}'' constraint is violated on ''{1}''
121
_UI_GenericConstraint_diagnostic = The ''{0}'' constraint is violated on ''{1}''
(-)src/org/eclipse/emf/ecore/plugin/EcorePlugin.java (-62 / +65 lines)
Lines 55-61 Link Here
55
 * A collection of platform-neutral static utilities
55
 * A collection of platform-neutral static utilities
56
 * as well as Eclipse support utilities.
56
 * as well as Eclipse support utilities.
57
 */
57
 */
58
public class EcorePlugin  extends EMFPlugin
58
public class EcorePlugin extends EMFPlugin
59
{
59
{
60
  /**
60
  /**
61
   * The singleton instance of the plugin.
61
   * The singleton instance of the plugin.
Lines 67-73 Link Here
67
   */
67
   */
68
  private EcorePlugin()
68
  private EcorePlugin()
69
  {
69
  {
70
    super(new ResourceLocator[] {});
70
    super(new ResourceLocator []{});
71
  }
71
  }
72
72
73
  @Override
73
  @Override
Lines 162-168 Link Here
162
   * @param arguments an array of "command line" options.
162
   * @param arguments an array of "command line" options.
163
   * @return the arguments stripped of those recognized as platform resource options.
163
   * @return the arguments stripped of those recognized as platform resource options.
164
   */
164
   */
165
  public static String [] handlePlatformResourceOptions(String [] arguments)
165
  public static String[] handlePlatformResourceOptions(String[] arguments)
166
  {
166
  {
167
    getPlatformResourceMap();
167
    getPlatformResourceMap();
168
168
Lines 204-210 Link Here
204
          }
204
          }
205
        }
205
        }
206
206
207
        String [] remainingArguments = new String [arguments.length - (i - start)];
207
        String[] remainingArguments = new String [arguments.length - (i - start)];
208
        System.arraycopy(arguments, 0, remainingArguments, 0, start);
208
        System.arraycopy(arguments, 0, remainingArguments, 0, start);
209
        System.arraycopy(arguments, i, remainingArguments, start, arguments.length - i);
209
        System.arraycopy(arguments, i, remainingArguments, start, arguments.length - i);
210
        return remainingArguments;
210
        return remainingArguments;
Lines 213-219 Link Here
213
213
214
    return arguments;
214
    return arguments;
215
  }
215
  }
216
  
216
217
  /**
217
  /**
218
   * Returns a map from {@link EPackage#getNsURI() package namespace URI} (represented as a String) 
218
   * Returns a map from {@link EPackage#getNsURI() package namespace URI} (represented as a String) 
219
   * to the location of the GenModel containing a GenPackage for the package (represented as a {@link URI URI}).
219
   * to the location of the GenModel containing a GenPackage for the package (represented as a {@link URI URI}).
Lines 258-267 Link Here
258
    }
258
    }
259
    return result;
259
    return result;
260
  }
260
  }
261
  
261
262
  private static Pattern bundleSymbolNamePattern;
262
  private static Pattern bundleSymbolNamePattern;
263
  private static byte [] NO_BYTES = new byte [0];
263
  private static byte[] NO_BYTES = new byte [0];
264
  
264
265
  /**
265
  /**
266
   * Computes a map from <code>platform:/plugin/&lt;plugin-id>/</code> {@link URI} to 
266
   * Computes a map from <code>platform:/plugin/&lt;plugin-id>/</code> {@link URI} to 
267
   * <code>platform:/resource/&lt;plugin-location>/</code> URI
267
   * <code>platform:/resource/&lt;plugin-location>/</code> URI
Lines 277-288 Link Here
277
    Map<URI, URI> result = new HashMap<URI, URI>();
277
    Map<URI, URI> result = new HashMap<URI, URI>();
278
    IWorkspaceRoot root = getWorkspaceRoot();
278
    IWorkspaceRoot root = getWorkspaceRoot();
279
    if (root != null)
279
    if (root != null)
280
    { 
280
    {
281
      IProject [] projects = root.getProjects();
281
      IProject[] projects = root.getProjects();
282
      if (projects != null)
282
      if (projects != null)
283
      {
283
      {
284
        String pluginID = null;
284
        String pluginID = null;
285
        
285
286
        class Handler extends DefaultHandler
286
        class Handler extends DefaultHandler
287
        {
287
        {
288
          public String pluginID;
288
          public String pluginID;
Lines 298-308 Link Here
298
          }
298
          }
299
        }
299
        }
300
        Handler handler = new Handler();
300
        Handler handler = new Handler();
301
        
301
302
        SAXParserFactory parserFactory= SAXParserFactory.newInstance();
302
        SAXParserFactory parserFactory = SAXParserFactory.newInstance();
303
        parserFactory.setNamespaceAware(true);
303
        parserFactory.setNamespaceAware(true);
304
        SAXParser parser = null;
304
        SAXParser parser = null;
305
        
305
306
        try
306
        try
307
        {
307
        {
308
          parser = parserFactory.newSAXParser();
308
          parser = parserFactory.newSAXParser();
Lines 311-324 Link Here
311
        {
311
        {
312
          INSTANCE.log(exception);
312
          INSTANCE.log(exception);
313
        }
313
        }
314
        
314
315
        if (bundleSymbolNamePattern == null)
315
        if (bundleSymbolNamePattern == null)
316
        {
316
        {
317
          bundleSymbolNamePattern = Pattern.compile("^\\s*Bundle-SymbolicName\\s*:\\s*([^\\s;]*)\\s*(;.*)?$", Pattern.MULTILINE);
317
          bundleSymbolNamePattern = Pattern.compile("^\\s*Bundle-SymbolicName\\s*:\\s*([^\\s;]*)\\s*(;.*)?$", Pattern.MULTILINE);
318
        }
318
        }
319
        
319
320
        byte [] bytes = NO_BYTES;
320
        byte[] bytes = NO_BYTES;
321
        
321
322
        for (int i = 0, size = projects.length; i < size; ++i)
322
        for (int i = 0, size = projects.length; i < size; ++i)
323
        {
323
        {
324
          IProject project = projects[i];
324
          IProject project = projects[i];
Lines 331-337 Link Here
331
              InputStream inputStream = null;
331
              InputStream inputStream = null;
332
              try
332
              try
333
              {
333
              {
334
                inputStream = manifest.getContents(); 
334
                inputStream = manifest.getContents();
335
                int available = inputStream.available();
335
                int available = inputStream.available();
336
                if (bytes.length < available)
336
                if (bytes.length < available)
337
                {
337
                {
Lines 386-406 Link Here
386
                }
386
                }
387
              }
387
              }
388
            }
388
            }
389
            
389
390
            if (pluginID != null)
390
            if (pluginID != null)
391
            {
391
            {
392
              URI platformPluginURI = URI.createPlatformPluginURI(pluginID + "/", false);
392
              URI platformPluginURI = URI.createPlatformPluginURI(pluginID + "/", false);
393
              URI platformResourceURI = URI.createPlatformResourceURI(project.getName() + "/",  true);
393
              URI platformResourceURI = URI.createPlatformResourceURI(project.getName() + "/", true);
394
              result.put(platformPluginURI, platformResourceURI);
394
              result.put(platformPluginURI, platformResourceURI);
395
            }
395
            }
396
          }
396
          }
397
        }
397
        }
398
      }
398
      }
399
    }
399
    }
400
    
400
401
    return result;
401
    return result;
402
  }
402
  }
403
  
403
404
  /**
404
  /**
405
   * Computes a map so that plugins in the workspace will override those in the environment
405
   * Computes a map so that plugins in the workspace will override those in the environment
406
   * and so that plugins with Ecore and GenModels will look like projects in the workspace.
406
   * and so that plugins with Ecore and GenModels will look like projects in the workspace.
Lines 425-437 Link Here
425
    result.putAll(computePlatformResourceToPlatformPluginMap(new HashSet<URI>(EcorePlugin.getEPackageNsURIToGenModelLocationMap().values())));
425
    result.putAll(computePlatformResourceToPlatformPluginMap(new HashSet<URI>(EcorePlugin.getEPackageNsURIToGenModelLocationMap().values())));
426
    return result;
426
    return result;
427
  }
427
  }
428
  
428
429
  /**
429
  /**
430
   * The platform resource map.
430
   * The platform resource map.
431
   * @see #getPlatformResourceMap
431
   * @see #getPlatformResourceMap
432
   */
432
   */
433
  private static Map<String, URI> platformResourceMap;
433
  private static Map<String, URI> platformResourceMap;
434
  
434
435
  /**
435
  /**
436
   * The map from package namespace URIs to the location of the GenModel for that package.
436
   * The map from package namespace URIs to the location of the GenModel for that package.
437
   * @see #getPlatformResourceMap
437
   * @see #getPlatformResourceMap
Lines 452-458 Link Here
452
      super();
452
      super();
453
      plugin = this;
453
      plugin = this;
454
    }
454
    }
455
  
455
456
    /**
456
    /**
457
     * Starts up this plugin by reading some extensions and populating the relevant registries.
457
     * Starts up this plugin by reading some extensions and populating the relevant registries.
458
     * <p>
458
     * <p>
Lines 520-571 Link Here
520
        workspaceRoot = ResourcesPlugin.getWorkspace().getRoot();
520
        workspaceRoot = ResourcesPlugin.getWorkspace().getRoot();
521
      }
521
      }
522
522
523
      new RegistryReader
523
      new RegistryReader(
524
        (Platform.getExtensionRegistry(),
524
        Platform.getExtensionRegistry(),
525
         EcorePlugin.getPlugin().getBundle().getSymbolicName(), 
525
        EcorePlugin.getPlugin().getBundle().getSymbolicName(),
526
         PACKAGE_REGISTRY_IMPLEMENTATION_PPID)
526
        PACKAGE_REGISTRY_IMPLEMENTATION_PPID)
527
      {
528
        IConfigurationElement previous;
529
530
        @Override
531
        protected boolean readElement(IConfigurationElement element)
532
        {
527
        {
533
          if (element.getName().equals("registry"))
528
          IConfigurationElement previous;
529
530
          @Override
531
          protected boolean readElement(IConfigurationElement element)
534
          {
532
          {
535
            String implementationClass = element.getAttribute("class");
533
            if (element.getName().equals("registry"))
536
            if (implementationClass == null)
537
            {
534
            {
538
              logMissingAttribute(element, "class");
535
              String implementationClass = element.getAttribute("class");
539
            }
536
              if (implementationClass == null)
540
            else
537
              {
541
            {
538
                logMissingAttribute(element, "class");
542
              if (defaultRegistryImplementation != null)
539
              }
540
              else
543
              {
541
              {
544
                if (previous != null)
542
                if (defaultRegistryImplementation != null)
545
                {
543
                {
546
                  log("Both '" + previous.getContributor().getName() + "' and '" + element.getContributor().getName() + "' register a package registry implementation");
544
                  if (previous != null)
545
                  {
546
                    log("Both '" + previous.getContributor().getName() + "' and '" + element.getContributor().getName()
547
                      + "' register a package registry implementation");
548
                  }
549
                  if (defaultRegistryImplementation instanceof EPackageRegistryImpl.Delegator)
550
                  {
551
                    return false;
552
                  }
547
                }
553
                }
548
                if (defaultRegistryImplementation instanceof EPackageRegistryImpl.Delegator)
554
                try
549
                {
555
                {
550
                  return false;
556
                  defaultRegistryImplementation = (EPackage.Registry)element.createExecutableExtension("class");
557
                  previous = element;
551
                }
558
                }
559
                catch (CoreException exception)
560
                {
561
                  log(exception);
562
                }
563
                return true;
552
              }
564
              }
553
              try
554
              {
555
                defaultRegistryImplementation = (EPackage.Registry)element.createExecutableExtension("class");
556
                previous = element;
557
              }
558
              catch (CoreException exception)
559
              {
560
                log(exception);
561
              }
562
              return true;
563
            }
565
            }
566
            return false;
564
          }
567
          }
565
          return false;
568
566
        }
569
        }.readRegistry();
567
        
568
      }.readRegistry();
569
570
570
      new GeneratedPackageRegistryReader(getEPackageNsURIToGenModelLocationMap()).readRegistry();
571
      new GeneratedPackageRegistryReader(getEPackageNsURIToGenModelLocationMap()).readRegistry();
571
      new DynamicPackageRegistryReader().readRegistry();
572
      new DynamicPackageRegistryReader().readRegistry();
Lines 575-587 Link Here
575
      new ContentParserRegistryReader().readRegistry();
576
      new ContentParserRegistryReader().readRegistry();
576
      new ContentHandlerRegistryReader().readRegistry();
577
      new ContentHandlerRegistryReader().readRegistry();
577
      new URIMappingRegistryReader().readRegistry();
578
      new URIMappingRegistryReader().readRegistry();
579
      new ConstraintsDelegatorFactoryRegistryReader().readRegistry();
578
    }
580
    }
579
  }
581
  }
580
582
581
  /**
583
  /**
582
   * The default registry implementation singleton.
584
   * The default registry implementation singleton.
583
   */
585
   */
584
  private static EPackage.Registry defaultRegistryImplementation; 
586
  private static EPackage.Registry defaultRegistryImplementation;
585
587
586
  /**
588
  /**
587
   * Returns the default registry implementation singleton.
589
   * Returns the default registry implementation singleton.
Lines 631-634 Link Here
631
  public static final String SCHEME_PARSER_PPID = "scheme_parser";
633
  public static final String SCHEME_PARSER_PPID = "scheme_parser";
632
  public static final String URI_MAPPING_PPID = "uri_mapping";
634
  public static final String URI_MAPPING_PPID = "uri_mapping";
633
  public static final String PACKAGE_REGISTRY_IMPLEMENTATION_PPID = "package_registry_implementation";
635
  public static final String PACKAGE_REGISTRY_IMPLEMENTATION_PPID = "package_registry_implementation";
636
  public static final String CONSTRAINTS_DELEGATOR_FACTORY = "constraints_delegator_registry";
634
}
637
}
(-)src/org/eclipse/emf/ecore/util/EObjectValidator.java (-435 / +497 lines)
Lines 16-57 Link Here
16
 */
16
 */
17
package org.eclipse.emf.ecore.util;
17
package org.eclipse.emf.ecore.util;
18
18
19
19
import java.lang.reflect.Array;
20
import java.math.BigDecimal;
20
import java.util.ArrayList;
21
import java.util.ArrayList;
21
import java.util.Collection;
22
import java.util.Collection;
23
import java.util.Collections;
22
import java.util.HashMap;
24
import java.util.HashMap;
23
import java.util.Iterator;
25
import java.util.Iterator;
26
import java.util.LinkedList;
24
import java.util.List;
27
import java.util.List;
25
import java.util.ListIterator;
28
import java.util.ListIterator;
26
import java.util.Map;
29
import java.util.Map;
27
30
28
import java.lang.reflect.Array;
29
import java.math.BigDecimal;
30
31
import org.eclipse.emf.common.util.BasicDiagnostic;
31
import org.eclipse.emf.common.util.BasicDiagnostic;
32
import org.eclipse.emf.common.util.BasicEList;
32
import org.eclipse.emf.common.util.BasicEList;
33
import org.eclipse.emf.common.util.Diagnostic;
33
import org.eclipse.emf.common.util.Diagnostic;
34
import org.eclipse.emf.common.util.DiagnosticChain;
34
import org.eclipse.emf.common.util.DiagnosticChain;
35
import org.eclipse.emf.common.util.EMap;
35
import org.eclipse.emf.common.util.EMap;
36
import org.eclipse.emf.common.util.ResourceLocator;
36
import org.eclipse.emf.common.util.ResourceLocator;
37
37
import org.eclipse.emf.ecore.EAnnotation;
38
import org.eclipse.emf.ecore.EValidator;
39
40
import org.eclipse.emf.ecore.EAttribute;
38
import org.eclipse.emf.ecore.EAttribute;
41
import org.eclipse.emf.ecore.EObject;
42
import org.eclipse.emf.ecore.EClass;
39
import org.eclipse.emf.ecore.EClass;
43
import org.eclipse.emf.ecore.EReference;
44
import org.eclipse.emf.ecore.EcorePackage;
45
import org.eclipse.emf.ecore.EDataType;
40
import org.eclipse.emf.ecore.EDataType;
41
import org.eclipse.emf.ecore.EObject;
46
import org.eclipse.emf.ecore.EPackage;
42
import org.eclipse.emf.ecore.EPackage;
43
import org.eclipse.emf.ecore.EReference;
47
import org.eclipse.emf.ecore.EStructuralFeature;
44
import org.eclipse.emf.ecore.EStructuralFeature;
45
import org.eclipse.emf.ecore.EValidator;
46
import org.eclipse.emf.ecore.EcorePackage;
48
import org.eclipse.emf.ecore.InternalEObject;
47
import org.eclipse.emf.ecore.InternalEObject;
49
50
import org.eclipse.emf.ecore.plugin.EcorePlugin;
48
import org.eclipse.emf.ecore.plugin.EcorePlugin;
51
52
import org.eclipse.emf.ecore.resource.Resource;
49
import org.eclipse.emf.ecore.resource.Resource;
53
import org.eclipse.emf.ecore.resource.ResourceSet;
50
import org.eclipse.emf.ecore.resource.ResourceSet;
54
51
import org.eclipse.emf.ecore.util.ConstraintsDelegator.Factory;
55
import org.eclipse.emf.ecore.xml.type.util.XMLTypeUtil;
52
import org.eclipse.emf.ecore.xml.type.util.XMLTypeUtil;
56
53
57
54
Lines 60-65 Link Here
60
 */
57
 */
61
public class EObjectValidator implements EValidator
58
public class EObjectValidator implements EValidator
62
{
59
{
60
  private static final String USER_CONSTRAINT_VALIDATION_EANNOTATION_FACTORY = "factory";
61
62
  private static final String USER_CONSTRAINT_VALIDATION_EANNOTATION_CONSTRAINTS = "constraints";
63
64
  private static final String USER_CONSTRAINT_VALIDATION_EANNOTATION_INHERITANCE = "inheritsConstraints";
65
66
  private static final String USER_CONSTRAINT_VALIDATION_EANNOTATION_ECORE = "Ecore";
67
63
  public static final EObjectValidator INSTANCE = new EObjectValidator();
68
  public static final EObjectValidator INSTANCE = new EObjectValidator();
64
69
65
  public static final String DIAGNOSTIC_SOURCE = "org.eclipse.emf.ecore";
70
  public static final String DIAGNOSTIC_SOURCE = "org.eclipse.emf.ecore";
Lines 78-84 Link Here
78
  public static final int EOBJECT__UNIQUE_ID = 12;
83
  public static final int EOBJECT__UNIQUE_ID = 12;
79
  public static final int EOBJECT__EVERY_KEY_UNIQUE = 13;
84
  public static final int EOBJECT__EVERY_KEY_UNIQUE = 13;
80
  public static final int EOBJECT__EVERY_MAP_ENTRY_UNIQUE = 14;
85
  public static final int EOBJECT__EVERY_MAP_ENTRY_UNIQUE = 14;
81
  
86
82
  static final int EOBJECT_DIAGNOSTIC_CODE_COUNT = EOBJECT__EVERY_MAP_ENTRY_UNIQUE;
87
  static final int EOBJECT_DIAGNOSTIC_CODE_COUNT = EOBJECT__EVERY_MAP_ENTRY_UNIQUE;
83
88
84
  /**
89
  /**
Lines 173-182 Link Here
173
    else
178
    else
174
    {
179
    {
175
      List<EClass> eSuperTypes = eClass.getESuperTypes();
180
      List<EClass> eSuperTypes = eClass.getESuperTypes();
176
      return
181
      return eSuperTypes.isEmpty() ? validate_EveryDefaultConstraint(eObject, diagnostics, context) : validate(
177
        eSuperTypes.isEmpty() ?
182
        eSuperTypes.get(0),
178
          validate_EveryDefaultConstraint(eObject, diagnostics, context) :
183
        eObject,
179
          validate(eSuperTypes.get(0), eObject, diagnostics, context);
184
        diagnostics,
185
        context);
180
    }
186
    }
181
  }
187
  }
182
188
Lines 212-217 Link Here
212
    {
218
    {
213
      result &= validate_EveryMapEntryUnique(object, theDiagnostics, context);
219
      result &= validate_EveryMapEntryUnique(object, theDiagnostics, context);
214
    }
220
    }
221
    // ADDS FOR MANAGING USER CONSTRAINTS
222
    if (result || theDiagnostics != null)
223
    {
224
      result &= validate_UserConstraints(object, theDiagnostics, context);
225
    }
215
    return result;
226
    return result;
216
  }
227
  }
217
228
Lines 229-242 Link Here
229
    }
240
    }
230
    return result;
241
    return result;
231
  }
242
  }
232
  
243
233
  protected boolean validate_MultiplicityConforms
244
  protected boolean validate_MultiplicityConforms(
234
    (EObject eObject, EStructuralFeature eStructuralFeature, DiagnosticChain diagnostics, Map<Object, Object> context)
245
    EObject eObject,
246
    EStructuralFeature eStructuralFeature,
247
    DiagnosticChain diagnostics,
248
    Map<Object, Object> context)
235
  {
249
  {
236
    boolean result = true;
250
    boolean result = true;
237
    if (eStructuralFeature.isMany())
251
    if (eStructuralFeature.isMany())
238
    {
252
    {
239
      if (FeatureMapUtil.isFeatureMap(eStructuralFeature) &&  ExtendedMetaData.INSTANCE.isDocumentRoot(eObject.eClass()))
253
      if (FeatureMapUtil.isFeatureMap(eStructuralFeature) && ExtendedMetaData.INSTANCE.isDocumentRoot(eObject.eClass()))
240
      {
254
      {
241
        FeatureMap featureMap = (FeatureMap)eObject.eGet(eStructuralFeature);
255
        FeatureMap featureMap = (FeatureMap)eObject.eGet(eStructuralFeature);
242
        int count = 0;
256
        int count = 0;
Lines 254-273 Link Here
254
          result = false;
268
          result = false;
255
          if (diagnostics != null)
269
          if (diagnostics != null)
256
          {
270
          {
257
            diagnostics.add
271
            diagnostics.add(createDiagnostic(
258
              (createDiagnostic
272
              Diagnostic.ERROR,
259
                (Diagnostic.ERROR,
273
              DIAGNOSTIC_SOURCE,
260
                 DIAGNOSTIC_SOURCE,
274
              EOBJECT__EVERY_MULTIPCITY_CONFORMS,
261
                 EOBJECT__EVERY_MULTIPCITY_CONFORMS,
275
              "_UI_DocumentRootMustHaveOneElement_diagnostic",
262
                 "_UI_DocumentRootMustHaveOneElement_diagnostic",
276
              new Object []{ getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context), count },
263
                  new Object []
277
              new Object []{ eObject, eStructuralFeature },
264
                  {
278
              context));
265
                    getFeatureLabel(eStructuralFeature, context),
266
                    getObjectLabel(eObject, context),
267
                    count
268
                  },
269
                 new Object [] { eObject, eStructuralFeature },
270
                 context));
271
          }
279
          }
272
        }
280
        }
273
      }
281
      }
Lines 276-302 Link Here
276
        int lowerBound = eStructuralFeature.getLowerBound();
284
        int lowerBound = eStructuralFeature.getLowerBound();
277
        if (lowerBound > 0)
285
        if (lowerBound > 0)
278
        {
286
        {
279
          int size = ((List<?>)eObject.eGet(eStructuralFeature)).size();
287
          int size = ((List< ? >)eObject.eGet(eStructuralFeature)).size();
280
          if (size < lowerBound)
288
          if (size < lowerBound)
281
          {
289
          {
282
            result = false;
290
            result = false;
283
            if (diagnostics != null)
291
            if (diagnostics != null)
284
            {
292
            {
285
              diagnostics.add
293
              diagnostics.add(createDiagnostic(
286
                (createDiagnostic
294
                Diagnostic.ERROR,
287
                  (Diagnostic.ERROR,
295
                DIAGNOSTIC_SOURCE,
288
                   DIAGNOSTIC_SOURCE,
296
                EOBJECT__EVERY_MULTIPCITY_CONFORMS,
289
                   EOBJECT__EVERY_MULTIPCITY_CONFORMS,
297
                "_UI_FeatureHasTooFewValues_diagnostic",
290
                   "_UI_FeatureHasTooFewValues_diagnostic",
298
                new Object []{ getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context), size, lowerBound },
291
                    new Object []
299
                new Object []{ eObject, eStructuralFeature },
292
                    {
300
                context));
293
                      getFeatureLabel(eStructuralFeature, context),
294
                      getObjectLabel(eObject, context),
295
                      size,
296
                      lowerBound
297
                    },
298
                   new Object [] { eObject, eStructuralFeature },
299
                   context));
300
            }
301
            }
301
          }
302
          }
302
          int upperBound = eStructuralFeature.getUpperBound();
303
          int upperBound = eStructuralFeature.getUpperBound();
Lines 305-325 Link Here
305
            result = false;
306
            result = false;
306
            if (diagnostics != null)
307
            if (diagnostics != null)
307
            {
308
            {
308
              diagnostics.add
309
              diagnostics.add(createDiagnostic(
309
                (createDiagnostic
310
                Diagnostic.ERROR,
310
                  (Diagnostic.ERROR,
311
                DIAGNOSTIC_SOURCE,
311
                   DIAGNOSTIC_SOURCE,
312
                EOBJECT__EVERY_MULTIPCITY_CONFORMS,
312
                   EOBJECT__EVERY_MULTIPCITY_CONFORMS,
313
                "_UI_FeatureHasTooManyValues_diagnostic",
313
                   "_UI_FeatureHasTooManyValues_diagnostic",
314
                new Object []{ getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context), size, upperBound },
314
                   new Object []
315
                new Object []{ eObject, eStructuralFeature },
315
                   {
316
                context));
316
                     getFeatureLabel(eStructuralFeature, context),
317
                     getObjectLabel(eObject, context),
318
                     size,
319
                     upperBound
320
                   },
321
                   new Object [] { eObject, eStructuralFeature },
322
                   context));
323
            }
317
            }
324
          }
318
          }
325
        }
319
        }
Lines 328-354 Link Here
328
          int upperBound = eStructuralFeature.getUpperBound();
322
          int upperBound = eStructuralFeature.getUpperBound();
329
          if (upperBound > 0)
323
          if (upperBound > 0)
330
          {
324
          {
331
            int size = ((List<?>)eObject.eGet(eStructuralFeature)).size();
325
            int size = ((List< ? >)eObject.eGet(eStructuralFeature)).size();
332
            if (size > upperBound)
326
            if (size > upperBound)
333
            {
327
            {
334
              result = false;
328
              result = false;
335
              if (diagnostics != null)
329
              if (diagnostics != null)
336
              {
330
              {
337
                diagnostics.add
331
                diagnostics.add(createDiagnostic(
338
                  (createDiagnostic
332
                  Diagnostic.ERROR,
339
                    (Diagnostic.ERROR,
333
                  DIAGNOSTIC_SOURCE,
340
                     DIAGNOSTIC_SOURCE,
334
                  EOBJECT__EVERY_MULTIPCITY_CONFORMS,
341
                     EOBJECT__EVERY_MULTIPCITY_CONFORMS,
335
                  "_UI_FeatureHasTooManyValues_diagnostic",
342
                     "_UI_FeatureHasTooManyValues_diagnostic",
336
                  new Object []{ getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context), size, upperBound },
343
                     new Object []
337
                  new Object []{ eObject, eStructuralFeature },
344
                     {
338
                  context));
345
                       getFeatureLabel(eStructuralFeature, context),
346
                       getObjectLabel(eObject, context),
347
                       size,
348
                       upperBound
349
                     },
350
                     new Object [] { eObject, eStructuralFeature },
351
                     context));
352
              }
339
              }
353
            }
340
            }
354
          }
341
          }
Lines 362-376 Link Here
362
        result = false;
349
        result = false;
363
        if (diagnostics != null)
350
        if (diagnostics != null)
364
        {
351
        {
365
          diagnostics.add
352
          diagnostics.add(createDiagnostic(
366
            (createDiagnostic
353
            Diagnostic.ERROR,
367
              (Diagnostic.ERROR,
354
            DIAGNOSTIC_SOURCE,
368
               DIAGNOSTIC_SOURCE,
355
            EOBJECT__EVERY_MULTIPCITY_CONFORMS,
369
               EOBJECT__EVERY_MULTIPCITY_CONFORMS,
356
            "_UI_RequiredFeatureMustBeSet_diagnostic",
370
               "_UI_RequiredFeatureMustBeSet_diagnostic",
357
            new Object []{ getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context) },
371
               new Object [] { getFeatureLabel(eStructuralFeature, context), getObjectLabel(eObject, context) },
358
            new Object []{ eObject, eStructuralFeature },
372
               new Object [] { eObject, eStructuralFeature },
359
            context));
373
               context));
374
        }
360
        }
375
      }
361
      }
376
    }
362
    }
Lines 381-387 Link Here
381
  public boolean validate_EveryProxyResolves(EObject eObject, DiagnosticChain diagnostics, Map<Object, Object> context)
367
  public boolean validate_EveryProxyResolves(EObject eObject, DiagnosticChain diagnostics, Map<Object, Object> context)
382
  {
368
  {
383
    boolean result = true;
369
    boolean result = true;
384
    for (EContentsEList.FeatureIterator<EObject> i = (EContentsEList.FeatureIterator<EObject>)eObject.eCrossReferences().iterator(); i.hasNext(); )
370
    for (EContentsEList.FeatureIterator<EObject> i = (EContentsEList.FeatureIterator<EObject>)eObject.eCrossReferences().iterator(); i.hasNext();)
385
    {
371
    {
386
      EObject eCrossReferenceObject = i.next();
372
      EObject eCrossReferenceObject = i.next();
387
      if (eCrossReferenceObject.eIsProxy())
373
      if (eCrossReferenceObject.eIsProxy())
Lines 389-408 Link Here
389
        result = false;
375
        result = false;
390
        if (diagnostics != null)
376
        if (diagnostics != null)
391
        {
377
        {
392
          diagnostics.add
378
          diagnostics.add(createDiagnostic(
393
            (createDiagnostic
379
            Diagnostic.ERROR,
394
              (Diagnostic.ERROR,
380
            DIAGNOSTIC_SOURCE,
395
               DIAGNOSTIC_SOURCE,
381
            EOBJECT__EVERY_PROXY_RESOLVES,
396
               EOBJECT__EVERY_PROXY_RESOLVES,
382
            "_UI_UnresolvedProxy_diagnostic",
397
               "_UI_UnresolvedProxy_diagnostic",
383
            new Object []{
398
               new Object []
384
              getFeatureLabel(i.feature(), context),
399
               {
385
              getObjectLabel(eObject, context),
400
                 getFeatureLabel(i.feature(), context),
386
              getObjectLabel(eCrossReferenceObject, context) },
401
                 getObjectLabel(eObject, context),
387
            new Object []{ eObject, i.feature(), eCrossReferenceObject },
402
                 getObjectLabel(eCrossReferenceObject, context)
388
            context));
403
               },
404
               new Object [] { eObject, i.feature(), eCrossReferenceObject },
405
               context));
406
        }
389
        }
407
        else
390
        else
408
        {
391
        {
Lines 418-424 Link Here
418
    boolean result = true;
401
    boolean result = true;
419
    if (eObject.eResource() != null)
402
    if (eObject.eResource() != null)
420
    {
403
    {
421
      for (EContentsEList.FeatureIterator<EObject> i = (EContentsEList.FeatureIterator<EObject>)eObject.eCrossReferences().iterator(); i.hasNext(); )
404
      for (EContentsEList.FeatureIterator<EObject> i = (EContentsEList.FeatureIterator<EObject>)eObject.eCrossReferences().iterator(); i.hasNext();)
422
      {
405
      {
423
        EObject eCrossReferenceObject = i.next();
406
        EObject eCrossReferenceObject = i.next();
424
        if (eCrossReferenceObject.eResource() == null && !eCrossReferenceObject.eIsProxy() && !i.feature().isTransient())
407
        if (eCrossReferenceObject.eResource() == null && !eCrossReferenceObject.eIsProxy() && !i.feature().isTransient())
Lines 426-445 Link Here
426
          result = false;
409
          result = false;
427
          if (diagnostics != null)
410
          if (diagnostics != null)
428
          {
411
          {
429
            diagnostics.add
412
            diagnostics.add(createDiagnostic(
430
              (createDiagnostic
413
              Diagnostic.ERROR,
431
                (Diagnostic.ERROR,
414
              DIAGNOSTIC_SOURCE,
432
                 DIAGNOSTIC_SOURCE,
415
              EOBJECT__EVERY_REFERENCE_IS_CONTAINED,
433
                 EOBJECT__EVERY_REFERENCE_IS_CONTAINED,
416
              "_UI_DanglingReference_diagnostic",
434
                 "_UI_DanglingReference_diagnostic",
417
              new Object []{
435
                 new Object []
418
                getFeatureLabel(i.feature(), context),
436
                 {
419
                getObjectLabel(eObject, context),
437
                   getFeatureLabel(i.feature(), context),
420
                getObjectLabel(eCrossReferenceObject, context) },
438
                   getObjectLabel(eObject, context),
421
              new Object []{ eObject, i.feature(), eCrossReferenceObject },
439
                   getObjectLabel(eCrossReferenceObject, context)
422
              context));
440
                 },
441
                 new Object [] { eObject, i.feature(), eCrossReferenceObject },
442
                 context));
443
          }
423
          }
444
          else
424
          else
445
          {
425
          {
Lines 465-472 Link Here
465
    return result;
445
    return result;
466
  }
446
  }
467
447
468
  protected boolean validate_DataValueConforms
448
  protected boolean validate_DataValueConforms(
469
    (EObject eObject, EAttribute eAttribute, DiagnosticChain diagnostics, Map<Object, Object> context)
449
    EObject eObject,
450
    EAttribute eAttribute,
451
    DiagnosticChain diagnostics,
452
    Map<Object, Object> context)
470
  {
453
  {
471
    if (!eObject.eIsSet(eAttribute))
454
    if (!eObject.eIsSet(eAttribute))
472
    {
455
    {
Lines 478-492 Link Here
478
    Object value = eObject.eGet(eAttribute);
461
    Object value = eObject.eGet(eAttribute);
479
    if (FeatureMapUtil.isFeatureMap(eAttribute))
462
    if (FeatureMapUtil.isFeatureMap(eAttribute))
480
    {
463
    {
481
      @SuppressWarnings("unchecked") Collection<FeatureMap.Entry> featureMap = (Collection<FeatureMap.Entry>)value;
464
      @SuppressWarnings("unchecked")
465
      Collection<FeatureMap.Entry> featureMap = (Collection<FeatureMap.Entry>)value;
482
      EClass eClass = eObject.eClass();
466
      EClass eClass = eObject.eClass();
483
      Map<EStructuralFeature, DiagnosticChain> entryFeatureToDiagnosticChainMap = null;
467
      Map<EStructuralFeature, DiagnosticChain> entryFeatureToDiagnosticChainMap = null;
484
      for (Iterator<FeatureMap.Entry> i = featureMap.iterator(); i.hasNext() && (result || diagnostics != null); )
468
      for (Iterator<FeatureMap.Entry> i = featureMap.iterator(); i.hasNext() && (result || diagnostics != null);)
485
      {
469
      {
486
        FeatureMap.Entry entry = i.next();
470
        FeatureMap.Entry entry = i.next();
487
        EStructuralFeature entryFeature = entry.getEStructuralFeature();
471
        EStructuralFeature entryFeature = entry.getEStructuralFeature();
488
        if (entryFeature instanceof EAttribute &&
472
        if (entryFeature instanceof EAttribute && ExtendedMetaData.INSTANCE.getAffiliation(eClass, entryFeature) == eAttribute)
489
              ExtendedMetaData.INSTANCE.getAffiliation(eClass, entryFeature) == eAttribute)
490
        {
473
        {
491
          EDataType entryType = (EDataType)entryFeature.getEType();
474
          EDataType entryType = (EDataType)entryFeature.getEType();
492
          Object entryValue = entry.getValue();
475
          Object entryValue = entry.getValue();
Lines 514-520 Link Here
514
    }
497
    }
515
    else if (eAttribute.isMany())
498
    else if (eAttribute.isMany())
516
    {
499
    {
517
      for (Iterator<?> i = ((List<?>)value).iterator(); i.hasNext() && result; )
500
      for (Iterator< ? > i = ((List< ? >)value).iterator(); i.hasNext() && result;)
518
      {
501
      {
519
        result &= rootValidator.validate(eDataType, i.next(), null, context);
502
        result &= rootValidator.validate(eDataType, i.next(), null, context);
520
      }
503
      }
Lines 522-528 Link Here
522
      if (!result && diagnostics != null)
505
      if (!result && diagnostics != null)
523
      {
506
      {
524
        DiagnosticChain diagnostic = createBadDataValueDiagnostic(eObject, eAttribute, diagnostics, context);
507
        DiagnosticChain diagnostic = createBadDataValueDiagnostic(eObject, eAttribute, diagnostics, context);
525
        for (Iterator<?> i = ((List<?>)value).iterator(); i.hasNext(); )
508
        for (Iterator< ? > i = ((List< ? >)value).iterator(); i.hasNext();)
526
        {
509
        {
527
          rootValidator.validate(eDataType, i.next(), diagnostic, context);
510
          rootValidator.validate(eDataType, i.next(), diagnostic, context);
528
        }
511
        }
Lines 541-573 Link Here
541
    return result;
524
    return result;
542
  }
525
  }
543
526
544
  protected DiagnosticChain createBadDataValueDiagnostic
527
  protected DiagnosticChain createBadDataValueDiagnostic(
545
    (EObject eObject, EAttribute eAttribute, DiagnosticChain diagnostics, Map<Object, Object> context)
528
    EObject eObject,
546
  {
529
    EAttribute eAttribute,
547
    BasicDiagnostic diagnostic =
530
    DiagnosticChain diagnostics,
548
      createDiagnostic
531
    Map<Object, Object> context)
549
        (Diagnostic.ERROR,
532
  {
550
         DIAGNOSTIC_SOURCE,
533
    BasicDiagnostic diagnostic = createDiagnostic(
551
         EOBJECT__EVERY_DATA_VALUE_CONFORMS,
534
      Diagnostic.ERROR,
552
         "_UI_BadDataValue_diagnostic",
535
      DIAGNOSTIC_SOURCE,
553
         new Object []
536
      EOBJECT__EVERY_DATA_VALUE_CONFORMS,
554
         {
537
      "_UI_BadDataValue_diagnostic",
555
           getFeatureLabel(eAttribute, context),
538
      new Object []{ getFeatureLabel(eAttribute, context), getObjectLabel(eObject, context) },
556
           getObjectLabel(eObject, context)
539
      new Object []{ eObject, eAttribute },
557
         },
540
      context);
558
         new Object [] { eObject, eAttribute },
559
         context);
560
    diagnostics.add(diagnostic);
541
    diagnostics.add(diagnostic);
561
    return diagnostic;
542
    return diagnostic;
562
  }
543
  }
563
544
564
  protected boolean validatePattern
545
  protected boolean validatePattern(
565
    (EDataType eDataType, Object value, PatternMatcher [][] patterns, DiagnosticChain diagnostics, Map<Object, Object> context)
546
    EDataType eDataType,
547
    Object value,
548
    PatternMatcher[][] patterns,
549
    DiagnosticChain diagnostics,
550
    Map<Object, Object> context)
566
  {
551
  {
567
    String literal = EcoreUtil.convertToString(eDataType, value);
552
    String literal = EcoreUtil.convertToString(eDataType, value);
568
    for (int i = 0; i < patterns.length; ++i)
553
    for (int i = 0; i < patterns.length; ++i)
569
    {
554
    {
570
      PatternMatcher [] children = patterns[i];
555
      PatternMatcher[] children = patterns[i];
571
      boolean matches = false;
556
      boolean matches = false;
572
      for (int j = 0; j < children.length; ++j)
557
      for (int j = 0; j < children.length; ++j)
573
      {
558
      {
Lines 592-598 Link Here
592
  public class DynamicEDataTypeValidator
577
  public class DynamicEDataTypeValidator
593
  {
578
  {
594
    protected List<Object> effectiveEnumeration;
579
    protected List<Object> effectiveEnumeration;
595
    protected PatternMatcher [][] effectivePattern;
580
    protected PatternMatcher[][] effectivePattern;
596
    protected int effectiveTotalDigits = -1;
581
    protected int effectiveTotalDigits = -1;
597
    protected int effectiveFractionDigits = -1;
582
    protected int effectiveFractionDigits = -1;
598
    protected int effectiveMinLength = -1;
583
    protected int effectiveMinLength = -1;
Lines 643-651 Link Here
643
          {
628
          {
644
            patterns = new ArrayList<PatternMatcher[]>();
629
            patterns = new ArrayList<PatternMatcher[]>();
645
          }
630
          }
646
          PatternMatcher [] children = new PatternMatcher [pattern.size()];
631
          PatternMatcher[] children = new PatternMatcher [pattern.size()];
647
          patterns.add(children);
632
          patterns.add(children);
648
          for (ListIterator<String> i = pattern.listIterator(); i.hasNext(); )
633
          for (ListIterator<String> i = pattern.listIterator(); i.hasNext();)
649
          {
634
          {
650
            PatternMatcher patternMatcher = XMLTypeUtil.createPatternMatcher(i.next());
635
            PatternMatcher patternMatcher = XMLTypeUtil.createPatternMatcher(i.next());
651
            children[i.previousIndex()] = patternMatcher;
636
            children[i.previousIndex()] = patternMatcher;
Lines 729-735 Link Here
729
714
730
      if (patterns != null)
715
      if (patterns != null)
731
      {
716
      {
732
        effectivePattern = new PatternMatcher [patterns.size()][];
717
        effectivePattern = new PatternMatcher [patterns.size()] [];
733
        patterns.toArray(effectivePattern);
718
        patterns.toArray(effectivePattern);
734
      }
719
      }
735
720
Lines 740-753 Link Here
740
        {
725
        {
741
          digits.append("0");
726
          digits.append("0");
742
        }
727
        }
743
        
728
744
        try
729
        try
745
        {
730
        {
746
          Object lowerBound = EcoreUtil.createFromString(eDataType, "-" + digits.toString());
731
          Object lowerBound = EcoreUtil.createFromString(eDataType, "-" + digits.toString());
747
          @SuppressWarnings("unchecked") boolean lowerBounded = effectiveMin == null ||
732
          @SuppressWarnings("unchecked")
748
                (effectiveMinIsInclusive ?
733
          boolean lowerBounded = effectiveMin == null
749
                   ((Comparable<Object>)effectiveMin).compareTo(lowerBound) <= 0:
734
            || (effectiveMinIsInclusive
750
                   ((Comparable<Object>)effectiveMin).compareTo(lowerBound) < 0);
735
              ? ((Comparable<Object>)effectiveMin).compareTo(lowerBound) <= 0
736
              : ((Comparable<Object>)effectiveMin).compareTo(lowerBound) < 0);
751
          if (lowerBounded)
737
          if (lowerBounded)
752
          {
738
          {
753
            effectiveMinIsInclusive = false;
739
            effectiveMinIsInclusive = false;
Lines 755-761 Link Here
755
            effectiveTotalDigitsMin = effectiveTotalDigits;
741
            effectiveTotalDigitsMin = effectiveTotalDigits;
756
          }
742
          }
757
        }
743
        }
758
        catch (NumberFormatException exception) 
744
        catch (NumberFormatException exception)
759
        {
745
        {
760
          // Ignore the bound if the value is too big.
746
          // Ignore the bound if the value is too big.
761
        }
747
        }
Lines 763-772 Link Here
763
        try
749
        try
764
        {
750
        {
765
          Object upperBound = EcoreUtil.createFromString(eDataType, digits.toString());
751
          Object upperBound = EcoreUtil.createFromString(eDataType, digits.toString());
766
          @SuppressWarnings("unchecked") boolean upperBounded = effectiveMax == null ||
752
          @SuppressWarnings("unchecked")
767
                (effectiveMaxIsInclusive ?
753
          boolean upperBounded = effectiveMax == null
768
                   ((Comparable<Object>)effectiveMax).compareTo(upperBound) >= 0:
754
            || (effectiveMaxIsInclusive
769
                   ((Comparable<Object>)effectiveMax).compareTo(upperBound) > 0);
755
              ? ((Comparable<Object>)effectiveMax).compareTo(upperBound) >= 0
756
              : ((Comparable<Object>)effectiveMax).compareTo(upperBound) > 0);
770
          if (upperBounded)
757
          if (upperBounded)
771
          {
758
          {
772
            effectiveMaxIsInclusive = false;
759
            effectiveMaxIsInclusive = false;
Lines 774-780 Link Here
774
            effectiveTotalDigitsMax = effectiveTotalDigits;
761
            effectiveTotalDigitsMax = effectiveTotalDigits;
775
          }
762
          }
776
        }
763
        }
777
        catch (NumberFormatException exception) 
764
        catch (NumberFormatException exception)
778
        {
765
        {
779
          // Ignore the bound if the value is too big.
766
          // Ignore the bound if the value is too big.
780
        }
767
        }
Lines 795-801 Link Here
795
      {
782
      {
796
        if (!effectiveEnumeration.contains(value))
783
        if (!effectiveEnumeration.contains(value))
797
        {
784
        {
798
          if (diagnostics != null) reportEnumerationViolation(eDataType, value, effectiveEnumeration, diagnostics, context);
785
          if (diagnostics != null)
786
            reportEnumerationViolation(eDataType, value, effectiveEnumeration, diagnostics, context);
799
          result = false;
787
          result = false;
800
        }
788
        }
801
      }
789
      }
Lines 807-816 Link Here
807
795
808
      if (effectiveMin != null)
796
      if (effectiveMin != null)
809
      {
797
      {
810
        @SuppressWarnings("unchecked") Comparable<Object> comparableObject = (Comparable<Object>)effectiveMin;
798
        @SuppressWarnings("unchecked")
811
        if (effectiveMinIsInclusive ?
799
        Comparable<Object> comparableObject = (Comparable<Object>)effectiveMin;
812
              comparableObject.compareTo(value) > 0:
800
        if (effectiveMinIsInclusive ? comparableObject.compareTo(value) > 0 : comparableObject.compareTo(value) >= 0)
813
              comparableObject.compareTo(value) >= 0)
814
        {
801
        {
815
          if (diagnostics != null)
802
          if (diagnostics != null)
816
          {
803
          {
Lines 829-838 Link Here
829
816
830
      if (effectiveMax != null)
817
      if (effectiveMax != null)
831
      {
818
      {
832
        @SuppressWarnings("unchecked") Comparable<Object> comparableObject = (Comparable<Object>)effectiveMax;
819
        @SuppressWarnings("unchecked")
833
        if (effectiveMaxIsInclusive ?
820
        Comparable<Object> comparableObject = (Comparable<Object>)effectiveMax;
834
              comparableObject.compareTo(value) < 0:
821
        if (effectiveMaxIsInclusive ? comparableObject.compareTo(value) < 0 : comparableObject.compareTo(value) <= 0)
835
              comparableObject.compareTo(value) <= 0)
836
        {
822
        {
837
          if (diagnostics != null)
823
          if (diagnostics != null)
838
          {
824
          {
Lines 851-880 Link Here
851
837
852
      if (effectiveMinLength != -1)
838
      if (effectiveMinLength != -1)
853
      {
839
      {
854
        int length =
840
        int length = value instanceof String ? ((String)value).length() : value instanceof Collection< ? >
855
          value instanceof String ?
841
          ? ((Collection< ? >)value).size() : Array.getLength(value);
856
            ((String)value).length() :
857
             value instanceof Collection<?> ?
858
               ((Collection<?>)value).size() :
859
               Array.getLength(value);
860
        if (length < effectiveMinLength)
842
        if (length < effectiveMinLength)
861
        {
843
        {
862
          if (diagnostics != null) reportMinLengthViolation(eDataType, value, length, effectiveMinLength, diagnostics, context);
844
          if (diagnostics != null)
845
            reportMinLengthViolation(eDataType, value, length, effectiveMinLength, diagnostics, context);
863
          result = false;
846
          result = false;
864
        }
847
        }
865
      }
848
      }
866
849
867
      if (effectiveMaxLength != -1)
850
      if (effectiveMaxLength != -1)
868
      {
851
      {
869
        int length =
852
        int length = value instanceof String ? ((String)value).length() : value instanceof Collection< ? >
870
          value instanceof String ?
853
          ? ((Collection< ? >)value).size() : Array.getLength(value);
871
            ((String)value).length() :
872
             value instanceof Collection<?> ?
873
               ((Collection<?>)value).size() :
874
               Array.getLength(value);
875
        if (length > effectiveMaxLength)
854
        if (length > effectiveMaxLength)
876
        {
855
        {
877
          if (diagnostics != null) reportMaxLengthViolation(eDataType, value, length, effectiveMaxLength, diagnostics, context);
856
          if (diagnostics != null)
857
            reportMaxLengthViolation(eDataType, value, length, effectiveMaxLength, diagnostics, context);
878
          result = false;
858
          result = false;
879
        }
859
        }
880
      }
860
      }
Lines 883-889 Link Here
883
      {
863
      {
884
        if (value instanceof BigDecimal && ((BigDecimal)value).unscaledValue().abs().toString().length() > effectiveTotalDigits)
864
        if (value instanceof BigDecimal && ((BigDecimal)value).unscaledValue().abs().toString().length() > effectiveTotalDigits)
885
        {
865
        {
886
          if (diagnostics != null) reportTotalDigitsViolation(eDataType, value, effectiveTotalDigits, diagnostics, context);
866
          if (diagnostics != null)
867
            reportTotalDigitsViolation(eDataType, value, effectiveTotalDigits, diagnostics, context);
887
          result = false;
868
          result = false;
888
        }
869
        }
889
      }
870
      }
Lines 892-898 Link Here
892
      {
873
      {
893
        if (value instanceof BigDecimal && ((BigDecimal)value).scale() > effectiveFractionDigits)
874
        if (value instanceof BigDecimal && ((BigDecimal)value).scale() > effectiveFractionDigits)
894
        {
875
        {
895
          if (diagnostics != null) reportFractionDigitsViolation(eDataType, value, effectiveFractionDigits, diagnostics, context);
876
          if (diagnostics != null)
877
            reportFractionDigitsViolation(eDataType, value, effectiveFractionDigits, diagnostics, context);
896
          result = false;
878
          result = false;
897
        }
879
        }
898
      }
880
      }
Lines 900-906 Link Here
900
      if (itemType != null)
882
      if (itemType != null)
901
      {
883
      {
902
        EValidator rootValidator = getRootEValidator(context);
884
        EValidator rootValidator = getRootEValidator(context);
903
        for (Iterator<?> i = ((List<?>)value).iterator(); i.hasNext() && (result || diagnostics != null); )
885
        for (Iterator< ? > i = ((List< ? >)value).iterator(); i.hasNext() && (result || diagnostics != null);)
904
        {
886
        {
905
          result &= rootValidator.validate(itemType, i.next(), diagnostics, context);
887
          result &= rootValidator.validate(itemType, i.next(), diagnostics, context);
906
        }
888
        }
Lines 909-915 Link Here
909
      else if (!memberTypes.isEmpty())
891
      else if (!memberTypes.isEmpty())
910
      {
892
      {
911
        EValidator rootValidator = getRootEValidator(context);
893
        EValidator rootValidator = getRootEValidator(context);
912
        
894
913
        for (EDataType memberType : memberTypes)
895
        for (EDataType memberType : memberTypes)
914
        {
896
        {
915
          if (rootValidator.validate(memberType, value, null, context))
897
          if (rootValidator.validate(memberType, value, null, context))
Lines 943-949 Link Here
943
      }
925
      }
944
      else
926
      else
945
      {
927
      {
946
        if (diagnostics != null) reportDataValueTypeViolation(eDataType, value, diagnostics, context);
928
        if (diagnostics != null)
929
          reportDataValueTypeViolation(eDataType, value, diagnostics, context);
947
        return false;
930
        return false;
948
      }
931
      }
949
    }
932
    }
Lines 954-961 Link Here
954
    }
937
    }
955
    else
938
    else
956
    {
939
    {
957
      return
940
      return new DynamicEDataTypeValidator(eDataType)
958
        new DynamicEDataTypeValidator(eDataType)
959
        {
941
        {
960
          // Ensure that the class loader for this class will be used downstream.
942
          // Ensure that the class loader for this class will be used downstream.
961
          //
943
          //
Lines 963-1164 Link Here
963
    }
945
    }
964
  }
946
  }
965
947
966
  protected void reportMinViolation
948
  protected void reportMinViolation(
967
    (EDataType eDataType, Object value, Object bound, boolean isInclusive, DiagnosticChain diagnostics, Map<Object, Object> context)
949
    EDataType eDataType,
968
  {
950
    Object value,
969
    diagnostics.add
951
    Object bound,
970
      (createDiagnostic
952
    boolean isInclusive,
971
        (Diagnostic.ERROR,
953
    DiagnosticChain diagnostics,
972
         DIAGNOSTIC_SOURCE,
954
    Map<Object, Object> context)
973
         DATA_VALUE__VALUE_IN_RANGE,
955
  {
974
         isInclusive ? "_UI_MinInclusiveConstraint_diagnostic" : "_UI_MinExclusiveConstraint_diagnostic",
956
    diagnostics.add(createDiagnostic(Diagnostic.ERROR, DIAGNOSTIC_SOURCE, DATA_VALUE__VALUE_IN_RANGE, isInclusive
975
         new Object []
957
      ? "_UI_MinInclusiveConstraint_diagnostic" : "_UI_MinExclusiveConstraint_diagnostic", new Object []{
976
         {
958
      getValueLabel(eDataType, value, context),
977
           getValueLabel(eDataType, value, context),
959
      isInclusive ? ">=" : ">",
978
           isInclusive ? ">=" : ">",
960
      getValueLabel(eDataType, bound, context) }, new Object []{ value, bound, isInclusive ? Boolean.TRUE : Boolean.FALSE }, context));
979
           getValueLabel(eDataType, bound, context)
961
  }
980
         },
962
981
         new Object [] { value, bound, isInclusive ? Boolean.TRUE : Boolean.FALSE },
963
  protected void reportMaxViolation(
982
         context));
964
    EDataType eDataType,
983
  }
965
    Object value,
984
966
    Object bound,
985
  protected void reportMaxViolation
967
    boolean isInclusive,
986
    (EDataType eDataType, Object value, Object bound, boolean isInclusive, DiagnosticChain diagnostics, Map<Object, Object> context)
968
    DiagnosticChain diagnostics,
987
  {
969
    Map<Object, Object> context)
988
    diagnostics.add
970
  {
989
      (createDiagnostic
971
    diagnostics.add(createDiagnostic(Diagnostic.ERROR, DIAGNOSTIC_SOURCE, DATA_VALUE__VALUE_IN_RANGE, isInclusive
990
        (Diagnostic.ERROR,
972
      ? "_UI_MaxInclusiveConstraint_diagnostic" : "_UI_MaxExclusiveConstraint_diagnostic", new Object []{
991
         DIAGNOSTIC_SOURCE,
973
      getValueLabel(eDataType, value, context),
992
         DATA_VALUE__VALUE_IN_RANGE,
974
      "<",
993
         isInclusive ? "_UI_MaxInclusiveConstraint_diagnostic" : "_UI_MaxExclusiveConstraint_diagnostic",
975
      getValueLabel(eDataType, bound, context) }, new Object []{ value, bound, isInclusive ? Boolean.TRUE : Boolean.FALSE }, context));
994
         new Object []
976
  }
995
         {
977
996
           getValueLabel(eDataType, value, context),
978
  protected void reportMinLengthViolation(
997
           "<",
979
    EDataType eDataType,
998
           getValueLabel(eDataType, bound, context)
980
    Object value,
999
         },
981
    int length,
1000
         new Object [] { value, bound, isInclusive ? Boolean.TRUE : Boolean.FALSE },
982
    int bound,
1001
         context));
983
    DiagnosticChain diagnostics,
1002
  }
984
    Map<Object, Object> context)
1003
985
  {
1004
  protected void reportMinLengthViolation
986
    diagnostics.add(createDiagnostic(
1005
    (EDataType eDataType, Object value, int length, int bound, DiagnosticChain diagnostics, Map<Object, Object> context)
987
      Diagnostic.ERROR,
1006
  {
988
      DIAGNOSTIC_SOURCE,
1007
    diagnostics.add
989
      DATA_VALUE__LENGTH_IN_RANGE,
1008
      (createDiagnostic
990
      "_UI_MinLengthConstraint_diagnostic",
1009
        (Diagnostic.ERROR,
991
      new Object []{ getValueLabel(eDataType, value, context), Integer.toString(length), Integer.toString(bound) },
1010
         DIAGNOSTIC_SOURCE,
992
      new Object []{ value, eDataType, length, bound },
1011
         DATA_VALUE__LENGTH_IN_RANGE,
993
      context));
1012
         "_UI_MinLengthConstraint_diagnostic",
994
  }
1013
         new Object []
995
1014
         {
996
  protected void reportMaxLengthViolation(
1015
           getValueLabel(eDataType, value, context),
997
    EDataType eDataType,
1016
           Integer.toString(length),
998
    Object value,
1017
           Integer.toString(bound)
999
    int length,
1018
         },
1000
    int bound,
1019
         new Object [] { value, eDataType, length, bound },
1001
    DiagnosticChain diagnostics,
1020
         context));
1002
    Map<Object, Object> context)
1021
  }
1003
  {
1022
1004
    diagnostics.add(createDiagnostic(
1023
  protected void reportMaxLengthViolation
1005
      Diagnostic.ERROR,
1024
    (EDataType eDataType, Object value, int length, int bound, DiagnosticChain diagnostics, Map<Object, Object> context)
1006
      DIAGNOSTIC_SOURCE,
1025
  {
1007
      DATA_VALUE__LENGTH_IN_RANGE,
1026
    diagnostics.add
1008
      "_UI_MaxLengthConstraint_diagnostic",
1027
      (createDiagnostic
1009
      new Object []{ getValueLabel(eDataType, value, context), Integer.toString(length), Integer.toString(bound) },
1028
        (Diagnostic.ERROR,
1010
      new Object []{ value, eDataType, length, bound },
1029
         DIAGNOSTIC_SOURCE,
1011
      context));
1030
         DATA_VALUE__LENGTH_IN_RANGE,
1012
  }
1031
         "_UI_MaxLengthConstraint_diagnostic",
1013
1032
         new Object []
1014
  protected void reportTotalDigitsViolation(
1033
         {
1015
    EDataType eDataType,
1034
           getValueLabel(eDataType, value, context),
1016
    Object value,
1035
           Integer.toString(length),
1017
    int totalDigits,
1036
           Integer.toString(bound)
1018
    DiagnosticChain diagnostics,
1037
         },
1019
    Map<Object, Object> context)
1038
         new Object [] { value, eDataType, length, bound },
1020
  {
1039
         context));
1021
    diagnostics.add(createDiagnostic(
1040
  }
1022
      Diagnostic.ERROR,
1041
1023
      DIAGNOSTIC_SOURCE,
1042
  protected void reportTotalDigitsViolation
1024
      DATA_VALUE__TOTAL_DIGITS_IN_RANGE,
1043
    (EDataType eDataType, Object value, int totalDigits, DiagnosticChain diagnostics, Map<Object, Object> context)
1025
      "_UI_TotalDigitsConstraint_diagnostic",
1044
  {
1026
      new Object []{ getValueLabel(eDataType, value, context), totalDigits },
1045
    diagnostics.add
1027
      new Object []{ value, eDataType, totalDigits },
1046
      (createDiagnostic
1028
      context));
1047
        (Diagnostic.ERROR,
1029
  }
1048
         DIAGNOSTIC_SOURCE,
1030
1049
         DATA_VALUE__TOTAL_DIGITS_IN_RANGE,
1031
  protected void reportFractionDigitsViolation(
1050
         "_UI_TotalDigitsConstraint_diagnostic",
1032
    EDataType eDataType,
1051
         new Object []
1033
    Object value,
1052
         {
1034
    int fractionDigits,
1053
           getValueLabel(eDataType, value, context),
1035
    DiagnosticChain diagnostics,
1054
           totalDigits
1036
    Map<Object, Object> context)
1055
         },
1037
  {
1056
         new Object [] { value, eDataType, totalDigits },
1038
    diagnostics.add(createDiagnostic(
1057
         context));
1039
      Diagnostic.ERROR,
1058
  }
1040
      DIAGNOSTIC_SOURCE,
1059
1041
      DATA_VALUE__TOTAL_DIGITS_IN_RANGE,
1060
  protected void reportFractionDigitsViolation
1042
      "_UI_FractionDigitsConstraint_diagnostic",
1061
    (EDataType eDataType, Object value, int fractionDigits, DiagnosticChain diagnostics, Map<Object, Object> context)
1043
      new Object []{ getValueLabel(eDataType, value, context), fractionDigits },
1062
  {
1044
      new Object []{ value, eDataType, fractionDigits },
1063
    diagnostics.add
1045
      context));
1064
      (createDiagnostic
1046
  }
1065
        (Diagnostic.ERROR,
1047
1066
         DIAGNOSTIC_SOURCE,
1048
  protected void reportEnumerationViolation(
1067
         DATA_VALUE__TOTAL_DIGITS_IN_RANGE,
1049
    EDataType eDataType,
1068
         "_UI_FractionDigitsConstraint_diagnostic",
1050
    Object value,
1069
         new Object []
1051
    Collection< ? > values,
1070
         {
1052
    DiagnosticChain diagnostics,
1071
           getValueLabel(eDataType, value, context),
1053
    Map<Object, Object> context)
1072
           fractionDigits
1073
         },
1074
         new Object [] { value, eDataType, fractionDigits },
1075
         context));
1076
  }
1077
1078
  protected void reportEnumerationViolation
1079
    (EDataType eDataType, Object value, Collection<?> values, DiagnosticChain diagnostics, Map<Object, Object> context)
1080
  {
1054
  {
1081
    String valueLiterals = "";
1055
    String valueLiterals = "";
1082
    Iterator<?> i = values.iterator();
1056
    Iterator< ? > i = values.iterator();
1083
    if (i.hasNext())
1057
    if (i.hasNext())
1084
    {
1058
    {
1085
      valueLiterals =
1059
      valueLiterals = getEcoreResourceLocator().getString(
1086
        getEcoreResourceLocator().getString("_UI_ListHead_composition", new Object [] { getValueLabel(eDataType, i.next(), context) });
1060
        "_UI_ListHead_composition",
1061
        new Object []{ getValueLabel(eDataType, i.next(), context) });
1087
      while (i.hasNext())
1062
      while (i.hasNext())
1088
      {
1063
      {
1089
        valueLiterals =
1064
        valueLiterals = getEcoreResourceLocator().getString(
1090
          getEcoreResourceLocator().getString
1065
          "_UI_ListTail_composition",
1091
            ("_UI_ListTail_composition",
1066
          new Object []{ valueLiterals, getValueLabel(eDataType, i.next(), context) });
1092
             new Object [] { valueLiterals, getValueLabel(eDataType, i.next(), context) });
1067
      }
1093
      }
1068
    }
1094
    }
1069
    diagnostics.add(createDiagnostic(
1095
    diagnostics.add
1070
      Diagnostic.ERROR,
1096
      (createDiagnostic
1071
      DIAGNOSTIC_SOURCE,
1097
        (Diagnostic.ERROR,
1072
      DATA_VALUE__VALUE_IN_ENUMERATION,
1098
         DIAGNOSTIC_SOURCE,
1073
      "_UI_EnumerationConstraint_diagnostic",
1099
         DATA_VALUE__VALUE_IN_ENUMERATION,
1074
      new Object []{ getValueLabel(eDataType, value, context), valueLiterals },
1100
         "_UI_EnumerationConstraint_diagnostic",
1075
      new Object []{ value, eDataType, values },
1101
         new Object []
1076
      context));
1102
         {
1077
  }
1103
           getValueLabel(eDataType, value, context),
1078
1104
           valueLiterals
1079
  protected void reportDataValuePatternViolation(
1105
         },
1080
    EDataType eDataType,
1106
         new Object [] { value, eDataType, values },
1081
    Object value,
1107
         context));
1082
    PatternMatcher[] patterns,
1108
  }
1083
    DiagnosticChain diagnostics,
1109
1084
    Map<Object, Object> context)
1110
  protected void reportDataValuePatternViolation
1111
    (EDataType eDataType, Object value, PatternMatcher [] patterns, DiagnosticChain diagnostics, Map<Object, Object> context)
1112
  {
1085
  {
1113
    String patternLiterals = "";
1086
    String patternLiterals = "";
1114
    if (patterns.length > 0)
1087
    if (patterns.length > 0)
1115
    {
1088
    {
1116
      patternLiterals = getEcoreResourceLocator().getString("_UI_ListHead_composition", new Object [] { patterns[0] });
1089
      patternLiterals = getEcoreResourceLocator().getString("_UI_ListHead_composition", new Object []{ patterns[0] });
1117
      for (int i = 1; i < patterns.length; ++i)
1090
      for (int i = 1; i < patterns.length; ++i)
1118
      {
1091
      {
1119
        patternLiterals = getEcoreResourceLocator().getString("_UI_ListTail_composition", new Object [] { patternLiterals, patterns[i] });
1092
        patternLiterals = getEcoreResourceLocator().getString("_UI_ListTail_composition", new Object []{ patternLiterals, patterns[i] });
1120
      }
1093
      }
1121
    }
1094
    }
1122
1095
1123
    diagnostics.add
1096
    diagnostics.add(createDiagnostic(
1124
      (createDiagnostic
1097
      Diagnostic.ERROR,
1125
        (Diagnostic.ERROR,
1098
      DIAGNOSTIC_SOURCE,
1126
         DIAGNOSTIC_SOURCE,
1099
      DATA_VALUE__MATCHES_PATTERN,
1127
         DATA_VALUE__MATCHES_PATTERN,
1100
      "_UI_PatternConstraint_diagnostic",
1128
         "_UI_PatternConstraint_diagnostic",
1101
      new Object []{ getValueLabel(eDataType, value, context), patternLiterals },
1129
         new Object []
1102
      new Object []{ value, eDataType, patterns },
1130
         {
1103
      context));
1131
           getValueLabel(eDataType, value, context),
1104
  }
1132
           patternLiterals
1105
1133
         },
1106
  protected void reportDataValueTypeViolation(EDataType eDataType, Object value, DiagnosticChain diagnostics, Map<Object, Object> context)
1134
         new Object [] { value, eDataType, patterns },
1107
  {
1135
         context));
1108
    diagnostics.add(createDiagnostic(
1136
  }
1109
      Diagnostic.ERROR,
1137
1110
      DIAGNOSTIC_SOURCE,
1138
  protected void reportDataValueTypeViolation
1111
      DATA_VALUE__TYPE_CORRECT,
1139
    (EDataType eDataType, Object value, DiagnosticChain diagnostics, Map<Object, Object> context)
1112
      "_UI_BadDataValueType_diagnostic",
1140
  {
1113
      new Object []{
1141
    diagnostics.add
1114
        getValueLabel(eDataType, value, context),
1142
      (createDiagnostic
1115
        value == null ? "<null>" : value.getClass().getName(),
1143
        (Diagnostic.ERROR,
1116
        eDataType.getInstanceClass().getName() },
1144
         DIAGNOSTIC_SOURCE,
1117
      new Object []{ value, eDataType },
1145
         DATA_VALUE__TYPE_CORRECT,
1118
      context));
1146
         "_UI_BadDataValueType_diagnostic",
1147
         new Object []
1148
         {
1149
           getValueLabel(eDataType, value, context),
1150
           value == null ? "<null>" : value.getClass().getName(),
1151
           eDataType.getInstanceClass().getName()
1152
         },
1153
         new Object [] { value, eDataType },
1154
         context));
1155
  }
1119
  }
1156
1120
1157
  protected static Collection<Object> wrapEnumerationValues(Object [] values)
1121
  protected static Collection<Object> wrapEnumerationValues(Object[] values)
1158
  {
1122
  {
1159
    return java.util.Arrays.asList(values);
1123
    return java.util.Arrays.asList(values);
1160
  }
1124
  }
1161
  
1125
1162
  /**
1126
  /**
1163
   * @since 2.2
1127
   * @since 2.2
1164
   */
1128
   */
Lines 1175-1194 Link Here
1175
        if (eObject != otherEObject && otherEObject != null)
1139
        if (eObject != otherEObject && otherEObject != null)
1176
        {
1140
        {
1177
          // ...
1141
          // ...
1178
          diagnostics.add
1142
          diagnostics.add(createDiagnostic(
1179
            (createDiagnostic
1143
            Diagnostic.ERROR,
1180
              (Diagnostic.ERROR,
1144
            DIAGNOSTIC_SOURCE,
1181
               DIAGNOSTIC_SOURCE,
1145
            EOBJECT__UNIQUE_ID,
1182
               EOBJECT__UNIQUE_ID,
1146
            "_UI_DuplicateID_diagnostic",
1183
               "_UI_DuplicateID_diagnostic",
1147
            new Object []{ id, getObjectLabel(eObject, context), getObjectLabel(otherEObject, context) },
1184
               new Object []
1148
            new Object []{ eObject, otherEObject, id },
1185
               {
1149
            context));
1186
                 id,
1187
                 getObjectLabel(eObject, context),
1188
                 getObjectLabel(otherEObject, context)
1189
               },
1190
               new Object [] { eObject, otherEObject, id },
1191
               context));
1192
        }
1150
        }
1193
      }
1151
      }
1194
    }
1152
    }
Lines 1224-1230 Link Here
1224
    }
1182
    }
1225
    return result;
1183
    return result;
1226
  }
1184
  }
1227
  
1185
1228
  /**
1186
  /**
1229
   * @since 2.3
1187
   * @since 2.3
1230
   * @param eObject
1188
   * @param eObject
Lines 1233-1249 Link Here
1233
   * @param context
1191
   * @param context
1234
   * @return whether every key is unique.
1192
   * @return whether every key is unique.
1235
   */
1193
   */
1236
  protected boolean validate_KeyUnique
1194
  protected boolean validate_KeyUnique(EObject eObject, EReference eReference, DiagnosticChain diagnostics, Map<Object, Object> context)
1237
    (EObject eObject, EReference eReference, DiagnosticChain diagnostics, Map<Object, Object> context)
1238
  {
1195
  {
1239
    boolean result = true;
1196
    boolean result = true;
1240
    Map<List<Object>, EObject> keys = new HashMap<List<Object>, EObject>();
1197
    Map<List<Object>, EObject> keys = new HashMap<List<Object>, EObject>();
1241
    EAttribute [] eAttributes = (EAttribute[])((BasicEList<?>)eReference.getEKeys()).data();
1198
    EAttribute[] eAttributes = (EAttribute[])((BasicEList< ? >)eReference.getEKeys()).data();
1242
    @SuppressWarnings("unchecked")
1199
    @SuppressWarnings("unchecked")
1243
    List<EObject> values = (List<EObject>)eObject.eGet(eReference);
1200
    List<EObject> values = (List<EObject>)eObject.eGet(eReference);
1244
    for (EObject value : values)
1201
    for (EObject value : values)
1245
    {
1202
    {
1246
      ArrayList<Object> key = new ArrayList<Object>(); 
1203
      ArrayList<Object> key = new ArrayList<Object>();
1247
      for (int i = 0, size = eAttributes.length; i < size; ++i)
1204
      for (int i = 0, size = eAttributes.length; i < size; ++i)
1248
      {
1205
      {
1249
        EAttribute eAttribute = eAttributes[i];
1206
        EAttribute eAttribute = eAttributes[i];
Lines 1251-1257 Link Here
1251
        {
1208
        {
1252
          break;
1209
          break;
1253
        }
1210
        }
1254
        else 
1211
        else
1255
        {
1212
        {
1256
          key.add(value.eGet(eAttribute));
1213
          key.add(value.eGet(eAttribute));
1257
        }
1214
        }
Lines 1272-1292 Link Here
1272
          {
1229
          {
1273
            uriFragmentSegment = uriFragmentSegment.substring(index);
1230
            uriFragmentSegment = uriFragmentSegment.substring(index);
1274
          }
1231
          }
1275
          diagnostics.add
1232
          diagnostics.add(createDiagnostic(
1276
            (createDiagnostic
1233
            Diagnostic.ERROR,
1277
              (Diagnostic.ERROR,
1234
            DIAGNOSTIC_SOURCE,
1278
               DIAGNOSTIC_SOURCE,
1235
            EOBJECT__EVERY_KEY_UNIQUE,
1279
               EOBJECT__EVERY_KEY_UNIQUE,
1236
            "_UI_DuplicateKey_diagnostic",
1280
               "_UI_DuplicateKey_diagnostic",
1237
            new Object []{
1281
               new Object []
1238
              getFeatureLabel(eReference, context),
1282
               {
1239
              uriFragmentSegment,
1283
                 getFeatureLabel(eReference, context),
1240
              getObjectLabel(value, context),
1284
                 uriFragmentSegment,
1241
              getObjectLabel(otherValue, context) },
1285
                 getObjectLabel(value, context),
1242
            new Object []{ eObject, eReference, value, otherValue },
1286
                 getObjectLabel(otherValue, context)
1243
            context));
1287
               },
1288
               new Object [] { eObject, eReference, value, otherValue },
1289
               context));
1290
        }
1244
        }
1291
      }
1245
      }
1292
    }
1246
    }
Lines 1329-1347 Link Here
1329
   * @param context
1283
   * @param context
1330
   * @return whether every map entry is unique.
1284
   * @return whether every map entry is unique.
1331
   */
1285
   */
1332
  protected boolean validate_MapEntryUnique
1286
  protected boolean validate_MapEntryUnique(EObject eObject, EReference eReference, DiagnosticChain diagnostics, Map<Object, Object> context)
1333
    (EObject eObject, EReference eReference, DiagnosticChain diagnostics, Map<Object, Object> context)
1334
  {
1287
  {
1335
    boolean result = true;
1288
    boolean result = true;
1336
    Object value = eObject.eGet(eReference);
1289
    Object value = eObject.eGet(eReference);
1337
    if (value instanceof EMap<?, ?>)
1290
    if (value instanceof EMap< ? , ? >)
1338
    {
1291
    {
1339
      EMap<?, ?> eMap = (EMap<?, ?>)value;
1292
      EMap< ? , ? > eMap = (EMap< ? , ? >)value;
1340
      for (int i = 0, size = eMap.size(); i < size; ++i)
1293
      for (int i = 0, size = eMap.size(); i < size; ++i)
1341
      {
1294
      {
1342
        Map.Entry<?, ?> entry = eMap.get(i);
1295
        Map.Entry< ? , ? > entry = eMap.get(i);
1343
        Object key = entry.getKey();
1296
        Object key = entry.getKey();
1344
        int index =  eMap.indexOfKey(key);
1297
        int index = eMap.indexOfKey(key);
1345
        if (index != i)
1298
        if (index != i)
1346
        {
1299
        {
1347
          result = false;
1300
          result = false;
Lines 1351-1370 Link Here
1351
          }
1304
          }
1352
          else
1305
          else
1353
          {
1306
          {
1354
            diagnostics.add
1307
            diagnostics.add(createDiagnostic(
1355
              (createDiagnostic
1308
              Diagnostic.ERROR,
1356
                (Diagnostic.ERROR,
1309
              DIAGNOSTIC_SOURCE,
1357
                 DIAGNOSTIC_SOURCE,
1310
              EOBJECT__EVERY_MAP_ENTRY_UNIQUE,
1358
                 EOBJECT__EVERY_MAP_ENTRY_UNIQUE,
1311
              "_UI_DuplicateMapEntry_diagnostic",
1359
                 "_UI_DuplicateMapEntry_diagnostic",
1312
              new Object []{ getFeatureLabel(eReference, context), i, index },
1360
                 new Object []
1313
              new Object []{ eObject, eReference, entry, eMap.get(index) },
1361
                 {
1314
              context));
1362
                   getFeatureLabel(eReference, context),
1363
                   i,
1364
                   index
1365
                 },
1366
                 new Object [] { eObject, eReference, entry, eMap.get(index) },
1367
                 context));
1368
          }
1315
          }
1369
        }
1316
        }
1370
      }
1317
      }
Lines 1374-1379 Link Here
1374
  }
1321
  }
1375
1322
1376
  /**
1323
  /**
1324
   * @since 2.5
1325
   * @param theEClass
1326
   * @param object
1327
   * @param theDiagnostics
1328
   * @param context
1329
   * @return
1330
   */
1331
  protected boolean validate_UserConstraintsByEClass(
1332
    EClass theEClass,
1333
    EObject object,
1334
    DiagnosticChain theDiagnostics,
1335
    Map<Object, Object> context)
1336
  {
1337
    Collection<EAnnotation> annotations = theEClass.getEAnnotations();
1338
    Collection<String> constraints = new LinkedList<String>();
1339
    String factoryName = "";
1340
    String keyName = "";
1341
    boolean result = true;
1342
    boolean inheritsConstraints = true;
1343
    for (EAnnotation e : annotations)
1344
    {
1345
      if (USER_CONSTRAINT_VALIDATION_EANNOTATION_ECORE.equals(e.getSource()))
1346
      {
1347
        // check if user specifies how to manage constraints inheritance
1348
        if (e.getDetails().containsKey(USER_CONSTRAINT_VALIDATION_EANNOTATION_INHERITANCE))
1349
        {
1350
          String value = e.getDetails().get(USER_CONSTRAINT_VALIDATION_EANNOTATION_INHERITANCE);
1351
          if (value != null && ("true".equals(value.trim().toLowerCase()) || "false".equals(value.trim().toLowerCase())))
1352
          {
1353
            inheritsConstraints = Boolean.valueOf(value);
1354
          }
1355
        }
1356
        if (e.getDetails().containsKey(USER_CONSTRAINT_VALIDATION_EANNOTATION_CONSTRAINTS))
1357
        {
1358
          String strConstraints = e.getDetails().get(USER_CONSTRAINT_VALIDATION_EANNOTATION_CONSTRAINTS);
1359
1360
          String[] stringSplited = strConstraints.split("\\s");
1361
          Collections.addAll(constraints, stringSplited);
1362
          if (stringSplited != null && stringSplited.length > 0)
1363
          {
1364
            if (e.getDetails().containsKey(USER_CONSTRAINT_VALIDATION_EANNOTATION_FACTORY))
1365
            {
1366
              String strFactory = e.getDetails().get(USER_CONSTRAINT_VALIDATION_EANNOTATION_FACTORY);
1367
              String[] strs = strFactory.split("#");
1368
              if (strs != null && strs.length == 2)
1369
              {
1370
                factoryName = strs[0];
1371
                keyName = strs[1];
1372
              }
1373
              else
1374
              {
1375
                factoryName = strFactory;
1376
                keyName = strFactory;
1377
              }
1378
            }
1379
          }
1380
          break;
1381
        }
1382
      }
1383
    }
1384
    if (inheritsConstraints)
1385
    {
1386
      for (EClass c : theEClass.getESuperTypes())
1387
      {
1388
        result &= validate_UserConstraintsByEClass(c, object, theDiagnostics, context);
1389
      }
1390
    }
1391
    if (constraints.size() > 0 && keyName.length() > 0 && factoryName.length() > 0)
1392
    {
1393
      for (String currentConstraint : constraints)
1394
      {
1395
        for (EAnnotation e : annotations)
1396
        {
1397
          if (keyName.equals(e.getSource()))
1398
          {
1399
            if (e.getDetails().containsKey(currentConstraint))
1400
            {
1401
              String rule = e.getDetails().get(currentConstraint);
1402
              Factory factory = ConstraintsDelegator.Factory.Registry.INSTANCE.getFactory(factoryName);
1403
              if (factory != null)
1404
              {
1405
                ConstraintsDelegator constraintDelegator = factory.createConstraintDelegator();
1406
                if (constraintDelegator != null)
1407
                {
1408
                  result &= constraintDelegator.validate(rule, object, theDiagnostics, context);
1409
                }
1410
              }
1411
            }
1412
          }
1413
        }
1414
      }
1415
    }
1416
    return result;
1417
  }
1418
1419
  /**
1420
     * @since 2.5
1421
     * @param object
1422
     * @param theDiagnostics
1423
     * @param context
1424
     * @return
1425
     */
1426
  protected boolean validate_UserConstraints(EObject object, DiagnosticChain theDiagnostics, Map<Object, Object> context)
1427
  {
1428
    EClass theclass = object.eClass();
1429
    boolean result = validate_UserConstraintsByEClass(theclass, object, theDiagnostics, context);
1430
    return result;
1431
  }
1432
1433
  /**
1377
   * Creates a new {@link BasicDiagnostic#BasicDiagnostic(int, String, int, String, Object[]) basic diagnostic}.
1434
   * Creates a new {@link BasicDiagnostic#BasicDiagnostic(int, String, int, String, Object[]) basic diagnostic}.
1378
   * If the source is {@link #DIAGNOSTIC_SOURCE "org.eclipse.emf.ecore"}, 
1435
   * If the source is {@link #DIAGNOSTIC_SOURCE "org.eclipse.emf.ecore"}, 
1379
   * it calls {@link #getEcoreString(String, Object[])};
1436
   * it calls {@link #getEcoreString(String, Object[])};
Lines 1389-1401 Link Here
1389
   * @see BasicDiagnostic#BasicDiagnostic(int, String, int, String, Object[])
1446
   * @see BasicDiagnostic#BasicDiagnostic(int, String, int, String, Object[])
1390
   * @since 2.4
1447
   * @since 2.4
1391
   */
1448
   */
1392
  protected BasicDiagnostic createDiagnostic
1449
  protected BasicDiagnostic createDiagnostic(
1393
    (int severity, String source, int code, String messageKey, Object[] messageSubstitutions, Object[] data, Map<Object, Object> context)
1450
    int severity,
1394
  {
1451
    String source,
1395
    String message =
1452
    int code,
1396
      DIAGNOSTIC_SOURCE.equals(source) ?
1453
    String messageKey,
1397
        getEcoreString(messageKey, messageSubstitutions) :
1454
    Object[] messageSubstitutions,
1398
        getString(messageKey, messageSubstitutions);
1455
    Object[] data,
1456
    Map<Object, Object> context)
1457
  {
1458
    String message = DIAGNOSTIC_SOURCE.equals(source) ? getEcoreString(messageKey, messageSubstitutions) : getString(
1459
      messageKey,
1460
      messageSubstitutions);
1399
    return new BasicDiagnostic(severity, source, code, message, data);
1461
    return new BasicDiagnostic(severity, source, code, message, data);
1400
  }
1462
  }
1401
1463
Lines 1407-1413 Link Here
1407
   * @return the message.
1469
   * @return the message.
1408
   * @since 2.4
1470
   * @since 2.4
1409
   */
1471
   */
1410
  protected String getEcoreString(String key, Object [] substitutions)
1472
  protected String getEcoreString(String key, Object[] substitutions)
1411
  {
1473
  {
1412
    return getString(getEcoreResourceLocator(), key, substitutions);
1474
    return getString(getEcoreResourceLocator(), key, substitutions);
1413
  }
1475
  }
Lines 1430-1436 Link Here
1430
   * @return the message.
1492
   * @return the message.
1431
   * @since 2.4
1493
   * @since 2.4
1432
   */
1494
   */
1433
  protected String getString(String key, Object [] substitutions)
1495
  protected String getString(String key, Object[] substitutions)
1434
  {
1496
  {
1435
    return getString("_UI_GenericConstraint_diagnostic".equals(key) ? getEcoreResourceLocator() : getResourceLocator(), key, substitutions);
1497
    return getString("_UI_GenericConstraint_diagnostic".equals(key) ? getEcoreResourceLocator() : getResourceLocator(), key, substitutions);
1436
  }
1498
  }
Lines 1447-1453 Link Here
1447
    return getEcoreResourceLocator();
1509
    return getEcoreResourceLocator();
1448
  }
1510
  }
1449
1511
1450
  private String getString(ResourceLocator resourceLocator, String key, Object [] substitutions)
1512
  private String getString(ResourceLocator resourceLocator, String key, Object[] substitutions)
1451
  {
1513
  {
1452
    return substitutions == null ? resourceLocator.getString(key) : resourceLocator.getString(key, substitutions);
1514
    return substitutions == null ? resourceLocator.getString(key) : resourceLocator.getString(key, substitutions);
1453
  }
1515
  }
(-)src/org/eclipse/emf/ecore/plugin/ConstraintsDelegatorFactoryRegistryReader.java (+87 lines)
Added Link Here
1
/**
2
 * <copyright>
3
 *
4
 * Copyright (c) 2005 IBM Corporation and others.
5
 * All rights reserved.   This program and the accompanying materials
6
 * are made available under the terms of the Common Public License v1.0
7
 * which accompanies this distribution, and is available at
8
 * http://www.eclipse.org/legal/cpl-v10.html
9
 * 
10
 * Contributors: 
11
 *   IBM - Initial API and implementation
12
 *
13
 * </copyright>
14
 *
15
 * $Id: EMF_codetemplates.xml,v 1.1 2008/05/06 20:12:20 nickb Exp $
16
 */
17
package org.eclipse.emf.ecore.plugin;
18
19
import org.eclipse.core.runtime.CoreException;
20
import org.eclipse.core.runtime.IConfigurationElement;
21
import org.eclipse.core.runtime.Platform;
22
import org.eclipse.emf.common.util.WrappedException;
23
import org.eclipse.emf.ecore.util.ConstraintsDelegator;
24
import org.eclipse.emf.ecore.util.ConstraintsDelegator.Factory;
25
26
/**
27
 * A plugin extension reader that populates the
28
 * {@link org.eclipse.emf.ecore.util.ConstraintsDelegator.Factory.Registry#INSTANCE global} resource factory's
29
 * Clients are not expected to use this class directly.
30
 */
31
public class ConstraintsDelegatorFactoryRegistryReader extends RegistryReader
32
{
33
  static final String TAG_FACTORY = "factory";
34
  static final String ATT_URI = "uri";
35
  static final String ATT_CLASS = "class";
36
  
37
  public ConstraintsDelegatorFactoryRegistryReader()
38
  {
39
    super
40
    (Platform.getExtensionRegistry(),
41
     EcorePlugin.getPlugin().getBundle().getSymbolicName(), 
42
     EcorePlugin.CONSTRAINTS_DELEGATOR_FACTORY);
43
  }
44
  
45
  @Override
46
  protected boolean readElement(IConfigurationElement element, boolean add)
47
  {
48
    if (element.getName().equals(TAG_FACTORY))
49
    {
50
      String packageURI = element.getAttribute(ATT_URI);
51
      if (packageURI == null)
52
      {
53
        logMissingAttribute(element, ATT_URI);
54
      }
55
      else if (element.getAttribute(ATT_CLASS) == null)
56
      {
57
        logMissingAttribute(element, ATT_CLASS);
58
      }
59
      else
60
      {
61
        try
62
        {
63
          Object o = element.createExecutableExtension(ATT_CLASS);
64
          if (o instanceof ConstraintsDelegator.Factory)
65
          {
66
            Factory tmp = ConstraintsDelegator.Factory.Registry.INSTANCE.getFactory(packageURI);
67
            if (tmp != null)
68
            {
69
              EcorePlugin.INSTANCE.log
70
              ("factory '" + o.getClass().getName() + "'tries to override '" + packageURI + "' instead of factor '" + tmp.getClass().getName()+"'");
71
            }
72
            else 
73
            {
74
              ConstraintsDelegator.Factory.Registry.INSTANCE.putFactory(packageURI, (Factory)o);
75
            }
76
          }
77
          return true;
78
        }
79
        catch (CoreException e)
80
        {
81
          throw new WrappedException(e);
82
        }
83
      }
84
    }
85
    return false;
86
  }
87
}
(-)schema/constraints_delegator_registry.exsd (+113 lines)
Added Link Here
1
<?xml version='1.0' encoding='UTF-8'?>
2
<!-- Schema file written by PDE -->
3
<schema targetNamespace="org.eclipse.emf.ecore" xmlns="http://www.w3.org/2001/XMLSchema">
4
<annotation>
5
      <appinfo>
6
         <meta.schema plugin="org.eclipse.emf.ecore" id="constraints_delegator_registry" name="%_UI_ConstraintsDelegatorRegistry_extensionpoint"/>
7
      </appinfo>
8
      <documentation>
9
         Adds a ConstraintDelegatorFactory to check constraints in Ecore models
10
      </documentation>
11
   </annotation>
12
13
   <element name="extension">
14
      <annotation>
15
         <appinfo>
16
            <meta.element />
17
         </appinfo>
18
      </annotation>
19
      <complexType>
20
         <sequence>
21
            <element ref="factory"/>
22
         </sequence>
23
         <attribute name="point" type="string" use="required">
24
            <annotation>
25
               <documentation>
26
                  
27
               </documentation>
28
            </annotation>
29
         </attribute>
30
         <attribute name="id" type="string">
31
            <annotation>
32
               <documentation>
33
                  
34
               </documentation>
35
            </annotation>
36
         </attribute>
37
         <attribute name="name" type="string">
38
            <annotation>
39
               <documentation>
40
                  
41
               </documentation>
42
               <appinfo>
43
                  <meta.attribute translatable="true"/>
44
               </appinfo>
45
            </annotation>
46
         </attribute>
47
      </complexType>
48
   </element>
49
50
   <element name="factory">
51
      <complexType>
52
         <attribute name="uri" type="string" use="required">
53
            <annotation>
54
               <documentation>
55
                  the uri which will be inserted by user to check constraints
56
               </documentation>
57
            </annotation>
58
         </attribute>
59
         <attribute name="class" type="string" use="required">
60
            <annotation>
61
               <documentation>
62
                  A fully qualified name of the Java class implementing &lt;samp&gt;org.eclipse.emf.ecore.util.ConstraintsDelegator.Factory
63
&lt;/samp&gt;.
64
               </documentation>
65
               <appinfo>
66
                  <meta.attribute kind="java" basedOn=":org.eclipse.emf.ecore.util.ConstraintsDelegator.Factory"/>
67
               </appinfo>
68
            </annotation>
69
         </attribute>
70
      </complexType>
71
   </element>
72
73
   <annotation>
74
      <appinfo>
75
         <meta.section type="since"/>
76
      </appinfo>
77
      <documentation>
78
         2.5.0
79
      </documentation>
80
   </annotation>
81
82
   <annotation>
83
      <appinfo>
84
         <meta.section type="examples"/>
85
      </appinfo>
86
      <documentation>
87
         Following is an example of implementation
88
&lt;pre&gt;
89
&lt;extension
90
         point=&quot;org.eclipse.emf.ecore.constraints_delegator_regstry&quot;&gt;
91
      &lt;factory
92
            class=&quot;ocl.test.ConstraintsDelegator.MyFactory&quot;
93
            uri=&quot;org.eclipse.emf.ocl&quot;&gt;
94
      &lt;/factory&gt;
95
   &lt;/extension&gt;
96
&lt;/pre&gt;
97
      </documentation>
98
   </annotation>
99
100
101
102
   <annotation>
103
      <appinfo>
104
         <meta.section type="copyright"/>
105
      </appinfo>
106
      <documentation>
107
         Copyright (c) 2002, 2004 IBM Corporation and others.&lt;br&gt;
108
All rights reserved. This program and the accompanying materials are made available under the terms of the Eclipse Public License v1.0 which accompanies this distribution, and is available at &lt;a 
109
href=&quot;http://www.eclipse.org/legal/epl-v10.html&quot;&gt;http://www.eclipse.org/legal/epl-v10.html&lt;/a&gt;
110
      </documentation>
111
   </annotation>
112
113
</schema>
(-)src/org/eclipse/emf/ecore/util/ConstraintsDelegator.java (+85 lines)
Added Link Here
1
/**
2
 * <copyright>
3
 *
4
 * Copyright (c) 2005 IBM Corporation and others.
5
 * All rights reserved.   This program and the accompanying materials
6
 * are made available under the terms of the Common Public License v1.0
7
 * which accompanies this distribution, and is available at
8
 * http://www.eclipse.org/legal/cpl-v10.html
9
 * 
10
 * Contributors: 
11
 *   IBM - Initial API and implementation
12
 *
13
 * </copyright>
14
 *
15
 * $Id: ConstraintsDelegator.java,v 1.0 2008/11/19 16:37:42 tfaure Exp $
16
 */
17
package org.eclipse.emf.ecore.util;
18
19
import java.util.HashMap;
20
import java.util.Map;
21
22
import org.eclipse.emf.common.util.DiagnosticChain;
23
import org.eclipse.emf.ecore.EObject;
24
25
26
/**
27
 * An interface to validate a constraint
28
 * The only method to implement is {@link #validate(String, EObject, DiagnosticChain, Map)
29
 * To add a factory please see extension point : constraints_delegator_regstry
30
 */
31
public interface ConstraintsDelegator
32
{
33
  interface Factory
34
  {
35
    interface Registry
36
    {
37
      Registry INSTANCE = new Impl();
38
39
      /**
40
       * Returns the factory identified by the key
41
       * @param key the factory id
42
       * @return the factory or null if it doesn't exist
43
       */
44
      Factory getFactory(String key);
45
46
      /**
47
       * Registers a factory and associates it to an id
48
       * @param key the id
49
       * @param value the factory
50
       */
51
      void putFactory(String key, Factory value);
52
53
      class Impl extends HashMap<String, Factory> implements Registry
54
      {
55
        private static final long serialVersionUID = 1L;
56
57
        public Factory getFactory(String key)
58
        {
59
          return get(key);
60
        }
61
62
        public void putFactory(String key, Factory value)
63
        {
64
          put(key, value);
65
        }
66
      }
67
    }
68
69
    /**
70
     * Create a constraint delegator which is able to check a constraint
71
     * @return the constraint Delegator
72
     */
73
    ConstraintsDelegator createConstraintDelegator();
74
  }
75
76
  /**
77
   * Validate a constraint and add to the diagnostic chain the evaluation's diagnostic
78
   * @param value the expression to manage
79
   * @param object the current EObject
80
   * @param theDiagnostics the diagnostic's chain
81
   * @param context the context of the current validation
82
   * @return true if it's OK else false
83
   */
84
  boolean validate(String value, EObject object, DiagnosticChain theDiagnostics, Map<Object, Object> context);
85
}

Return to bug 255786