From 280aed8e609ca5c9243a8d749e6d974cebc2f47e Mon Sep 17 00:00:00 2001
From: fedoreno <fedoreno>
Date: Thu, 10 Mar 2016 10:41:31 +0000
Subject: [PATCH] SSDM-3284: fixing dtos with missing fields/logic

SVN: 35865
---
 .../openbis-v3-api-test/html/test/common.js   | 176 ++++++++----------
 .../openbis-v3-api-test/html/test/dtos.js     | 165 ++++++++++++++++
 .../openbis-v3-api-test/html/test/main.js     |  14 +-
 .../html/test/test-custom-services.js         |   4 +-
 .../html/test/test-dto-roundtrip.js           | 110 +++++++++++
 .../openbis-v3-api-test/html/test/test-dto.js |  45 +++--
 .../jstest/service/V3ApiDtoTestService.java   |  68 +++++--
 7 files changed, 445 insertions(+), 137 deletions(-)
 create mode 100644 js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/dtos.js
 create mode 100644 js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto-roundtrip.js

diff --git a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/common.js b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/common.js
index 5e8ff6dfa4f..86cfa8af3c8 100644
--- a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/common.js
+++ b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/common.js
@@ -1,24 +1,4 @@
-define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/project/create/ProjectCreation', 'as/dto/experiment/create/ExperimentCreation', 'as/dto/sample/create/SampleCreation',
-		'as/dto/material/create/MaterialCreation', 'as/dto/attachment/create/AttachmentCreation', 'as/dto/space/update/SpaceUpdate', 'as/dto/project/update/ProjectUpdate',
-		'as/dto/experiment/update/ExperimentUpdate', 'as/dto/sample/update/SampleUpdate', 'as/dto/dataset/update/DataSetUpdate', 'as/dto/dataset/update/PhysicalDataUpdate',
-		'as/dto/material/update/MaterialUpdate', 'as/dto/space/delete/SpaceDeletionOptions', 'as/dto/project/delete/ProjectDeletionOptions', 'as/dto/experiment/delete/ExperimentDeletionOptions',
-		'as/dto/sample/delete/SampleDeletionOptions', 'as/dto/dataset/delete/DataSetDeletionOptions', 'as/dto/material/delete/MaterialDeletionOptions', 'as/dto/entitytype/id/EntityTypePermId',
-		'as/dto/space/id/SpacePermId', 'as/dto/project/id/ProjectPermId', 'as/dto/project/id/ProjectIdentifier', 'as/dto/experiment/id/ExperimentPermId', 'as/dto/experiment/id/ExperimentIdentifier',
-		'as/dto/sample/id/SamplePermId', 'as/dto/dataset/id/DataSetPermId', 'as/dto/dataset/id/FileFormatTypePermId', 'as/dto/material/id/MaterialPermId', 'as/dto/tag/id/TagCode',
-		'as/dto/space/search/SpaceSearchCriteria', 'as/dto/project/search/ProjectSearchCriteria', 'as/dto/experiment/search/ExperimentSearchCriteria', 'as/dto/sample/search/SampleSearchCriteria',
-		'as/dto/dataset/search/DataSetSearchCriteria', 'as/dto/material/search/MaterialSearchCriteria', 'as/dto/space/fetchoptions/SpaceFetchOptions',
-		'as/dto/project/fetchoptions/ProjectFetchOptions', 'as/dto/experiment/fetchoptions/ExperimentFetchOptions', 'as/dto/sample/fetchoptions/SampleFetchOptions',
-		'as/dto/dataset/fetchoptions/DataSetFetchOptions', 'as/dto/material/fetchoptions/MaterialFetchOptions', 'as/dto/deletion/fetchoptions/DeletionFetchOptions',
-		'as/dto/deletion/search/DeletionSearchCriteria', 'as/dto/service/search/CustomASServiceSearchCriteria', 'as/dto/service/fetchoptions/CustomASServiceFetchOptions',
-		'as/dto/service/id/CustomASServiceCode', 'as/dto/service/CustomASServiceExecutionOptions', 'as/dto/global/search/GlobalSearchCriteria',
-		'as/dto/global/fetchoptions/GlobalSearchObjectFetchOptions', 'as/dto/objectkindmodification/search/ObjectKindModificationSearchCriteria',
-		'as/dto/objectkindmodification/fetchoptions/ObjectKindModificationFetchOptions' ], function($, openbis, SpaceCreation, ProjectCreation, ExperimentCreation, SampleCreation, MaterialCreation,
-		AttachmentCreation, SpaceUpdate, ProjectUpdate, ExperimentUpdate, SampleUpdate, DataSetUpdate, PhysicalDataUpdate, MaterialUpdate, SpaceDeletionOptions, ProjectDeletionOptions,
-		ExperimentDeletionOptions, SampleDeletionOptions, DataSetDeletionOptions, MaterialDeletionOptions, EntityTypePermId, SpacePermId, ProjectPermId, ProjectIdentifier, ExperimentPermId,
-		ExperimentIdentifier, SamplePermId, DataSetPermId, FileFormatTypePermId, MaterialPermId, TagCode, SpaceSearchCriteria, ProjectSearchCriteria, ExperimentSearchCriteria, SampleSearchCriteria,
-		DataSetSearchCriteria, MaterialSearchCriteria, SpaceFetchOptions, ProjectFetchOptions, ExperimentFetchOptions, SampleFetchOptions, DataSetFetchOptions, MaterialFetchOptions,
-		DeletionFetchOptions, DeletionSearchCriteria, CustomASServiceSearchCriteria, CustomASServiceFetchOptions, CustomASServiceCode, CustomASServiceExecutionOptions, GlobalSearchCriteria,
-		GlobalSearchObjectFetchOptions, ObjectKindModificationSearchCriteria, ObjectKindModificationFetchOptions) {
+define([ 'jquery', 'openbis', 'underscore', 'test/dtos' ], function($, openbis, _, dtos) {
 
 	/*
 	 * These tests should be run against openBIS instance with screening sprint
@@ -37,58 +17,62 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 	var Common = function(assert) {
 		this.assert = assert;
 
-		this.SpaceCreation = SpaceCreation;
-		this.ProjectCreation = ProjectCreation;
-		this.ExperimentCreation = ExperimentCreation;
-		this.SampleCreation = SampleCreation;
-		this.MaterialCreation = MaterialCreation;
-		this.AttachmentCreation = AttachmentCreation;
-		this.SpaceUpdate = SpaceUpdate;
-		this.ProjectUpdate = ProjectUpdate;
-		this.ExperimentUpdate = ExperimentUpdate;
-		this.SampleUpdate = SampleUpdate;
-		this.DataSetUpdate = DataSetUpdate;
-		this.PhysicalDataUpdate = PhysicalDataUpdate;
-		this.MaterialUpdate = MaterialUpdate;
-		this.SpaceDeletionOptions = SpaceDeletionOptions;
-		this.ProjectDeletionOptions = ProjectDeletionOptions;
-		this.ExperimentDeletionOptions = ExperimentDeletionOptions;
-		this.SampleDeletionOptions = SampleDeletionOptions;
-		this.DataSetDeletionOptions = DataSetDeletionOptions;
-		this.MaterialDeletionOptions = MaterialDeletionOptions;
-		this.EntityTypePermId = EntityTypePermId;
-		this.SpacePermId = SpacePermId;
-		this.ProjectPermId = ProjectPermId;
-		this.ProjectIdentifier = ProjectIdentifier;
-		this.ExperimentPermId = ExperimentPermId;
-		this.ExperimentIdentifier = ExperimentIdentifier;
-		this.SamplePermId = SamplePermId;
-		this.DataSetPermId = DataSetPermId;
-		this.FileFormatTypePermId = FileFormatTypePermId;
-		this.MaterialPermId = MaterialPermId;
-		this.TagCode = TagCode;
-		this.SpaceSearchCriteria = SpaceSearchCriteria;
-		this.ProjectSearchCriteria = ProjectSearchCriteria;
-		this.ExperimentSearchCriteria = ExperimentSearchCriteria;
-		this.SampleSearchCriteria = SampleSearchCriteria;
-		this.DataSetSearchCriteria = DataSetSearchCriteria;
-		this.MaterialSearchCriteria = MaterialSearchCriteria;
-		this.SpaceFetchOptions = SpaceFetchOptions;
-		this.ProjectFetchOptions = ProjectFetchOptions;
-		this.ExperimentFetchOptions = ExperimentFetchOptions;
-		this.SampleFetchOptions = SampleFetchOptions;
-		this.DataSetFetchOptions = DataSetFetchOptions;
-		this.MaterialFetchOptions = MaterialFetchOptions;
-		this.DeletionFetchOptions = DeletionFetchOptions;
-		this.DeletionSearchCriteria = DeletionSearchCriteria;
-		this.CustomASServiceSearchCriteria = CustomASServiceSearchCriteria;
-		this.CustomASServiceFetchOptions = CustomASServiceFetchOptions;
-		this.CustomASServiceCode = CustomASServiceCode;
-		this.CustomASServiceExecutionOptions = CustomASServiceExecutionOptions;
-		this.GlobalSearchCriteria = GlobalSearchCriteria;
-		this.GlobalSearchObjectFetchOptions = GlobalSearchObjectFetchOptions;
-		this.ObjectKindModificationSearchCriteria = ObjectKindModificationSearchCriteria;
-		this.ObjectKindModificationFetchOptions = ObjectKindModificationFetchOptions;
+		this.SpaceCreation = dtos.SpaceCreation;
+		this.ProjectCreation = dtos.ProjectCreation;
+		this.ExperimentCreation = dtos.ExperimentCreation;
+		this.SampleCreation = dtos.SampleCreation;
+		this.MaterialCreation = dtos.MaterialCreation;
+		this.AttachmentCreation = dtos.AttachmentCreation;
+		this.SpaceUpdate = dtos.SpaceUpdate;
+		this.ProjectUpdate = dtos.ProjectUpdate;
+		this.ExperimentUpdate = dtos.ExperimentUpdate;
+		this.SampleUpdate = dtos.SampleUpdate;
+		this.DataSetUpdate = dtos.DataSetUpdate;
+		this.PhysicalDataUpdate = dtos.PhysicalDataUpdate;
+		this.MaterialUpdate = dtos.MaterialUpdate;
+		this.SpaceDeletionOptions = dtos.SpaceDeletionOptions;
+		this.ProjectDeletionOptions = dtos.ProjectDeletionOptions;
+		this.ExperimentDeletionOptions = dtos.ExperimentDeletionOptions;
+		this.SampleDeletionOptions = dtos.SampleDeletionOptions;
+		this.DataSetDeletionOptions = dtos.DataSetDeletionOptions;
+		this.MaterialDeletionOptions = dtos.MaterialDeletionOptions;
+		this.EntityTypePermId = dtos.EntityTypePermId;
+		this.SpacePermId = dtos.SpacePermId;
+		this.ProjectPermId = dtos.ProjectPermId;
+		this.ProjectIdentifier = dtos.ProjectIdentifier;
+		this.ExperimentPermId = dtos.ExperimentPermId;
+		this.ExperimentIdentifier = dtos.ExperimentIdentifier;
+		this.SamplePermId = dtos.SamplePermId;
+		this.DataSetPermId = dtos.DataSetPermId;
+		this.FileFormatTypePermId = dtos.FileFormatTypePermId;
+		this.MaterialPermId = dtos.MaterialPermId;
+		this.TagCode = dtos.TagCode;
+		this.SpaceSearchCriteria = dtos.SpaceSearchCriteria;
+		this.ProjectSearchCriteria = dtos.ProjectSearchCriteria;
+		this.ExperimentSearchCriteria = dtos.ExperimentSearchCriteria;
+		this.SampleSearchCriteria = dtos.SampleSearchCriteria;
+		this.DataSetSearchCriteria = dtos.DataSetSearchCriteria;
+		this.MaterialSearchCriteria = dtos.MaterialSearchCriteria;
+		this.SpaceFetchOptions = dtos.SpaceFetchOptions;
+		this.ProjectFetchOptions = dtos.ProjectFetchOptions;
+		this.ExperimentFetchOptions = dtos.ExperimentFetchOptions;
+		this.SampleFetchOptions = dtos.SampleFetchOptions;
+		this.DataSetFetchOptions = dtos.DataSetFetchOptions;
+		this.MaterialFetchOptions = dtos.MaterialFetchOptions;
+		this.DeletionFetchOptions = dtos.DeletionFetchOptions;
+		this.DeletionSearchCriteria = dtos.DeletionSearchCriteria;
+		this.CustomASServiceSearchCriteria = dtos.CustomASServiceSearchCriteria;
+		this.CustomASServiceFetchOptions = dtos.CustomASServiceFetchOptions;
+		this.CustomASServiceCode = dtos.CustomASServiceCode;
+		this.CustomASServiceExecutionOptions = dtos.CustomASServiceExecutionOptions;
+		this.GlobalSearchCriteria = dtos.GlobalSearchCriteria;
+		this.GlobalSearchObjectFetchOptions = dtos.GlobalSearchObjectFetchOptions;
+		this.ObjectKindModificationSearchCriteria = dtos.ObjectKindModificationSearchCriteria;
+		this.ObjectKindModificationFetchOptions = dtos.ObjectKindModificationFetchOptions;
+
+		this.getDtos = function() {
+			return dtos;
+		}
 
 		this.generateId = function(base) {
 			var date = new Date();
@@ -98,7 +82,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 
 		this.createSpace = function(facade) {
 			var c = this;
-			var creation = new SpaceCreation();
+			var creation = new dtos.SpaceCreation();
 			creation.setCode(c.generateId("SPACE"));
 			return facade.createSpaces([ creation ]).then(function(permIds) {
 				return permIds[0];
@@ -108,7 +92,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		this.createProject = function(facade) {
 			var c = this;
 			return c.createSpace(facade).then(function(spacePermId) {
-				var creation = new ProjectCreation();
+				var creation = new dtos.ProjectCreation();
 				creation.setCode(c.generateId("PROJECT"));
 				creation.setSpaceId(spacePermId);
 				return facade.createProjects([ creation ]).then(function(permIds) {
@@ -120,9 +104,9 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		this.createExperiment = function(facade) {
 			var c = this;
 			return c.createProject(facade).then(function(projectPermId) {
-				var creation = new ExperimentCreation();
+				var creation = new dtos.ExperimentCreation();
 				creation.setCode(c.generateId("EXPERIMENT"));
-				creation.setTypeId(new EntityTypePermId("UNKNOWN"));
+				creation.setTypeId(new dtos.EntityTypePermId("UNKNOWN"));
 				creation.setProjectId(projectPermId);
 				return facade.createExperiments([ creation ]).then(function(permIds) {
 					return permIds[0];
@@ -133,9 +117,9 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		this.createSample = function(facade) {
 			var c = this;
 			return c.createSpace(facade).then(function(spacePermId) {
-				var creation = new SampleCreation();
+				var creation = new dtos.SampleCreation();
 				creation.setCode(c.generateId("SAMPLE"));
-				creation.setTypeId(new EntityTypePermId("UNKNOWN"));
+				creation.setTypeId(new dtos.EntityTypePermId("UNKNOWN"));
 				creation.setSpaceId(spacePermId);
 				return facade.createSamples([ creation ]).then(function(permIds) {
 					return permIds[0];
@@ -146,7 +130,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		this.createDataSet = function(facade) {
 			var c = this;
 			return this.getResponseFromJSTestAggregationService(facade, {}, function(response) {
-				return new DataSetPermId(response.result.rows[0][0].value);
+				return new dtos.DataSetPermId(response.result.rows[0][0].value);
 			});
 		}.bind(this);
 
@@ -168,9 +152,9 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 
 		this.createMaterial = function(facade) {
 			var c = this;
-			var creation = new MaterialCreation();
+			var creation = new dtos.MaterialCreation();
 			creation.setCode(c.generateId("MATERIAL"));
-			creation.setTypeId(new EntityTypePermId("COMPOUND"));
+			creation.setTypeId(new dtos.EntityTypePermId("COMPOUND"));
 			return facade.createMaterials([ creation ]).then(function(permIds) {
 				return permIds[0];
 			});
@@ -220,42 +204,42 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 
 		this.deleteSpace = function(facade, id) {
 			var c = this;
-			var options = new SpaceDeletionOptions();
+			var options = new dtos.SpaceDeletionOptions();
 			options.setReason("test reason");
 			return facade.deleteSpaces([ id ], options);
 		}.bind(this);
 
 		this.deleteProject = function(facade, id) {
 			var c = this;
-			var options = new ProjectDeletionOptions();
+			var options = new dtos.ProjectDeletionOptions();
 			options.setReason("test reason");
 			return facade.deleteProjects([ id ], options);
 		}.bind(this);
 
 		this.deleteExperiment = function(facade, id) {
 			var c = this;
-			var options = new ExperimentDeletionOptions();
+			var options = new dtos.ExperimentDeletionOptions();
 			options.setReason("test reason");
 			return facade.deleteExperiments([ id ], options);
 		}.bind(this);
 
 		this.deleteSample = function(facade, id) {
 			var c = this;
-			var options = new SampleDeletionOptions();
+			var options = new dtos.SampleDeletionOptions();
 			options.setReason("test reason");
 			return facade.deleteSamples([ id ], options);
 		}.bind(this);
 
 		this.deleteDataSet = function(facade, id) {
 			var c = this;
-			var options = new DataSetDeletionOptions();
+			var options = new dtos.DataSetDeletionOptions();
 			options.setReason("test reason");
 			return facade.deleteDataSets([ id ], options);
 		}.bind(this);
 
 		this.deleteMaterial = function(facade, id) {
 			var c = this;
-			var options = new MaterialDeletionOptions();
+			var options = new dtos.MaterialDeletionOptions();
 			options.setReason("test reason");
 			return facade.deleteMaterials([ id ], options);
 		}.bind(this);
@@ -289,7 +273,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createSpaceFetchOptions = function() {
-			var fo = new SpaceFetchOptions();
+			var fo = new dtos.SpaceFetchOptions();
 			fo.withProjects();
 			fo.withSamples();
 			fo.withRegistrator();
@@ -297,7 +281,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createProjectFetchOptions = function() {
-			var fo = new ProjectFetchOptions();
+			var fo = new dtos.ProjectFetchOptions();
 			fo.withSpace();
 			fo.withExperiments();
 			fo.withRegistrator();
@@ -308,7 +292,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createExperimentFetchOptions = function() {
-			var fo = new ExperimentFetchOptions();
+			var fo = new dtos.ExperimentFetchOptions();
 			fo.withType();
 			fo.withProject().withSpace();
 			fo.withDataSets();
@@ -324,7 +308,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createSampleFetchOptions = function() {
-			var fo = new SampleFetchOptions();
+			var fo = new dtos.SampleFetchOptions();
 			fo.withType();
 			fo.withExperiment().withProject().withSpace();
 			fo.withSpace();
@@ -345,7 +329,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createDataSetFetchOptions = function() {
-			var fo = new DataSetFetchOptions();
+			var fo = new dtos.DataSetFetchOptions();
 			fo.withType();
 			fo.withExperiment().withProject().withSpace();
 			fo.withSample();
@@ -366,7 +350,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createMaterialFetchOptions = function() {
-			var fo = new MaterialFetchOptions();
+			var fo = new dtos.MaterialFetchOptions();
 			fo.withType();
 			fo.withHistory();
 			fo.withRegistrator();
@@ -377,7 +361,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 
 		this.createGlobalSearchObjectFetchOptions = function() {
-			var fo = new GlobalSearchObjectFetchOptions();
+			var fo = new dtos.GlobalSearchObjectFetchOptions();
 			fo.withExperiment();
 			fo.withSample();
 			fo.withDataSet();
@@ -386,7 +370,7 @@ define([ 'jquery', 'openbis', 'as/dto/space/create/SpaceCreation', 'as/dto/proje
 		};
 		
 		this.createObjectKindModificationFetchOptions = function() {
-			var fo = new ObjectKindModificationFetchOptions();
+			var fo = new dtos.ObjectKindModificationFetchOptions();
 			return fo;
 		};
 
diff --git a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/dtos.js b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/dtos.js
new file mode 100644
index 00000000000..c890c19c8c0
--- /dev/null
+++ b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/dtos.js
@@ -0,0 +1,165 @@
+define(['as/dto/space/create/SpaceCreation',
+		'as/dto/project/create/ProjectCreation',
+		'as/dto/experiment/create/ExperimentCreation',
+		'as/dto/sample/create/SampleCreation',
+		'as/dto/material/create/MaterialCreation',
+		'as/dto/attachment/create/AttachmentCreation',
+		'as/dto/space/update/SpaceUpdate',
+		'as/dto/project/update/ProjectUpdate',
+		'as/dto/experiment/update/ExperimentUpdate',
+		'as/dto/sample/update/SampleUpdate',
+		'as/dto/dataset/update/DataSetUpdate',
+		'as/dto/dataset/update/PhysicalDataUpdate',
+		'as/dto/material/update/MaterialUpdate',
+		'as/dto/space/delete/SpaceDeletionOptions',
+		'as/dto/project/delete/ProjectDeletionOptions',
+		'as/dto/experiment/delete/ExperimentDeletionOptions',
+		'as/dto/sample/delete/SampleDeletionOptions',
+		'as/dto/dataset/delete/DataSetDeletionOptions',
+		'as/dto/material/delete/MaterialDeletionOptions',
+		'as/dto/entitytype/id/EntityTypePermId',
+		'as/dto/space/id/SpacePermId',
+		'as/dto/project/id/ProjectPermId',
+		'as/dto/project/id/ProjectIdentifier',
+		'as/dto/experiment/id/ExperimentPermId',
+		'as/dto/experiment/id/ExperimentIdentifier',
+		'as/dto/sample/id/SamplePermId',
+		'as/dto/dataset/id/DataSetPermId',
+		'as/dto/dataset/id/FileFormatTypePermId',
+		'as/dto/material/id/MaterialPermId',
+		'as/dto/tag/id/TagCode',
+		'as/dto/space/search/SpaceSearchCriteria',
+		'as/dto/project/search/ProjectSearchCriteria',
+		'as/dto/experiment/search/ExperimentSearchCriteria',
+		'as/dto/sample/search/SampleSearchCriteria',
+		'as/dto/dataset/search/DataSetSearchCriteria',
+		'as/dto/material/search/MaterialSearchCriteria',
+		'as/dto/space/fetchoptions/SpaceFetchOptions',
+		'as/dto/project/fetchoptions/ProjectFetchOptions',
+		'as/dto/experiment/fetchoptions/ExperimentFetchOptions',
+		'as/dto/sample/fetchoptions/SampleFetchOptions',
+		'as/dto/dataset/fetchoptions/DataSetFetchOptions',
+		'as/dto/material/fetchoptions/MaterialFetchOptions',
+		'as/dto/deletion/fetchoptions/DeletionFetchOptions',
+		'as/dto/deletion/search/DeletionSearchCriteria',
+		'as/dto/service/search/CustomASServiceSearchCriteria',
+		'as/dto/service/fetchoptions/CustomASServiceFetchOptions',
+		'as/dto/service/id/CustomASServiceCode',
+		'as/dto/service/CustomASServiceExecutionOptions',
+		'as/dto/global/search/GlobalSearchCriteria',
+		'as/dto/global/fetchoptions/GlobalSearchObjectFetchOptions',
+		'as/dto/objectkindmodification/search/ObjectKindModificationSearchCriteria',
+		'as/dto/objectkindmodification/fetchoptions/ObjectKindModificationFetchOptions' ], 
+		function(
+			SpaceCreation,
+			ProjectCreation,
+			ExperimentCreation,
+			SampleCreation,
+			MaterialCreation,
+			AttachmentCreation,
+			SpaceUpdate,
+			ProjectUpdate,
+			ExperimentUpdate,
+			SampleUpdate,
+			DataSetUpdate,
+			PhysicalDataUpdate,
+			MaterialUpdate,
+			SpaceDeletionOptions,
+			ProjectDeletionOptions,
+			ExperimentDeletionOptions,
+			SampleDeletionOptions,
+			DataSetDeletionOptions,
+			MaterialDeletionOptions,
+			EntityTypePermId,
+			SpacePermId,
+			ProjectPermId,
+			ProjectIdentifier,
+			ExperimentPermId,
+			ExperimentIdentifier,
+			SamplePermId,
+			DataSetPermId,
+			FileFormatTypePermId,
+			MaterialPermId,
+			TagCode,
+			SpaceSearchCriteria,
+			ProjectSearchCriteria,
+			ExperimentSearchCriteria,
+			SampleSearchCriteria,
+			DataSetSearchCriteria,
+			MaterialSearchCriteria,
+			SpaceFetchOptions,
+			ProjectFetchOptions,
+			ExperimentFetchOptions,
+			SampleFetchOptions,
+			DataSetFetchOptions,
+			MaterialFetchOptions,
+			DeletionFetchOptions,
+			DeletionSearchCriteria,
+			CustomASServiceSearchCriteria,
+			CustomASServiceFetchOptions,
+			CustomASServiceCode,
+			CustomASServiceExecutionOptions,
+			GlobalSearchCriteria,
+			GlobalSearchObjectFetchOptions,
+			ObjectKindModificationSearchCriteria,
+			ObjectKindModificationFetchOptions) 
+{
+
+	var Dtos = function() {
+
+		this.SpaceCreation = SpaceCreation;
+		this.ProjectCreation = ProjectCreation;
+		this.ExperimentCreation = ExperimentCreation;
+		this.SampleCreation = SampleCreation;
+		this.MaterialCreation = MaterialCreation;
+		this.AttachmentCreation = AttachmentCreation;
+		this.SpaceUpdate = SpaceUpdate;
+		this.ProjectUpdate = ProjectUpdate;
+		this.ExperimentUpdate = ExperimentUpdate;
+		this.SampleUpdate = SampleUpdate;
+		this.DataSetUpdate = DataSetUpdate;
+		this.PhysicalDataUpdate = PhysicalDataUpdate;
+		this.MaterialUpdate = MaterialUpdate;
+		this.SpaceDeletionOptions = SpaceDeletionOptions;
+		this.ProjectDeletionOptions = ProjectDeletionOptions;
+		this.ExperimentDeletionOptions = ExperimentDeletionOptions;
+		this.SampleDeletionOptions = SampleDeletionOptions;
+		this.DataSetDeletionOptions = DataSetDeletionOptions;
+		this.MaterialDeletionOptions = MaterialDeletionOptions;
+		this.EntityTypePermId = EntityTypePermId;
+		this.SpacePermId = SpacePermId;
+		this.ProjectPermId = ProjectPermId;
+		this.ProjectIdentifier = ProjectIdentifier;
+		this.ExperimentPermId = ExperimentPermId;
+		this.ExperimentIdentifier = ExperimentIdentifier;
+		this.SamplePermId = SamplePermId;
+		this.DataSetPermId = DataSetPermId;
+		this.FileFormatTypePermId = FileFormatTypePermId;
+		this.MaterialPermId = MaterialPermId;
+		this.TagCode = TagCode;
+		this.SpaceSearchCriteria = SpaceSearchCriteria;
+		this.ProjectSearchCriteria = ProjectSearchCriteria;
+		this.ExperimentSearchCriteria = ExperimentSearchCriteria;
+		this.SampleSearchCriteria = SampleSearchCriteria;
+		this.DataSetSearchCriteria = DataSetSearchCriteria;
+		this.MaterialSearchCriteria = MaterialSearchCriteria;
+		this.SpaceFetchOptions = SpaceFetchOptions;
+		this.ProjectFetchOptions = ProjectFetchOptions;
+		this.ExperimentFetchOptions = ExperimentFetchOptions;
+		this.SampleFetchOptions = SampleFetchOptions;
+		this.DataSetFetchOptions = DataSetFetchOptions;
+		this.MaterialFetchOptions = MaterialFetchOptions;
+		this.DeletionFetchOptions = DeletionFetchOptions;
+		this.DeletionSearchCriteria = DeletionSearchCriteria;
+		this.CustomASServiceSearchCriteria = CustomASServiceSearchCriteria;
+		this.CustomASServiceFetchOptions = CustomASServiceFetchOptions;
+		this.CustomASServiceCode = CustomASServiceCode;
+		this.CustomASServiceExecutionOptions = CustomASServiceExecutionOptions;
+		this.GlobalSearchCriteria = GlobalSearchCriteria;
+		this.GlobalSearchObjectFetchOptions = GlobalSearchObjectFetchOptions;
+		this.ObjectKindModificationSearchCriteria = ObjectKindModificationSearchCriteria;
+		this.ObjectKindModificationFetchOptions = ObjectKindModificationFetchOptions;
+
+	};
+	return new Dtos();
+})
diff --git a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/main.js b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/main.js
index b84adf7db28..19f4d808bac 100644
--- a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/main.js
+++ b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/main.js
@@ -1,5 +1,15 @@
-define([ 'test/test-login', 'test/test-jsVSjava', 'test/test-create', 'test/test-update', 'test/test-search', 
-         'test/test-map', 'test/test-delete', 'test/test-dto', 'test/test-custom-services' ], function() {
+define([ 
+         'test/test-login', 
+         'test/test-jsVSjava', 
+         'test/test-create', 'test/test-update', 'test/test-search', 
+
+         'test/test-map', 
+         'test/test-delete', 
+
+         'test/test-dto', 
+         'test/test-dto-roundtrip', 
+         'test/test-custom-services' 
+         ], function() {
 	var testSuites = arguments;
 	return function() {
 		for (var i = 0; i < testSuites.length; i++) {
diff --git a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-custom-services.js b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-custom-services.js
index 3f5fa396f53..b9ebef28d84 100644
--- a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-custom-services.js
+++ b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-custom-services.js
@@ -39,7 +39,7 @@ define(['jquery', 'underscore', 'openbis', 'test/common'], function($, _, openbi
 			}
 			
 			testAction(c, fAction, fCheck);
-		})
+		});
 		
 		QUnit.test("executeCustomASService()", function(assert){
 			var c = new common(assert);
@@ -60,6 +60,6 @@ define(['jquery', 'underscore', 'openbis', 'test/common'], function($, _, openbi
 			}
 			
 			testAction(c, fAction, fCheck);
-		})
+		});
 	}
 })
\ No newline at end of file
diff --git a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto-roundtrip.js b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto-roundtrip.js
new file mode 100644
index 00000000000..38786ebb264
--- /dev/null
+++ b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto-roundtrip.js
@@ -0,0 +1,110 @@
+define(['jquery', 'underscore', 'openbis', 'test/common'], function($, _, openbis, common) {
+	return function() {
+		QUnit.module("Dto roundtrip test");
+
+		var testAction = function(c, fAction, fCheck) {
+			c.start();
+
+			c.createFacadeAndLogin()
+				.then(function(facade) {
+					c.ok("Login");
+					return fAction(facade);
+				})
+				.then(function(res) {
+					c.ok("Sent data. Checking results...");
+					return fCheck(res);
+				})
+				.then(function() {
+					c.finish();
+				})
+				.fail(function(error) {
+					c.fail(error.message);
+					c.finish();
+				});
+		}
+
+		QUnit.test("dtosRoundtripTest()", function(assert){
+			var c = new common(assert);
+			
+			var id = new c.CustomASServiceCode("custom-service-a");
+			var actionFacade;
+
+			var fAction = function(facade) {
+				actionFacade = facade;
+
+				return _.chain(c.getDtos())
+					.map(function(proto) {
+						return new c.CustomASServiceExecutionOptions().withParameter("object", new proto(""));
+					})
+					.map(function(options) {
+						return facade.executeCustomASService(id, options);
+					})
+					.value();
+			}
+
+			var fCheck = function(promises) {
+				return $.when.apply($, promises).then(function(here_we_get_unknown_number_of_resolved_dtos_so_foo){
+					c.ok("Got results");
+					
+					var dtos = Array.prototype.slice.call(arguments);
+					var roundtrips = _.map(dtos, function(dto){
+
+						c.ok("Testing " + dto['@type']);
+						c.ok('Rountrip ok.');
+
+						var proto = require(dto['@type'].replace(/\./g, '/'));
+						if (proto) {
+							var subj = new proto("");
+
+							_.chain(_.keys(dto))
+							.filter(function(key) {
+								return !key.startsWith("@");
+							})
+							.each(function(key){
+								var val = dto[key];
+								if (val && _.isFunction(val.getValue)) {
+									val = val.getValue();
+								}
+
+								if (val) {
+									var setter = _.find(_.functions(subj), function(fn) {
+										return fn.toLowerCase() === key.toLowerCase() || fn.toLowerCase() === "set" + key.toLowerCase();
+									});
+									c.ok("Setter: [set]" + key);
+
+									if (setter) {
+										subj[setter](val);
+									} else {
+										c.ok("Skipping field " + key + " that has no setter.");
+									}
+								} else {
+									c.ok("Skipping field " + key + " as it's empty (i.e. complex).");
+								}
+							});
+
+
+							// let's send it back and see if it's acceptable
+							var options = new c.CustomASServiceExecutionOptions().withParameter("object", subj).withParameter("echo", "true");
+							return actionFacade.executeCustomASService(id, options)
+								.then(function(res) {
+									assert.deepEqual(JSON.parse(JSON.stringify(res)), JSON.parse(JSON.stringify(dto)), "Reconstructed " + dto['@type'] + " from Java template has same fields as the one generated and initialized by java.");
+								});
+
+						} else {
+							debugger;
+							c.fail('Type ' + dto['@type'] + ' is unknown to the common.');
+
+						}
+					});
+					var applied = $.when.apply($, roundtrips);
+
+					return applied;
+
+				});
+			}
+			
+			testAction(c, fAction, fCheck);
+
+		});
+	}
+});
\ No newline at end of file
diff --git a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto.js b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto.js
index 5ed336ea05b..14020a56b19 100644
--- a/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto.js
+++ b/js-test/servers/common/core-plugins/tests/1/as/webapps/openbis-v3-api-test/html/test/test-dto.js
@@ -10,32 +10,29 @@ define([ 'underscore', 'test/common' ], function(_, common) {
 
 			var running = 0;
 
-			_.each(_.functions(c), function(el) {
-				var prop = c[el];
-				if (prop.prototype && prop.prototype['@type']) {
-					var dto = new prop(++running); // just in case the constructor expects something
-					_.chain(_.allKeys(dto))
-						.filter(function(el) {
-							return el.startsWith('set');
-						})
-						.each(function(setter) {
-							var getter = setter.replace(/^set/, 'get');
-							if (_.isFunction(dto[getter])) {
-
-								var value = String(running); // string is more universal
-								running++;
-
-								dto[setter](value);
-								var result = dto[getter]();
-								if (result['@type'] && result['getValue']) {
-									result = result['getValue']();
-								}
-								c.assertEqual(result, value, "Getter " + getter + " of type " + dto['@type'] + " returns same as was put by setter " + setter);
+			_.each(c.getDtos(), function(proto) {
+				var dto = new proto(++running); // just in case the constructor expects something
+				_.chain(_.allKeys(dto))
+					.filter(function(el) {
+						return el.startsWith('set');
+					})
+					.each(function(setter) {
+						var getter = setter.replace(/^set/, 'get');
+						if (_.isFunction(dto[getter])) {
+
+							var value = String(running); // string is more universal
+							running++;
+
+							dto[setter](value);
+							var result = dto[getter]();
+							if (result['@type'] && result['getValue']) {
+								result = result['getValue']();
 							}
-						});
-				}
-
+							c.assertEqual(result, value, "Getter " + getter + " of type " + dto['@type'] + " returns same as was put by setter " + setter);
+						} 
+					});
 			});
+
 		});
 
 		var assertAttributes = function(assert, criteria, expectedName, expextedType, expectedValueType, expectedValue) {
diff --git a/js-test/source/java/ch/systemsx/cisd/openbis/jstest/service/V3ApiDtoTestService.java b/js-test/source/java/ch/systemsx/cisd/openbis/jstest/service/V3ApiDtoTestService.java
index 24500ca0525..2ef0afa1dd6 100644
--- a/js-test/source/java/ch/systemsx/cisd/openbis/jstest/service/V3ApiDtoTestService.java
+++ b/js-test/source/java/ch/systemsx/cisd/openbis/jstest/service/V3ApiDtoTestService.java
@@ -16,14 +16,14 @@
 
 package ch.systemsx.cisd.openbis.jstest.service;
 
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.lang.reflect.Parameter;
 import java.util.Date;
 import java.util.Map;
 import java.util.Properties;
-import java.util.Map.Entry;
-import java.util.Set;
 
 import ch.ethz.sis.openbis.generic.asapi.v3.dto.service.CustomASServiceExecutionOptions;
-import ch.ethz.sis.openbis.generic.asapi.v3.dto.space.Space;
 import ch.ethz.sis.openbis.generic.asapi.v3.plugin.service.ICustomASServiceExecutor;
 import ch.ethz.sis.openbis.generic.asapi.v3.plugin.service.context.CustomASServiceContext;
 
@@ -44,19 +44,61 @@ public class V3ApiDtoTestService implements ICustomASServiceExecutor
         Map<String, Object> parameters = options.getParameters();
         String sessionToken = context.getSessionToken();
         System.out.println("SESSION TOKEN: " + sessionToken);
-        Set<Entry<String, Object>> entrySet = parameters.entrySet();
         System.out.println("PARAMETERS:");
-        for (Entry<String, Object> entry : entrySet)
+        
+        Object obj = parameters.get("object");
+        return parameters.containsKey("echo") ? obj : populate(obj);
+    }
+
+    private Object populate(Object obj)
+    {
+        for (Method method : obj.getClass().getMethods())
         {
-            String key = entry.getKey();
-            Object value = entry.getValue();
-            System.out.println(">>>>> " + key + " = " + value + (value == null ? "" : "[" + value.getClass().getName() + "]"));
+            if (method.getParameterCount() == 1) {
+                Parameter parameter = method.getParameters()[0];
+                Class<?> type = parameter.getType();
+                if (type.isPrimitive() || type.equals(String.class) || type.equals(Date.class)){
+                    try
+                    {
+                        setItUp(obj, method, parameter);
+                    } catch (Exception e)
+                    {
+                        e.printStackTrace();
+                    }
+                } 
+            }
         }
-        Space space = new Space();
-        space.setCode("SPACE1");
-        space.setDescription("a space");
-        space.setRegistrationDate(new Date(1234567890));
-        return space;
+        return obj;
+    }
+
+    private void setItUp(Object obj, Method method, Parameter parameter) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException
+    {
+        method.invoke(obj, getValue(parameter));
+    }
+
+    private Object getValue(Parameter parameter)
+    {
+        double random = Math.random();
+        long rnd = (long) (random*1000000);
+        Class<?> type = parameter.getType();
+        if (type == String.class) {
+            return String.valueOf(random);
+        } 
+        
+        if (type == Date.class) {
+            return new Date(rnd);
+        } 
+
+        if (type == Long.class) {
+            return rnd;
+        } 
+        
+        if (type == Boolean.class) {
+            return random < 0.5;
+        } 
+        
+        
+        return null;
     }
 
 }
-- 
GitLab