Changeset 13 for trunk/grails-app/services/nl
- Timestamp:
- Feb 10, 2011, 5:03:02 PM (12 years ago)
- Location:
- trunk/grails-app/services/nl/tno/metagenomics
- Files:
-
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/grails-app/services/nl/tno/metagenomics/FastaService.groovy
r12 r13 3 3 import java.io.BufferedWriter; 4 4 import java.io.File; 5 import java.io.Writer; 5 6 import java.util.ArrayList; 6 7 import java.util.zip.ZipEntry … … 11 12 def fileService 12 13 def fuzzySearchService 14 def sampleExcelService 13 15 14 16 static transactional = true … … 428 430 429 431 // Save the tag for exporting 430 tags << [assaySampleId: assaySample.id, sampleName: assaySample.sample.name, assayName: assaySample.assay.name, tag: tag]432 tags << [assaySampleId: assaySample.id, sampleName: assaySample.sample.name, assayName: assaySample.assay.name, studyName: assaySample.assay.study.name, tag: tag] 431 433 } 432 434 } … … 481 483 } 482 484 485 // Export a tab delimited file with tags 486 zipFile.putNextEntry( new ZipEntry( name + "_sample-tag.tab" ) ); 487 exportSampleTagFile( tags, zipWriter ); 488 zipWriter.flush(); 489 zipFile.closeEntry(); 490 491 // Export an excel file with information about the samples 492 zipFile.putNextEntry( new ZipEntry( name + ".xls" ) ); 493 sampleExcelService.exportExcelSampleData( assaySamples, tags, zipFile ); 494 zipFile.closeEntry(); 495 483 496 zipFile.close(); 484 485 // Export a tab delimited file with tags 486 //exportSampleTagFile( tags ); 497 } 498 499 /** 500 * Creates a tab delimited file with two columns and column headers "Sequence" and "Samplename" 501 * @param tags Map with newly created tags 502 * @param zipWriter Writer to write the data to 503 */ 504 protected void exportSampleTagFile( List tags, Writer zipWriter ) { 505 zipWriter.write( "Sequence" + "\t" + "Samplename" + "\n" ); 506 507 // Check whether the sample names are unique. If they aren't, the assay and study names 508 // are appended to the sample name 509 def sampleNames = tags*.sampleNames; 510 if( sampleNames.unique().size() < sampleNames.size() ) { 511 tags.each { 512 it.uniqueName = it.sampleName + " (" + it.assayName + " / " + it.studyName + ")"; 513 } 514 } else { 515 tags.each { 516 it.uniqueName = it.sampleName; 517 } 518 } 519 520 tags.each { 521 zipWriter.write( it.tag + "\t" + it.uniqueName + "\n" ); 522 } 487 523 } 488 524 -
trunk/grails-app/services/nl/tno/metagenomics/SampleExcelService.groovy
r9 r13 1 1 package nl.tno.metagenomics 2 3 import org.springframework.web.context.request.RequestContextHolder; 2 4 3 5 class SampleExcelService { 4 6 def excelService 5 7 def fuzzySearchService 8 def gscfService 6 9 7 10 static transactional = true … … 15 18 def possibleFields = [sampleNameName, runName, tagNameName, tagSequenceName, oligoNumberName] 16 19 17 def downloadSampleExcel( def assaySamples, boolean includeRun = true ) { 20 /** 21 * Download a sample excel file with information about the metagenomics data of the assaySamples (i.e. all assaySample properties) 22 * @param assaySamples AssaySamples for which the information should be exported 23 * @param includeRun Whether to include a column with run name or not 24 * @return 25 */ 26 def downloadSampleExcel( def assaySamples, boolean includeRun = true ) { 18 27 def sheetIndex = 0; 19 28 … … 50 59 excelService.autoSizeColumns( wb, sheetIndex, 0..2) 51 60 52 return wb; 61 return wb; 53 62 } 54 63 64 /** 65 * Parses a given excel file and tries to match the column names with assaySample properties 66 * @param file 67 * @return 68 */ 55 69 def parseTagsExcel( File file, boolean includeRun = true ) { 56 70 def sheetIndex = 0 … … 81 95 } 82 96 97 /** 98 * Updates given assay samples with data from the excel file 99 * @param matchColumns Indicated which columns from the excel file should go into which field of the assaySample 100 * @param possibleFields List with possible fields to enter 101 * @param file Excel file with the data 102 * @param assaySamples Assay Samples to be updated 103 * @return 104 */ 83 105 def updateTagsByExcel( def matchColumns, def possibleFields, File file, def assaySamples ) { 84 106 def sheetIndex = 0 … … 187 209 } 188 210 } 211 212 /** 213 * Exports all known data about the samples to an excel file 214 * @param assaySamples Assaysamples to export information about 215 * @param tags Tags associated with the assay samples 216 * @param stream Outputstream to write the data to 217 * @return 218 */ 219 def exportExcelSampleData( List<AssaySample> assaySamples, def tags, OutputStream stream ) { 220 if( assaySamples == null ) 221 assaySamples = [] 222 223 // Gather data from GSCF. 224 def sampleTokens = assaySamples*.sample.unique()*.sampleToken; 225 def sessionToken = RequestContextHolder.currentRequestAttributes().getSession().sessionToken 226 def gscfData 227 try { 228 gscfData = gscfService.getSamples( sessionToken, sampleTokens ); 229 } catch( Exception e ) { 230 log.error "Exception occurred while fetching sample data from gscf: " + e.getMessage(); 231 return; 232 } 233 234 // Determine which fields to show from the GSCF data 235 def gscfFields = [] 236 def subjectFields = [] 237 def eventFields = [] 238 def moduleFields = [ "Sample name", "Assay name", "Study name", "Run name", "# sequences", "Artificial tag sequence", "Original tag sequence", "Tag name", "Oligo number" ] 239 gscfData.each { sample -> 240 sample.each { key, value -> 241 if( key == "subjectObject" ) { 242 value.each { subjectKey, subjectValue -> 243 if( subjectValue && !value.isNull( subjectKey ) && !subjectFields.contains( subjectKey ) ) 244 subjectFields << subjectKey 245 } 246 } else if( key == "eventObject" ) { 247 value.each { eventKey, eventValue -> 248 if( eventValue && !value.isNull( eventKey ) && !eventFields.contains( eventKey ) ) 249 eventFields << eventKey 250 } 251 } else if( value && !sample.isNull( key ) && !gscfFields.contains( key ) ) { 252 gscfFields << key 253 } 254 } 255 } 256 257 // Handle specific fields and names in GSCF 258 def fields = handleSpecificFields( [ "module": moduleFields, "gscf": gscfFields, "subject": subjectFields, "event": eventFields ] ); 259 260 // Put the module data in the right format (and sorting the samples by name) 261 def data = [] 262 assaySamples.toList().sort { it.sample.name }.each { assaySample -> 263 // Lookup the tag for this assaySample 264 def currentTag = tags.find { it.assaySampleId == assaySample.id }; 265 266 // First add the module data 267 def row = [ 268 assaySample.sample.name, 269 assaySample.assay.name, 270 assaySample.assay.study.name, 271 assaySample.run?.name, 272 assaySample.numSequences(), 273 currentTag?.tag, 274 assaySample.tagName, 275 assaySample.tagSequence, 276 assaySample.oligoNumber 277 ] 278 279 // Afterwards add the gscfData including subject and event data 280 def gscfRow = gscfData.find { it.sampleToken == assaySample.sample.sampleToken }; 281 if( gscfRow ) { 282 fields[ "names" ][ "gscf" ].each { field -> 283 row << prepare( gscfRow, field ); 284 } 285 fields[ "names" ][ "subject" ].each { field -> 286 row << prepare( gscfRow.optJSONObject( "subjectObject" ), field ); 287 } 288 fields[ "names" ][ "event" ].each { field -> 289 row << prepare( gscfRow.optJSONObject( "eventObject" ), field ); 290 } 291 } 292 293 data << row; 294 295 } 296 297 // Create excel file 298 def sheetIndex = 0; 299 300 // Create an excel sheet 301 def wb = excelService.create(); 302 303 // Put the headers on the first row 304 excelService.writeHeader( wb, fields[ "descriptions" ][ "all" ], sheetIndex ); 305 excelService.writeData( wb, data, sheetIndex, 1 ); 306 307 // Auto resize columns 308 excelService.autoSizeColumns( wb, sheetIndex, 0..fields[ "names" ][ "all" ].size()-1) 309 310 // Write the data to the output stream 311 wb.write( stream ); 312 } 313 314 protected String prepare( def object, def fieldName ) { 315 if( object.isNull( fieldName ) ) 316 return ""; 317 318 // If the field is a object, return the 'name' property 319 def obj = object.optJSONObject( fieldName ) 320 if( obj ) 321 return obj.optString( "name" ) 322 else 323 return object.optString( fieldName ); 324 } 325 326 protected handleSpecificFields( def inputFields ) { 327 def fields = [ 328 "names": [ 329 "all": [] 330 ], 331 "descriptions": [ 332 "all": [] 333 ] 334 ] 335 336 inputFields.each { key, value -> 337 def names = []; 338 def descriptions = [] 339 switch( key ) { 340 case "gscf": 341 value.each { 342 if( it != "sampleToken" && it != "name" ) { 343 names << it; 344 if( it == "startTime" ) 345 descriptions << "Event start time"; 346 else 347 descriptions << it 348 } 349 } 350 break; 351 case "subject": 352 value.each { 353 if( it != "name" ) { 354 names << it; 355 descriptions << it 356 } 357 } 358 break; 359 case "event": 360 value.each { 361 if( it != "startTime" ) { 362 names << it; 363 descriptions << it 364 } 365 } 366 break; 367 default: 368 names = value; descriptions = value; 369 break; 370 } 371 372 fields[ "names" ][ key ] = names; 373 fields[ "names" ][ "all" ] += names; 374 fields[ "descriptions" ][ key ] = descriptions; 375 fields[ "descriptions" ][ "all" ] += descriptions; 376 } 377 378 return fields; 379 380 } 381 189 382 } -
trunk/grails-app/services/nl/tno/metagenomics/files/FileService.groovy
r12 r13 100 100 101 101 if( !uploadDir ) 102 uploadDir = "fileuploads"102 uploadDir = "fileuploads" 103 103 104 104 return absolutePath( uploadDir ); -
trunk/grails-app/services/nl/tno/metagenomics/integration/GscfService.groovy
r9 r13 12 12 */ 13 13 class GscfService { 14 15 14 def config = ConfigurationHolder.config 16 15 17 16 static transactional = true 18 19 20 17 21 18 /** … … 51 48 return "${config.gscf.baseURL}/study/showByToken/" + studyToken 52 49 } 53 54 /** 55 * Returns the url to add a new study in GSCF56 *57 * @return URL to redirect the user to58 */59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 50 51 /** 52 * Returns the url to add a new study in GSCF 53 * 54 * @return URL to redirect the user to 55 */ 56 public String urlAddStudy( String studyToken ) { 57 return config.gscf.baseURL + config.gscf.addStudyPath 58 } 59 60 /** 61 * Retrieves the currently logged in user from GSCF 62 * 63 * @param sessionToken String 64 * 65 * @return Map 66 */ 67 public Map getUser(String sessionToken) { 68 def user = [:] 69 this.callGSCF(sessionToken, "getUser").each { 70 user[ it.key ] = it.value; 71 } 72 return user 73 } 74 78 75 /** 79 76 * Retrieve a list of Studies from the GSCF … … 87 84 } 88 85 89 86 90 87 /** 91 88 * Retrieve a list of Studies from the GSCF … … 116 113 } catch( ResourceNotFoundException e ) { 117 114 throw new ResourceNotFoundException( "Study with token " + studyToken + " not found in GSCF" ) 118 throw e // Other exceptions are thrown as they appear 119 } 115 } // Other exceptions are thrown as they appear 120 116 121 117 // Return only the first element of the list, since we are only interested in one study 122 if( list.size() == 0 ) { 118 if( list?.size() ) { 119 return list[0]; 120 } else { 123 121 return [] 124 } else {125 return list[0];126 122 } 127 123 } … … 172 168 } 173 169 174 /** 175 * Retrieve a list of Samples from the GSCF 176 * 177 * @param sessionToken String 178 * @param assay Assay (parameter assay is optional, only used when you want to limit the list of samples of an Assay within a Study) 179 * 180 * @return ArrayList 181 */ 182 public ArrayList getSamples(String sessionToken, String assayToken) throws NotAuthorizedException, ResourceNotFoundException { 183 // Samples of a Study limited to a single Assay 184 try { 185 return this.callGSCF(sessionToken, "getSamples", ["assayToken":assayToken]) 186 } catch( NotAuthorizedException e ) { 187 throw new NotAuthorizedException( "User is not authorized to access study for assay with token " + assayToken ) 188 } catch( ResourceNotFoundException e ) {1 189 throw new ResourceNotFoundException( "Assay with token " + assayToken + " not found in GSCF" ) 190 } // Other exceptions are thrown as they appear 191 192 } 193 170 194 171 /** 195 172 * Retrieve a single Sample from the GSCF 196 * 173 * 197 174 * @param sessionToken String 198 175 * @param assay Assay 199 * @param sample Sample 200 * 201 * @return ArrayList 176 * @param sample Sample 177 * 178 * @return ArrayList 202 179 */ 203 180 public def getSample(String sessionToken, String assayToken, String sampleToken) throws NotAuthorizedException, ResourceNotFoundException { … … 219 196 220 197 } 198 199 /** 200 * Retrieve a list of Samples from the GSCF 201 * 202 * @param sessionToken String 203 * @param assay Assay (parameter assay is optional, only used when you want to limit the list of samples of an Assay within a Study) 204 * 205 * @return ArrayList 206 */ 207 public ArrayList getSamples(String sessionToken, String assayToken) throws NotAuthorizedException, ResourceNotFoundException { 208 // Samples of a Study limited to a single Assay 209 try { 210 return this.callGSCF(sessionToken, "getSamples", ["assayToken":assayToken]) 211 } catch( NotAuthorizedException e ) { 212 throw new NotAuthorizedException( "User is not authorized to access study for assay with token " + assayToken ) 213 } catch( ResourceNotFoundException e ) {1 214 throw new ResourceNotFoundException( "Assay with token " + assayToken + " not found in GSCF" ) 215 } // Other exceptions are thrown as they appear 216 217 } 218 219 /** 220 * Retrieve a list of samples from the GSCF 221 * 222 * @param sessionToken String 223 * @param sampleTokens List of sampleTokens 224 * 225 * @return ArrayList 226 */ 227 public def getSamples(String sessionToken, List sampleTokens) throws NotAuthorizedException, ResourceNotFoundException { 228 def list 229 230 try { 231 list = this.callGSCF(sessionToken, "getSamples", ["sampleToken": sampleTokens]) 232 } catch( NotAuthorizedException e ) { 233 throw new NotAuthorizedException( "User is not authorized to access samples" ) 234 } catch( ResourceNotFoundException e ) { 235 throw new ResourceNotFoundException( "Samples with token " + sampleTokens + " not found in GSCF" ) 236 } // Other exceptions are thrown as they appear 237 238 // Return only the first element of the list, since we are only interested in one sample 239 return list 240 } 241 221 242 222 243 /** … … 273 294 274 295 // concat all Rest Call specific arguments behind addr 275 restParams.each {parameter -> 296 restParams.each {parameter -> 276 297 // If a list is given as value, the parameter should show up multiple times 277 298 if( parameter.value instanceof Collection ) { … … 281 302 } else { 282 303 addr += "&${parameter.key}=" + parameter.value.toString().encodeAsURL() 283 } 304 } 284 305 } 285 306 -
trunk/grails-app/services/nl/tno/metagenomics/integration/SynchronizationService.groovy
r12 r13 261 261 // Can't retrieve data. Maybe sessionToken has expired or invalid. Anyway, stop 262 262 // synchronizing and return null 263 e.printStackTrace() 263 264 log.error( "Exception occurred when fetching study " + study.studyToken + ": " + e.getMessage() ) 264 265 throw new Exception( "Error while fetching study " + study.studyToken, e)
Note: See TracChangeset
for help on using the changeset viewer.