From e3c433c28b0233dfbb304f0953a282a9372d3cda Mon Sep 17 00:00:00 2001 From: Ertugrul Karademir Date: Mon, 29 Jan 2024 14:46:34 +0000 Subject: [PATCH] refactor(declarations): move declaration uniqueness check to model file (#794) * refactor(declarations): Move unique name check to model file. Signed-off-by: Ertugrul Karademir * refactor(test): move validation checks for duplicate class to model file Signed-off-by: Ertugrul Karademir * test: empty commit to trigger test Signed-off-by: Ertugrul Karademir --------- Signed-off-by: Ertugrul Karademir --- .../src/introspect/classdeclaration.js | 15 -------- .../concerto-core/src/introspect/modelfile.js | 16 ++++++++ .../test/introspect/modelfile.js | 37 +++++++++++++++++++ 3 files changed, 53 insertions(+), 15 deletions(-) diff --git a/packages/concerto-core/src/introspect/classdeclaration.js b/packages/concerto-core/src/introspect/classdeclaration.js index dd5c8dbeb..fad391cc4 100644 --- a/packages/concerto-core/src/introspect/classdeclaration.js +++ b/packages/concerto-core/src/introspect/classdeclaration.js @@ -201,21 +201,6 @@ class ClassDeclaration extends Declaration { validate() { super.validate(); - const declarations = this.getModelFile().getAllDeclarations(); - const declarationNames = declarations.map( - d => d.getFullyQualifiedName() - ); - const uniqueNames = new Set(declarationNames); - - if (uniqueNames.size !== declarations.length) { - const duplicateElements = declarationNames.filter( - (item, index) => declarationNames.indexOf(item) !== index - ); - throw new IllegalModelException( - `Duplicate class name ${duplicateElements[0]}` - ); - } - // if we have a super type make sure it exists if (this.superType !== null) { // and make sure that the class isn't extending itself diff --git a/packages/concerto-core/src/introspect/modelfile.js b/packages/concerto-core/src/introspect/modelfile.js index 1bff4ea16..6ca63ce8a 100644 --- a/packages/concerto-core/src/introspect/modelfile.js +++ b/packages/concerto-core/src/introspect/modelfile.js @@ -281,6 +281,22 @@ class ModelFile { }); // Validate all of the types in this model file. + // Check if names of the declarations are unique. + const declarationNames = this.declarations.map( + d => d.getFullyQualifiedName() + ); + const uniqueNames = new Set(declarationNames); + + if (uniqueNames.size !== this.declarations.length) { + const duplicateElements = declarationNames.filter( + (item, index) => declarationNames.indexOf(item) !== index + ); + throw new IllegalModelException( + `Duplicate class name ${duplicateElements[0]}` + ); + } + + // Run validations on class declarations for(let n=0; n < this.declarations.length; n++) { let classDeclaration = this.declarations[n]; classDeclaration.validate(); diff --git a/packages/concerto-core/test/introspect/modelfile.js b/packages/concerto-core/test/introspect/modelfile.js index 469af7d5d..793d22aaf 100644 --- a/packages/concerto-core/test/introspect/modelfile.js +++ b/packages/concerto-core/test/introspect/modelfile.js @@ -44,10 +44,12 @@ describe('ModelFile', () => { const carLeaseModel = fs.readFileSync(path.resolve(__dirname, '../data/model/carlease.cto'), 'utf8'); let modelManager; let sandbox; + let introspectUtils; beforeEach(() => { modelManager = new ModelManager(); Util.addComposerModel(modelManager); + introspectUtils = new IntrospectUtils(modelManager); sandbox = sinon.createSandbox(); }); @@ -204,6 +206,41 @@ describe('ModelFile', () => { describe('#validate', () => { + it('should throw when asset name is duplicted in a modelfile', () => { + let asset = introspectUtils.loadModelFile('test/data/parser/classdeclaration.dupeassetname.cto'); + (() => { + asset.validate(); + }).should.throw(/Duplicate class/); + }); + + it('should throw when transaction name is duplicted in a modelfile', () => { + let asset = introspectUtils.loadModelFile('test/data/parser/classdeclaration.dupetransactionname.cto'); + (() => { + asset.validate(); + }).should.throw(/Duplicate class/); + }); + + it('should throw when participant name is duplicted in a modelfile', () => { + let asset = introspectUtils.loadModelFile('test/data/parser/classdeclaration.dupeparticipantname.cto'); + (() => { + asset.validate(); + }).should.throw(/Duplicate class/); + }); + + it('should throw when concept name is duplicted in a modelfile', () => { + let asset = introspectUtils.loadModelFile('test/data/parser/classdeclaration.dupeconceptname.cto'); + (() => { + asset.validate(); + }).should.throw(/Duplicate class/); + }); + + it('should throw when enum name is duplicted in a modelfile', () => { + let asset = introspectUtils.loadModelFile('test/data/parser/classdeclaration.dupeenumname.cto'); + (() => { + asset.validate(); + }).should.throw(/Duplicate class/); + }); + it('should throw if an import exists for an invalid namespace', () => { const model = ` namespace org.acme@1.0.0