diff options
| author | Laurent Fasani | 2018-04-26 14:28:06 +0000 |
|---|---|---|
| committer | Pierre-Charles David | 2018-05-02 12:31:38 +0000 |
| commit | 27b00a81ce506c870da28da643b1c52a5a3acbc7 (patch) | |
| tree | 4b52ec578e2d020ded1e48497c5b283d93a86cd5 | |
| parent | 24d949e7850611eb8ec662c64877a041d8487105 (diff) | |
| download | org.eclipse.sirius-27b00a81ce506c870da28da643b1c52a5a3acbc7.tar.gz org.eclipse.sirius-27b00a81ce506c870da28da643b1c52a5a3acbc7.tar.xz org.eclipse.sirius-27b00a81ce506c870da28da643b1c52a5a3acbc7.zip | |
[481386] Execute rules that are defined in DiagramDescriptionExtension
* Now rule that are defined in DiagramDescriptionExtension which extend
the current DiagramDescription are taken from the same viewpoint and
from another viewpoint.
* Complete an existing test
bug: 481386
Change-Id: I88fbbd28d589ca015a0da9cbc85fe36be52fb135
Signed-off-by: Laurent Fasani <laurent.fasani@obeo.fr>
4 files changed, 105 insertions, 61 deletions
diff --git a/plugins/org.eclipse.sirius.diagram/src-core/org/eclipse/sirius/diagram/tools/api/validation/constraint/AbstractDDiagramConstraint.java b/plugins/org.eclipse.sirius.diagram/src-core/org/eclipse/sirius/diagram/tools/api/validation/constraint/AbstractDDiagramConstraint.java index 3f60761d6a..d21fd458d1 100644 --- a/plugins/org.eclipse.sirius.diagram/src-core/org/eclipse/sirius/diagram/tools/api/validation/constraint/AbstractDDiagramConstraint.java +++ b/plugins/org.eclipse.sirius.diagram/src-core/org/eclipse/sirius/diagram/tools/api/validation/constraint/AbstractDDiagramConstraint.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2007, 2015 THALES GLOBAL SERVICES. + * Copyright (c) 2007, 2018 THALES GLOBAL SERVICES. * 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 @@ -12,8 +12,9 @@ package org.eclipse.sirius.diagram.tools.api.validation.constraint; import java.util.ArrayList; import java.util.Collection; -import java.util.Collections; import java.util.Iterator; +import java.util.Objects; +import java.util.stream.Collectors; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.MultiStatus; @@ -23,7 +24,7 @@ import org.eclipse.emf.validation.EMFEventType; import org.eclipse.emf.validation.IValidationContext; import org.eclipse.emf.validation.model.ConstraintStatus; import org.eclipse.sirius.business.api.session.Session; -import org.eclipse.sirius.business.api.session.SessionManager; +import org.eclipse.sirius.business.internal.metamodel.helper.ComponentizationHelper; import org.eclipse.sirius.common.tools.api.util.StringUtil; import org.eclipse.sirius.diagram.DDiagram; import org.eclipse.sirius.diagram.DDiagramElement; @@ -31,6 +32,7 @@ import org.eclipse.sirius.diagram.DEdge; import org.eclipse.sirius.diagram.Messages; import org.eclipse.sirius.diagram.description.DiagramDescription; import org.eclipse.sirius.diagram.description.DiagramElementMapping; +import org.eclipse.sirius.diagram.description.DiagramExtensionDescription; import org.eclipse.sirius.tools.api.validation.constraint.RuleWrappingStatus; import org.eclipse.sirius.viewpoint.DSemanticDecorator; import org.eclipse.sirius.viewpoint.SiriusPlugin; @@ -42,9 +44,8 @@ import org.eclipse.sirius.viewpoint.description.validation.ValidationSet; import org.eclipse.sirius.viewpoint.description.validation.ViewValidationRule; /** - * Common class for all the DDiagram constraints. This class wrapp the base - * behavior of getting the first failling rule, clients should define the - * "isValid" method to say wether the rule match the current constraint or not. + * Common class for all the DDiagram constraints. This class wrapp the base behavior of getting the first failing rule, + * clients should define the "isValid" method to say whether the rule matches the current constraint or not. * * @author cbrun * @@ -103,8 +104,7 @@ public abstract class AbstractDDiagramConstraint extends AbstractModelConstraint * * @param objectToValidate * object we are testing. - * @return the first {@link ValidationRule} conform to isValid() which - * fails. + * @return the first {@link ValidationRule} conform to isValid() which fails. */ private Collection<ValidationRule> getFailingRules(final EObject objectToValidate) { final Collection<ValidationRule> failingRules = new ArrayList<ValidationRule>(); @@ -119,47 +119,56 @@ public abstract class AbstractDDiagramConstraint extends AbstractModelConstraint if (diagram != null) { /* - * If some rules are manually activated, then we'll pick in these - * ones, otherwhise we'll use all the rules. + * If some rules are manually activated, then we'll pick in these ones, otherwise we'll use all the rules. */ + Collection<Viewpoint> selectedVps = Session.of(objectToValidate).map(s -> s.getSelectedViewpoints(false)).orElseGet(() -> new ArrayList<Viewpoint>()); if (diagram.getActivatedRules().size() > 0) { - failingRules.addAll(getFaillingRulesFromCollection(objectToValidate, diagram.getActivatedRules().iterator())); + failingRules.addAll(getFailingRulesFromCollection(objectToValidate, diagram.getActivatedRules().iterator())); } else if (diagram.getDescription() != null) { final DiagramDescription desc = diagram.getDescription(); final ValidationSet validationSet = desc.getValidationSet(); if (validationSet != null) { - failingRules.addAll(getFaillingRulesFromCollection(objectToValidate, validationSet.getAllRules().iterator())); + failingRules.addAll(getFailingRulesFromCollection(objectToValidate, validationSet.getAllRules().iterator())); } + + failingRules.addAll(getFailingRulesFromDiagramExtension(objectToValidate, desc, selectedVps)); } - failingRules.addAll(checkRulesFromActivatedViewpoints(objectToValidate, diagram)); + failingRules.addAll(checkRulesFromActivatedViewpoints(objectToValidate, selectedVps)); } return failingRules; } - private Collection<ValidationRule> checkRulesFromActivatedViewpoints(final EObject objectToValidate, final DDiagram diagram) { - if (objectToValidate instanceof DSemanticDecorator) { - final EObject semantic = ((DSemanticDecorator) objectToValidate).getTarget(); - final Session session = SessionManager.INSTANCE.getSession(semantic); - if (session != null) { - final Iterator<Viewpoint> it = session.getSelectedViewpoints(false).iterator(); - while (it.hasNext()) { - final Viewpoint vp = it.next(); - if (vp.getValidationSet() != null) { - return getFaillingRulesFromCollection(objectToValidate, vp.getValidationSet().getAllRules().iterator()); - } - } - } - } + /** + * Get validation rules of RepresentationExtensionDescription (of provided viewpoints) that matches + * diagDescExtension. + * + * @param objectToValidate + * object we are testing. + * @param diagDescExtension + * DiagramDescription of the objectToValidate + * @param viewpoints + * viewpoints in which to find the RepresentationExtensionDescription + * @return + */ + private Collection<ValidationRule> getFailingRulesFromDiagramExtension(EObject objectToValidate, DiagramDescription diagDescExtension, Collection<Viewpoint> viewpoints) { + // get validation rules of RepresentationExtensionDescription that matches diagDescExtension + Collection<ValidationRule> failingRules = viewpoints.stream().flatMap(vp -> vp.getOwnedRepresentationExtensions().stream()).filter(DiagramExtensionDescription.class::isInstance) + .filter(ext -> ComponentizationHelper.match(diagDescExtension, ext)).map(ext -> ((DiagramExtensionDescription) ext).getValidationSet()).filter(Objects::nonNull) + .flatMap(vs -> getFailingRulesFromCollection(objectToValidate, vs.getAllRules().iterator()).stream()).collect(Collectors.toList()); + + return failingRules; + } - return Collections.emptyList(); + private Collection<ValidationRule> checkRulesFromActivatedViewpoints(final EObject objectToValidate, final Collection<Viewpoint> selectedVps) { + return selectedVps.stream().map(vp -> vp.getValidationSet()).filter(Objects::nonNull).flatMap(vs -> getFailingRulesFromCollection(objectToValidate, vs.getAllRules().iterator()).stream()) + .collect(Collectors.toList()); } - private Collection<ValidationRule> getFaillingRulesFromCollection(final EObject objectToValidate, final Iterator<ValidationRule> it) { + private Collection<ValidationRule> getFailingRulesFromCollection(final EObject objectToValidate, final Iterator<ValidationRule> it) { final Collection<ValidationRule> failingRules = new ArrayList<ValidationRule>(); /* - * Iterate and return the first failling rule. null if no rule is - * failling. + * Iterate and return the first failing rule. null if no rule is failing. */ while (it.hasNext()) { final ValidationRule rule = it.next(); @@ -191,8 +200,7 @@ public abstract class AbstractDDiagramConstraint extends AbstractModelConstraint * @param objectToValidate * The object to validate * @param semanticElement - * The semantic element associated with the - * <code>objectToValidate</code>. + * The semantic element associated with the <code>objectToValidate</code>. * @param expectedClass * The expected class for the semantic element. * @return true if the semantic element must be validate, false otherwise. @@ -218,13 +226,11 @@ public abstract class AbstractDDiagramConstraint extends AbstractModelConstraint } /** - * return true if this validation rule apply to the current context, false - * otherwise. + * return true if this validation rule apply to the current context, false otherwise. * * @param rule * a validation rule. - * @return true if this validation rule apply to the current context, false - * otherwise. + * @return true if this validation rule apply to the current context, false otherwise. */ protected abstract boolean isValid(ValidationRule rule); } diff --git a/plugins/org.eclipse.sirius.tests.junit/data/unit/validation/validationExt.odesign b/plugins/org.eclipse.sirius.tests.junit/data/unit/validation/validationExt.odesign new file mode 100644 index 0000000000..69b3f834ae --- /dev/null +++ b/plugins/org.eclipse.sirius.tests.junit/data/unit/validation/validationExt.odesign @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<description:Group xmi:version="2.0" xmlns:xmi="http://www.omg.org/XMI" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:description="http://www.eclipse.org/sirius/description/1.1.0" xmlns:description_1="http://www.eclipse.org/sirius/diagram/description/1.1.0" xmlns:validation="http://www.eclipse.org/sirius/description/validation/1.1.0" name="validationExt" version="12.0.0.2017041100"> + <ownedViewpoints name="ValidationExt" modelFileExtension="*.ecore"> + <ownedRepresentationExtensions xsi:type="description_1:DiagramExtensionDescription" name="DiagramExtension" viewpointURI="viewpoint:/org.eclipse.sirius.tests.junit/Ticket 1666" representationName="Validation"> + <validationSet> + <ownedRules xsi:type="validation:SemanticValidationRule" name="NameSizeRule" message="Name must start with p" targetClass="ecore::EClass"> + <audits auditExpression="aql:self.name.startsWith('p')"/> + </ownedRules> + </validationSet> + </ownedRepresentationExtensions> + </ownedViewpoints> +</description:Group> diff --git a/plugins/org.eclipse.sirius.tests.junit/src/org/eclipse/sirius/tests/unit/api/validation/DiagramValidationTest.java b/plugins/org.eclipse.sirius.tests.junit/src/org/eclipse/sirius/tests/unit/api/validation/DiagramValidationTest.java index 0634953fb8..cd4c7101a1 100644 --- a/plugins/org.eclipse.sirius.tests.junit/src/org/eclipse/sirius/tests/unit/api/validation/DiagramValidationTest.java +++ b/plugins/org.eclipse.sirius.tests.junit/src/org/eclipse/sirius/tests/unit/api/validation/DiagramValidationTest.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2010, 2017 THALES GLOBAL SERVICES. + * Copyright (c) 2010, 2018 THALES GLOBAL SERVICES. * 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 @@ -14,6 +14,9 @@ import static org.easymock.EasyMock.createMock; import static org.easymock.EasyMock.replay; import static org.easymock.EasyMock.verify; +import java.util.Arrays; +import java.util.Collections; + import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IMarker; import org.eclipse.core.resources.IResource; @@ -55,14 +58,20 @@ public class DiagramValidationTest extends SiriusDiagramTestCase { private static final String MODELER_PATH = "/" + SiriusTestsPlugin.PLUGIN_ID + "/data/unit/validation/ticket1666.odesign"; + private static final String MODELER_PATH_EXT = "/" + SiriusTestsPlugin.PLUGIN_ID + "/data/unit/validation/validationExt.odesign"; + private static final String VIEWPOINT_NAME = "Ticket 1666"; + private static final String VIEWPOINT_EXT_NAME = "ValidationExt"; + private static final String REPRESENTATION_DESC_NAME = "Validation"; private static final String REPRESENTATION_DESC_NAME_BREAKDOWN = "Breakdown"; private static final String ECLASS_NAME = "demo2"; + private static final String VALIDATION_RULE_EXT_MESSAGE = "Name must start with p"; + private DDiagram diagram; private IEditorPart editorPart; @@ -83,15 +92,17 @@ public class DiagramValidationTest extends SiriusDiagramTestCase { DiagramPlugin.getDefault().getLog().addLogListener(logListener); DiagramUIPlugin.getPlugin().getLog().addLogListener(logListener); - genericSetUp(SEMANTIC_MODEL_PATH, MODELER_PATH); + genericSetUp(Collections.singleton(SEMANTIC_MODEL_PATH), Arrays.asList(MODELER_PATH, MODELER_PATH_EXT), null); initViewpoint(VIEWPOINT_NAME); + initViewpoint(VIEWPOINT_EXT_NAME); subTicket1666_1EPackage = ((EPackage) semanticModel).getESubpackages().get(1); rootEPackage = ((EPackage) semanticModel).getESubpackages().get(2); } /** - * Test case. It checks that source point location of a specific edge does not change after zoom in operation. + * Check that validation is correctly done. </br> + * Check also that rules that are in diagram extension are correctly found. * * @throws Exception * Test error. @@ -111,15 +122,27 @@ public class DiagramValidationTest extends SiriusDiagramTestCase { WorkbenchPartDescriptor workbenchPartDescriptor = new WorkbenchPartDescriptor(editorPart.getSite().getId(), editorPart.getClass(), editorPart.getSite().getPage()); ValidateAction va = new ValidateAction(workbenchPartDescriptor); va.run(); + TestsUtil.synchronizationWithUIThread(); assertTrue("Validation constraint has not been called", ConstraintStub.hasBeenCalled()); // Get session .aird file to find validation warnings IFile file = WorkspaceSynchronizer.getFile(session.getSessionResource()); file.refreshLocal(1, new NullProgressMonitor()); + TestsUtil.synchronizationWithUIThread(); + IMarker[] findUIMarkers = file.findMarkers(SiriusMarkerNavigationProvider.MARKER_TYPE, true, IResource.DEPTH_INFINITE); assertTrue("At least one marker must be found", findUIMarkers.length >= 1); + boolean foundRuleInDiagExtension = Arrays.asList(findUIMarkers).stream().filter(m -> { + try { + return VALIDATION_RULE_EXT_MESSAGE.equals(m.getAttribute(IMarker.MESSAGE)); + } catch (CoreException e) { + } + return false; + }).count() > 0.; + assertTrue("Marker created by validation in the diagramExtension of other viewpoint was not found", foundRuleInDiagExtension); + boolean found = false; for (int i = 0; i < findUIMarkers.length && !found; i++) { IMarker iMarker = findUIMarkers[i]; @@ -139,11 +162,11 @@ public class DiagramValidationTest extends SiriusDiagramTestCase { } /** - * Test there is only one error by elements not validated and not many errors message duplicate for same element. - * See VP-2940 + * Test there is only one error by elements not validated and not many + * errors message duplicate for same element. See VP-2940 * - * Also check that there is only one semantic error for the root element. See - * https://bugs.eclipse.org/bugs/show_bug.cgi?id=441642 + * Also check that there is only one semantic error for the root element. + * See https://bugs.eclipse.org/bugs/show_bug.cgi?id=441642 * * @throws CoreException * Test errors. @@ -206,8 +229,8 @@ public class DiagramValidationTest extends SiriusDiagramTestCase { * @param foundMarkers * markers found * @param expectedNbViewMarker - * expected number of view marker for the first {@link DNode} with target equals to - * {@code semanticElement} + * expected number of view marker for the first {@link DNode} + * with target equals to {@code semanticElement} * @param expectedNbSemanticMarker * expected number of semantic marker for {@code semanticElement} */ diff --git a/plugins/org.eclipse.sirius/src/org/eclipse/sirius/business/internal/metamodel/helper/ComponentizationHelper.java b/plugins/org.eclipse.sirius/src/org/eclipse/sirius/business/internal/metamodel/helper/ComponentizationHelper.java index 1239d690a0..e2028d2949 100644 --- a/plugins/org.eclipse.sirius/src/org/eclipse/sirius/business/internal/metamodel/helper/ComponentizationHelper.java +++ b/plugins/org.eclipse.sirius/src/org/eclipse/sirius/business/internal/metamodel/helper/ComponentizationHelper.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2008, 2009 THALES GLOBAL SERVICES. + * Copyright (c) 2008, 2018 THALES GLOBAL SERVICES. * 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 @@ -22,8 +22,7 @@ import org.eclipse.sirius.viewpoint.description.RepresentationExtensionDescripti import org.eclipse.sirius.viewpoint.description.Viewpoint; /** - * This class helps to use the Imported Diagram and Diagram Extension on Sirius - * . + * This class helps to use the Imported Diagram and Diagram Extension on Sirius . * * @author amartin */ @@ -33,21 +32,28 @@ public final class ComponentizationHelper { } /** - * Tests whether a representation extension applies to an existing - * representation. + * Tests whether a representation extension applies to an existing representation. * * @param extension * the extension * @param representation * the existing representation - * @return <code>true</code> if the extension applies to the specified - * representation. + * @return <code>true</code> if the extension applies to the specified representation. */ public static boolean extensionAppliesTo(final RepresentationExtensionDescription extension, final DRepresentation representation) { return ComponentizationHelper.match(DialectManager.INSTANCE.getDescription(representation), extension); } - private static boolean match(final RepresentationDescription representationDescription, final RepresentationExtensionDescription representationExtensionDescription) { + /** + * Tests whether a representation description extension applies to an existing representation description. + * + * @param representationDescription + * the representationDescription + * @param representationExtensionDescription + * the existing representationExtensionDescription + * @return <code>true</code> if the extension applies to the specified representationDescription. + */ + public static boolean match(final RepresentationDescription representationDescription, final RepresentationExtensionDescription representationExtensionDescription) { if (representationDescription == null) { return false; } @@ -56,8 +62,7 @@ public final class ComponentizationHelper { private static boolean match(final EObject desc, final String descName, final RepresentationExtensionDescription representationExtensionDescription) { /* - * desc.eContainer might be null if desc is a proxy and we can't resolve - * it. + * desc.eContainer might be null if desc is a proxy and we can't resolve it. */ final EObject container = desc.eContainer(); if (container != null) { @@ -73,15 +78,13 @@ public final class ComponentizationHelper { } /** - * Check if one of the representation descriptions of the given baseSirius - * is extended by at least one representation extension descriptions of the - * given extensionSirius. + * Check if one of the representation descriptions of the given baseSirius is extended by at least one + * representation extension descriptions of the given extensionSirius. * * @param extensionSirius * the extension Sirius that may extends the given base viewpoint * @param baseSirius - * the base Sirius which may be extended by the given extension - * Sirius + * the base Sirius which may be extended by the given extension Sirius * @return true if the extensionSirius extends the baseSirius */ public static boolean isExtendedBy(final Viewpoint extensionSirius, final Viewpoint baseSirius) { |
