source: trunk/test/unit/nl/tno/metagenomics/integration/TrashServiceTests.groovy @ 7

Last change on this file since 7 was 7, checked in by robert@…, 8 years ago
  • Created tests for the synchronization and trash
  • Improved synchronizationservice and trash
  • Put authorization checks in several pages
File size: 17.3 KB
Line 
1package nl.tno.metagenomics.integration
2
3import grails.test.*
4import nl.tno.metagenomics.*
5
6class TrashServiceTests extends GrailsUnitTestCase {
7        def trashService
8    Study trash
9       
10        protected void setUp() {
11        super.setUp()
12                mockDomain( Study );
13                mockDomain( Sample );
14                mockDomain( Assay );
15                mockDomain( AssaySample );
16                mockDomain( Run );
17                mockDomain( SequenceData );
18               
19                mockLogging( TrashService.class, true );
20               
21                trashService = new TrashService();
22
23                setupStudy();
24    }
25
26    protected void tearDown() {
27        super.tearDown()
28    }
29
30        protected void setupStudy() {
31                // Create a study trashcan
32                trash = new Study( name: "Trashcan", studyToken: "trashcan", trashcan: true );
33                trash.save(flush:true);
34               
35                // Setup a study with two assays, 4 samples
36                Study s = new Study( name: "Study 1", studyToken: "study1" );
37
38                s.save(flush:true);
39               
40                // Create two assays
41                Assay a1 = new Assay( id: 1, name: "Assay 1", assayToken: "assay1", study: s );
42                Assay a2 = new Assay( id: 2, name: "Assay 2", assayToken: "assay2", study: s );
43                Assay a3 = new Assay( id: 3, name: "Assay 3", assayToken: "assay3", study: s );
44                def assays = [a1, a2, a3];
45
46                assays.each { s.addToAssays( it ); it.save( flush: true ); }
47               
48                // Create four samples
49                Sample sa1 = new Sample( id: 1, name: "Sample 1a", sampleToken: "sample1a", study: s );
50                Sample sa2 = new Sample( id: 2, name: "Sample 1b", sampleToken: "sample1b", study: s );
51                Sample sa3 = new Sample( id: 3, name: "Sample 2a", sampleToken: "sample2a", study: s );
52                Sample sa4 = new Sample( id: 4, name: "Sample 2b", sampleToken: "sample2b", study: s );
53                Sample sa5 = new Sample( id: 5, name: "Sample 3a", sampleToken: "sample3a", study: s );
54                def samples = [sa1, sa2, sa3, sa4, sa5]
55               
56                samples.each { s.addToSamples( it ); it.save(flush:true); }
57               
58                s.save(flush:true);
59               
60                // Create a single run
61                Run run = new Run( name: "abc" );
62                run.save(flush:true);
63               
64                // Create desired combinations of samples and assays
65                // Such that: assay1 has 2 samples with data, assay2 has 1 sample with data and assay3 has no samples with data
66           AssaySample as1a = new AssaySample( oligoNumber: "123", tagSequence: "abc", sample: sa1, assay: a1 );
67           AssaySample as1b = new AssaySample( oligoNumber: "200", tagSequence: "def", sample: sa2, assay: a1 );
68           AssaySample as2a = new AssaySample( oligoNumber: "300", tagSequence: "ghi", sample: sa3, assay: a2 );
69           AssaySample as2b = new AssaySample( id: 12, sample: sa4, assay: a2);
70           AssaySample as3a = new AssaySample( sample: sa5, assay: a3);
71           def assaySamples= [as1a, as1b, as2a, as2b, as3a]
72
73           a1.addToAssaySamples( as1a ); sa1.addToAssaySamples( as1a ); run.addToAssaySamples( as1a );
74           as1a.save(flush:true);
75           
76           a1.addToAssaySamples( as1b ); sa2.addToAssaySamples( as1b ); run.addToAssaySamples( as1b );
77           as1b.save(flush:true);
78
79           a2.addToAssaySamples( as2a ); sa3.addToAssaySamples( as2a ); run.addToAssaySamples( as2a );
80           as2a.save(flush:true);
81
82           a2.addToAssaySamples( as2b ); sa4.addToAssaySamples( as2b ); run.addToAssaySamples( as2b );
83           as2b.save(flush:true);
84
85           a3.addToAssaySamples( as3a ); sa5.addToAssaySamples( as3a ); run.addToAssaySamples( as3a );
86           as3a.save(flush:true);
87           
88           assert as1a.sample.name == "Sample 1a"
89           
90           // Save samples and assays again
91           assays.each { it.save(flush:true); }
92           samples.each { it.save(flush:true); }
93           run.save(flush:true);
94           
95           // Add sequencedata objects to as1a and as1b
96           SequenceData sd1 = new SequenceData( assaySample: as1a, sequenceFile: "fasta1", qualityFile: "qual1", numSequences: 100, averageQuality: 10.0 );
97           SequenceData sd2 = new SequenceData( assaySample: as1a, sequenceFile: "fasta2", qualityFile: "qual2", numSequences: 30, averageQuality: 14.0 );
98           SequenceData sd3 = new SequenceData( assaySample: as1b, sequenceFile: "fasta3", qualityFile: "qual3", numSequences: 2000, averageQuality: 17.0 );
99           def sequenceData = [sd1, sd2, sd3];
100           
101           as1a.addToSequenceData( sd1 );
102           as1a.addToSequenceData( sd2 );
103           as1b.addToSequenceData( sd3 );
104           
105           as1a.save(flush:true); as1b.save(flush:true);
106           sequenceData.each { it.save(flush:true); }
107        }
108       
109        protected void setupTrash() {
110                // Create a study trashcan
111                trash = Study.findByStudyToken( "trashcan" );
112               
113                // Create a trash assay
114                Assay a1 = new Assay( id: 100, name: "Trash Assay 1", assayToken: "trash_assay1", study: trash );
115                def assays = [a1];
116
117                assays.each { trash.addToAssays( it ); it.save( flush: true ); }
118               
119                // Create three samples, two originally also present in assay 1, the other one isn't
120                Sample sa1 = new Sample( id: 101, name: "Sample 1a", sampleToken: "tsample1a", study: trash );
121                Sample sa2 = new Sample( id: 102, name: "Sample 1b", sampleToken: "tsample1b", study: trash );
122                Sample sa3 = new Sample( id: 103, name: "Sample 2a", sampleToken: "tsample2a", study: trash );
123                def samples = [sa1, sa2, sa3]
124               
125                samples.each { trash.addToSamples( it ); it.save(flush:true); }
126               
127                trash.save(flush:true);
128               
129           // Create a single run in order to be able to save sequencedata
130           Run run = new Run( name: "trashrun" );
131           run.save(flush:true);
132
133                // Create desired combinations of samples and assays
134                // Such that: assay1 has 2 samples with data, assay2 has 1 sample with data and assay3 has no samples with data
135           AssaySample as1a = new AssaySample( id: 102, oligoNumber: "fromtrash: 1", tagSequence: "fromtrash: abc", sample: sa1, assay: a1 );
136           AssaySample as1b = new AssaySample( oligoNumber: "fromtrash: 2", tagSequence: "fromtrash: def", sample: sa2, assay: a1 );
137           AssaySample as2a = new AssaySample( oligoNumber: "fromtrash: 3", tagSequence: "fromtrash: ghi", sample: sa3, assay: a1 );
138           def assaySamples= [as1a, as1b, as2a]
139
140           a1.addToAssaySamples( as1a ); sa1.addToAssaySamples( as1a ); run.addToAssaySamples( as1a );
141           as1a.save(flush:true);
142           
143           a1.addToAssaySamples( as1b ); sa2.addToAssaySamples( as1b ); run.addToAssaySamples( as1b );
144           as1b.save(flush:true);
145
146           a1.addToAssaySamples( as2a ); sa3.addToAssaySamples( as2a ); run.addToAssaySamples( as2a );
147           as2a.save(flush:true);
148
149           // Save samples and assays again
150           assays.each { it.save(flush:true); }
151           samples.each { it.save(flush:true); }
152           run.save( flush:true );
153           
154           // Add sequencedata objects to as1a and as1b
155           SequenceData sd1 = new SequenceData( assaySample: as1a, sequenceFile: "fromtrash: fasta1", qualityFile: "fromtrash: qual1", numSequences: 80, averageQuality: 11.0 );
156           SequenceData sd2 = new SequenceData( assaySample: as1a, sequenceFile: "fromtrash: fasta2", qualityFile: "fromtrash: qual2", numSequences: 520, averageQuality: 14.0 );
157           SequenceData sd3 = new SequenceData( assaySample: as1b, sequenceFile: "fromtrash: fasta3", qualityFile: "fromtrash: qual3", numSequences: 2000, averageQuality: 17.0 );
158           def sequenceData = [sd1, sd2, sd3];
159           
160           as1a.addToSequenceData( sd1 );
161           as1a.addToSequenceData( sd2 );
162           as1b.addToSequenceData( sd3 );
163           
164           as1a.save(flush:true); as1b.save(flush:true);
165           sequenceData.each { it.save(flush:true); }
166        }
167       
168    void testStudyTrash() {
169                def study = Study.findByStudyToken( "study1" );
170               
171                // Check whether the starting condition is correct
172                assert trash instanceof Study
173                assert study instanceof Study
174                assert study.assays?.size() == 3;
175                assert ( !trash.assays || trash.assays.size() == 0 );
176               
177                // Move data to trash and delete study
178                trashService.moveToTrash( study );
179               
180                // Check whether the study is really removed
181                assert null == Study.findByStudyToken( "study1" );
182               
183                // Check whether only the assays were kept that contain data
184                assert trash.assays.size() == 2;
185               
186                // Check whether only the assaysamples were kept that contain data
187                def assaySamples = trash.assays*.assaySamples.flatten().unique();
188                assert assaySamples.size() == 3;
189               
190                def assaySample = assaySamples.find { it.sample?.name == "Sample 1a"; }
191                assert assaySample
192                assert assaySample.oligoNumber == "123"
193                assert assaySample.tagSequence == "abc"
194                assert assaySample.sequenceData.size() == 2
195
196                assaySample = assaySamples.find { it.sample?.name == "Sample 1b"; }
197                assert assaySample
198                assert assaySample.oligoNumber == "200"
199                assert assaySample.tagSequence == "def"
200                assert assaySample.sequenceData.size() == 1
201
202                assaySample = assaySamples.find { it.sample?.name == "Sample 2a"; }
203                assert assaySample
204                assert assaySample.oligoNumber == "300"
205                assert assaySample.tagSequence == "ghi"
206                assert !assaySample.sequenceData || assaySample.sequenceData.size() == 0
207
208                // Check whether the assay samples contain the right sequence data
209                def sequenceData = trash.assays*.assaySamples*.sequenceData.flatten().unique();
210               
211                // Filter null values
212                sequenceData = sequenceData.findAll { it != null };
213                assert sequenceData.size() == 3;
214               
215                def sd = sequenceData.find { it.sequenceFile == "fasta1"; }
216                assert sd
217                assert sd.qualityFile == "qual1" 
218                assert sd.numSequences == 100 
219                assert sd.averageQuality == 10.0
220                assert sd.sample.assay.name == "Assay 1"
221                assert sd.sample.sample.name == "Sample 1a"
222               
223                sd = sequenceData.find { it.sequenceFile == "fasta2"; }
224                assert sd
225                assert sd.qualityFile == "qual2"
226                assert sd.numSequences == 30
227                assert sd.averageQuality == 14.0
228                assert sd.sample.assay.name == "Assay 1"
229                assert sd.sample.sample.name == "Sample 1a"
230               
231                sd = sequenceData.find { it.sequenceFile == "fasta3"; }
232                assert sd
233                assert sd.qualityFile == "qual3"
234                assert sd.numSequences == 2000
235                assert sd.averageQuality == 17.0
236                assert sd.sample.assay.name == "Assay 1"
237                assert sd.sample.sample.name == "Sample 1b"
238    }
239       
240        void testAssayTrash() {
241                def study = Study.findByStudyToken( "study1" );
242                def assay = study.assays.find { it.assayToken == "assay1" };
243               
244                // Check whether the starting condition is correct
245                assert trash instanceof Study
246                assert assay instanceof Assay
247                assert assay.assaySamples.size() == 2;
248                assert ( !trash.assays || trash.assays.size() == 0 );
249               
250                // Move data to trash and delete study
251                trashService.moveToTrash( assay );
252               
253                // Check whether the study itself still exists
254                study = Study.findByStudyToken( "study1" )
255                assert study
256                assay = study.assays.find { it.assayToken == "assay1" };
257               
258                study.assays.each { 
259                        println it.name + ", " + it.assaySamples?.size()
260                }
261                assert !assay
262                assert study.assays.size() == 2
263               
264                // Check whether the assay is really removed
265                assay = Assay.findByAssayToken( "assay1" );
266                assert !assay
267               
268                // Check whether the assay samples also have been removed
269                // assert AssaySample.list().findAll { it.assay?.study?.studyToken == "study1" && it.assay?.assayToken == "assay1" }.size() == 0
270               
271                // Check whether only the assays were kept that contain data
272                assert trash.assays.size() == 1;
273                assert trash.samples.size() == 2;
274               
275                // Check whether only the assaysamples were kept that contain data
276                def assaySamples = trash.assays*.assaySamples.flatten().unique();
277                assert assaySamples.size() == 2;
278               
279                def assaySample = assaySamples.find { it.sample?.name == "Sample 1a"; }
280                assert assaySample
281                assert assaySample.oligoNumber == "123"
282                assert assaySample.tagSequence == "abc"
283                assert assaySample.sequenceData.size() == 2
284
285                assaySample = assaySamples.find { it.sample?.name == "Sample 1b"; }
286                assert assaySample
287                assert assaySample.oligoNumber == "200"
288                assert assaySample.tagSequence == "def"
289                assert assaySample.sequenceData.size() == 1
290
291                // Check whether the assay samples contain the right sequence data
292                def sequenceData = trash.assays*.assaySamples*.sequenceData.flatten().unique();
293               
294                // Filter null values
295                sequenceData = sequenceData.findAll { it != null };
296                assert sequenceData.size() == 3;
297               
298                def sd = sequenceData.find { it.sequenceFile == "fasta1"; }
299                assert sd
300                assert sd.qualityFile == "qual1"
301                assert sd.numSequences == 100
302                assert sd.averageQuality == 10.0
303                assert sd.sample.assay.name == "Assay 1"
304                assert sd.sample.sample.name == "Sample 1a"
305               
306                sd = sequenceData.find { it.sequenceFile == "fasta2"; }
307                assert sd
308                assert sd.qualityFile == "qual2"
309                assert sd.numSequences == 30
310                assert sd.averageQuality == 14.0
311                assert sd.sample.assay.name == "Assay 1"
312                assert sd.sample.sample.name == "Sample 1a"
313               
314                sd = sequenceData.find { it.sequenceFile == "fasta3"; }
315                assert sd
316                assert sd.qualityFile == "qual3"
317                assert sd.numSequences == 2000
318                assert sd.averageQuality == 17.0
319                assert sd.sample.assay.name == "Assay 1"
320                assert sd.sample.sample.name == "Sample 1b"
321        }
322       
323        void testSampleTrash() {
324                def study = Study.findByStudyToken( "study1" );
325                def sample = study.samples.find { it.sampleToken == "sample1a" };
326                def assay
327               
328                // Check whether the starting condition is correct
329                assert trash instanceof Study
330                assert sample instanceof Sample
331                assert sample.assaySamples.size() == 1;
332                assert ( !trash.assays || trash.assays.size() == 0 );
333               
334                // Move data to trash and delete study
335                trashService.moveToTrash( sample );
336               
337                // Check whether the study and the assay itself still exists
338                study = Study.findByStudyToken( "study1" )
339                assert study
340                assay = study.assays.find { it.assayToken == "assay1" };
341                assert assay
342                assert study.assays.size() == 3
343               
344                // Check whether the sample is really removed
345                sample = Sample.findBySampleToken( "sample1a" );
346                assert !sample
347                sample = study.samples.find { it.sampleToken == "sample1a" }
348                assert !sample
349
350                // Check whether the assay samples also have been removed
351                //assert AssaySample.list().findAll { it.sample?.study?.studyToken == "study1" && it.sample?.sampleToken == "assay1" }.size() == 0
352                               
353                // Check whether only the assays were kept that contain data
354                assert trash.assays.size() == 1;
355                assert trash.samples.size() == 1;
356               
357                // Check whether only the assaysamples were kept that contain data and belong to sample 1
358                def assaySamples = trash.assays*.assaySamples.flatten().unique();
359                assert assaySamples.size() == 1;
360               
361                def assaySample = assaySamples.find { it.sample?.name == "Sample 1a"; }
362                assert assaySample
363                assert assaySample.assay?.name == "Assay 1"
364                assert assaySample.oligoNumber == "123"
365                assert assaySample.tagSequence == "abc"
366                assert assaySample.sequenceData.size() == 2
367
368                // Check whether the assay samples contain the right sequence data
369                def sequenceData = trash.assays*.assaySamples*.sequenceData.flatten().unique();
370               
371                // Filter null values
372                sequenceData = sequenceData.findAll { it != null };
373               
374                assert sequenceData.size() == 2;
375
376                // Filter null values
377                sequenceData = sequenceData.findAll { it != null };
378                assert sequenceData.size() == 2;
379               
380                def sd = sequenceData.find { it.sequenceFile == "fasta1"; }
381                assert sd
382                assert sd.qualityFile == "qual1"
383                assert sd.numSequences == 100
384                assert sd.averageQuality == 10.0
385                assert sd.sample.assay.name == "Assay 1"
386                assert sd.sample.sample.name == "Sample 1a"
387               
388                sd = sequenceData.find { it.sequenceFile == "fasta2"; }
389                assert sd
390                assert sd.qualityFile == "qual2"
391                assert sd.numSequences == 30
392                assert sd.averageQuality == 14.0
393                assert sd.sample.assay.name == "Assay 1"
394                assert sd.sample.sample.name == "Sample 1a"
395        }
396       
397        void testRestoreAssay() {
398                setupTrash();
399               
400                def study = Study.findByStudyToken( "study1" );
401               
402                def trashAssay = trash.assays.find { it.assayToken == "trash_assay1" };
403                def restoreTo = study.assays.find { it.assayToken == "assay1" };
404               
405                assert trashAssay
406                assert restoreTo
407               
408                assert restoreTo.assaySamples?.size() == 2
409               
410                trashService.restoreAssay( trashAssay, restoreTo );
411               
412                // Check whether the sample data is moved to the other assay
413                def restoredTo = study.assays.find { it.assayToken == "assay1" };
414                assert restoredTo.assaySamples?.size() == 2
415               
416                // Check for the copying of oligoNumber and tagSequence
417                def s = restoredTo.assaySamples.find { it.sample.sampleToken == "sample1a" }
418                assert s
419                assert s.oligoNumber == "fromtrash: 1";
420                assert s.tagSequence == "fromtrash: abc";
421                assert s.sequenceData?.size() == 4
422               
423                assert s.numSequences() == 730
424                def sequenceFiles = s.sequenceData.sequenceFile;
425                assert sequenceFiles.contains( "fromtrash: fasta1" )
426                assert sequenceFiles.contains( "fromtrash: fasta2" )
427               
428                // Also check the second assay sample
429                s = restoredTo.assaySamples.find { it.sample.sampleToken == "sample1b" }
430                assert s
431                assert s.oligoNumber == "fromtrash: 2";
432                assert s.tagSequence == "fromtrash: def";
433                assert s.sequenceData?.size() == 2
434               
435                assert s.numSequences() == 4000
436                sequenceFiles = s.sequenceData.sequenceFile;
437                assert sequenceFiles.contains( "fromtrash: fasta3" )
438        }
439       
440        void testRestoreSample() {
441                setupTrash();
442               
443                def study = Study.findByStudyToken( "study1" );
444
445                def trashAssay = trash.assays.find { it.assayToken == "trash_assay1" };
446                def restoreToAssay = study.assays.find { it.assayToken == "assay2" };
447
448                assert trashAssay
449                assert restoreToAssay
450
451                def trashSample = trashAssay.assaySamples.find { it.id == 102 };
452                def restoreTo = restoreToAssay.assaySamples.find { it.id == 12 };
453
454                assert trashSample
455                assert restoreTo
456               
457                assert restoreTo.sequenceData == null || restoreTo.sequenceData.size() == 0;
458               
459                trashService.restoreSample( trashSample, restoreTo );
460               
461                // Check whether the sample data is moved to the other assay
462                def restoredTo = restoreToAssay.assaySamples.find { it.id == 12 };
463                assert restoredTo
464               
465                // Check for the copying of oligoNumber and tagSequence
466                assert restoredTo.oligoNumber == "fromtrash: 1";
467                assert restoredTo.tagSequence == "fromtrash: abc";
468                assert restoredTo.sequenceData?.size() == 2
469               
470                assert restoredTo.numSequences() == 600
471                def sequenceFiles = restoredTo.sequenceData.sequenceFile;
472                assert sequenceFiles.contains( "fromtrash: fasta1" )
473                assert sequenceFiles.contains( "fromtrash: fasta2" )
474
475        }
476}
Note: See TracBrowser for help on using the repository browser.