Skip to content

Commit

Permalink
Merge pull request #103 from LorenzoBettini/task_94-Avoid_duplicates
Browse files Browse the repository at this point in the history
Task 94 avoid duplicates
  • Loading branch information
LorenzoBettini committed Jan 20, 2020
2 parents 81aeb3f + eb8dd33 commit 2a7cc00
Show file tree
Hide file tree
Showing 2 changed files with 79 additions and 0 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -405,4 +405,48 @@ class EdeltaValidatorTest extends EdeltaAbstractTest {
def void testValidLibMethodsInModifyEcore() {
modifyEcoreUsingLibMethods.parseWithTestEcore.assertNoErrors
}

@Test
def void testDuplicateDeclarations() {
val input = '''
import java.util.List
import org.eclipse.emf.ecore.EPackage
metamodel "foo"
def myFun(List<Integer> l) {}
def myFun(List<String> l) {}
def anotherFun(List<String> l) {} // OK, different params
def anotherDuplicate(EPackage p) {} // conflicts with modifyEcore
modifyEcore aTest epackage foo {}
modifyEcore aTest epackage foo {}
modifyEcore anotherDuplicate epackage foo {} // implicit Java method param: EPackage
modifyEcore anotherFun epackage foo {} // OK, different params
'''
input.parseWithTestEcore => [
assertError(
EdeltaPackage.eINSTANCE.edeltaOperation,
EdeltaValidator.DUPLICATE_DECLARATION,
input.indexOf("anotherDuplicate"), "anotherDuplicate".length,
"Duplicate definition 'anotherDuplicate'"
)
assertError(
EdeltaPackage.eINSTANCE.edeltaModifyEcoreOperation,
EdeltaValidator.DUPLICATE_DECLARATION,
input.lastIndexOf("anotherDuplicate"), "anotherDuplicate".length,
"Duplicate definition 'anotherDuplicate'"
)
assertErrorsAsStrings(
'''
Duplicate definition 'aTest'
Duplicate definition 'aTest'
Duplicate definition 'anotherDuplicate'
Duplicate definition 'anotherDuplicate'
Duplicate definition 'myFun'
Duplicate definition 'myFun'
'''
)
]
}
}
35 changes: 35 additions & 0 deletions edelta.parent/edelta/src/edelta/validation/EdeltaValidator.xtend
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,18 @@
package edelta.validation

import com.google.inject.Inject
import edelta.edelta.EdeltaProgram
import edelta.edelta.EdeltaUseAs
import edelta.lib.AbstractEdelta
import org.eclipse.emf.ecore.EObject
import org.eclipse.xtext.common.types.JvmGenericType
import org.eclipse.xtext.common.types.JvmTypeReference
import org.eclipse.xtext.validation.Check
import org.eclipse.xtext.xbase.jvmmodel.IJvmModelAssociations
import org.eclipse.xtext.xbase.typesystem.^override.OverrideHelper
import org.eclipse.xtext.xbase.typesystem.references.StandardTypeReferenceOwner
import org.eclipse.xtext.xbase.typesystem.util.CommonTypeComputationServices
import org.eclipse.xtext.xbase.typesystem.util.Multimaps2

import static edelta.edelta.EdeltaPackage.Literals.*

Expand All @@ -25,8 +29,11 @@ class EdeltaValidator extends AbstractEdeltaValidator {
public static val PREFIX = "edelta.";
public static val TYPE_MISMATCH = PREFIX + "TypeMismatch";
public static val INTERPRETER_TIMEOUT = PREFIX + "InterpreterTimeout";
public static val DUPLICATE_DECLARATION = PREFIX + "DuplicateDeclaration";

@Inject CommonTypeComputationServices services
@Inject OverrideHelper overrideHelper
@Inject extension IJvmModelAssociations

@Check
def void checkValidUseAs(EdeltaUseAs useAs) {
Expand All @@ -52,6 +59,34 @@ class EdeltaValidator extends AbstractEdeltaValidator {
}
}

@Check
def void checkDuplicateDeclarations(EdeltaProgram p) {
val javaClass = p.jvmElements.filter(JvmGenericType).head
val methods = overrideHelper.getResolvedFeatures(javaClass).declaredOperations

val map = Multimaps2.newLinkedHashListMultimap

for (d : methods) {
map.put(d.resolvedErasureSignature, d.getDeclaration)
}

for (entry : map.asMap.entrySet) {
val duplicates = entry.value
if (duplicates.size > 1) {
for (d : duplicates) {
val source = d.primarySourceElement
error(
"Duplicate definition '" + d.simpleName + "'",
source,
source.eClass.getEStructuralFeature("name"),
DUPLICATE_DECLARATION
)
}
}
}
}


def isConformant(EObject context, Class<?> expected, JvmTypeReference actual) {
val actualType = actual.toLightweightTypeReference(context)
actualType.isSubtypeOf(expected)
Expand Down

0 comments on commit 2a7cc00

Please sign in to comment.