From 150d9833026cd4ba7c6c089e3e3937724fa1339c Mon Sep 17 00:00:00 2001 From: Rike Date: Wed, 29 Mar 2023 11:48:53 +0200 Subject: [PATCH 1/6] Remove exit statements --- lib/NfcoreSchema.groovy | 3 +- lib/WorkflowMain.groovy | 2 ++ lib/WorkflowSarek.groovy | 25 +++++++------- workflows/sarek.nf | 72 ++++++++++++++-------------------------- 4 files changed, 41 insertions(+), 61 deletions(-) diff --git a/lib/NfcoreSchema.groovy b/lib/NfcoreSchema.groovy index 33cd4f6e8d..4d29681431 100755 --- a/lib/NfcoreSchema.groovy +++ b/lib/NfcoreSchema.groovy @@ -2,6 +2,7 @@ // This file holds several functions used to perform JSON parameter validation, help and summary rendering for the nf-core pipeline template. // +import nextflow.Nextflow import org.everit.json.schema.Schema import org.everit.json.schema.loader.SchemaLoader import org.everit.json.schema.ValidationException @@ -177,7 +178,7 @@ class NfcoreSchema { } if (has_error) { - System.exit(1) + Nextflow.error('Exiting!') } } diff --git a/lib/WorkflowMain.groovy b/lib/WorkflowMain.groovy index 255cbcdf57..f14c2b4679 100755 --- a/lib/WorkflowMain.groovy +++ b/lib/WorkflowMain.groovy @@ -2,6 +2,8 @@ // This file holds several functions specific to the main.nf workflow in the nf-core/sarek pipeline // +import nextflow.Nextflow + class WorkflowMain { // diff --git a/lib/WorkflowSarek.groovy b/lib/WorkflowSarek.groovy index 41b10ddd29..0dfd7e8222 100755 --- a/lib/WorkflowSarek.groovy +++ b/lib/WorkflowSarek.groovy @@ -2,6 +2,7 @@ // This file holds several functions specific to the workflow/sarek.nf in the nf-core/sarek pipeline // +import nextflow.Nextflow import groovy.text.SimpleTemplateEngine class WorkflowSarek { @@ -14,8 +15,7 @@ class WorkflowSarek { if (!params.fasta) { - log.error "Genome fasta file not specified with e.g. '--fasta genome.fa' or via a detectable config file." - System.exit(1) + Nextflow.error("Genome fasta file not specified with e.g. '--fasta genome.fa' or via a detectable config file.") } } @@ -66,39 +66,38 @@ class WorkflowSarek { // private static void genomeExistsError(params, log) { if (params.genomes && params.genome && !params.genomes.containsKey(params.genome)) { - log.error "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n" + + def error_string = "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n" + " Genome '${params.genome}' not found in any config files provided to the pipeline.\n" + " Currently, the available genome keys are:\n" + " ${params.genomes.keySet().join(", ")}\n" + "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~" - System.exit(1) + Nextflow.error(error_string) } } public static String retrieveInput(params, log){ if (!params.build_only_index) { switch (params.step) { - case 'mapping': log.warn "Can't start with step $params.step without samplesheet" - System.exit(1); + case 'mapping': Nextflow.error("Can't start with step $params.step without samplesheet") break - case 'markduplicates': log.warn "Using file ${params.outdir}/csv/mapped.csv" + case 'markduplicates': Nextflow.warn("Using file ${params.outdir}/csv/mapped.csv") params.putIfAbsent("input","${params.outdir}/csv/mapped.csv"); break - case 'prepare_recalibration': log.warn "Using file ${params.outdir}/csv/markduplicates_no_table.csv" + case 'prepare_recalibration': Nextflow.warn("Using file ${params.outdir}/csv/markduplicates_no_table.csv") params.putIfAbsent("input", "${params.outdir}/csv/markduplicates_no_table.csv"); break - case 'recalibrate': log.warn "Using file ${params.outdir}/csv/markduplicates.csv" + case 'recalibrate': Nextflow.warn("Using file ${params.outdir}/csv/markduplicates.csv") params.putIfAbsent("input", "${params.outdir}/csv/markduplicates.csv"); break - case 'variant_calling': log.warn "Using file ${params.outdir}/csv/recalibrated.csv" + case 'variant_calling': Nextflow.warn("Using file ${params.outdir}/csv/recalibrated.csv") params.putIfAbsent("input", "${params.outdir}/csv/recalibrated.csv"); break // case 'controlfreec': csv_file = file("${params.outdir}/variant_calling/csv/control-freec_mpileup.csv", checkIfExists: true); break - case 'annotate': log.warn "Using file ${params.outdir}/csv/variantcalled.csv" + case 'annotate': Nextflow.warn("Using file ${params.outdir}/csv/variantcalled.csv") params.putIfAbsent("input","${params.outdir}/csv/variantcalled.csv"); break - default: log.warn "Please provide an input samplesheet to the pipeline e.g. '--input samplesheet.csv'" - exit 1, "Unknown step $params.step" + default: Nextflow.warn("Please provide an input samplesheet to the pipeline e.g. '--input samplesheet.csv'") + Nextflow.error("Unknown step $params.step") } } } diff --git a/workflows/sarek.nf b/workflows/sarek.nf index 939495c0c5..3d382fe34c 100644 --- a/workflows/sarek.nf +++ b/workflows/sarek.nf @@ -60,9 +60,9 @@ input_sample = params.build_only_index ? Channel.empty() : extract_csv(file(para // Fails when wrongfull extension for intervals file if (params.wes && !params.step == 'annotate') { - if (params.intervals && !params.intervals.endsWith("bed")) exit 1, "Target file specified with `--intervals` must be in BED format for targeted data" + if (params.intervals && !params.intervals.endsWith("bed")) Nextflow.error("Target file specified with `--intervals` must be in BED format for targeted data") else log.warn("Intervals file was provided without parameter `--wes`: Pipeline will assume this is Whole-Genome-Sequencing data.") -} else if (params.intervals && !params.intervals.endsWith("bed") && !params.intervals.endsWith("list")) exit 1, "Intervals file must end with .bed, .list, or .interval_list" +} else if (params.intervals && !params.intervals.endsWith("bed") && !params.intervals.endsWith("list")) Nextflow.error("Intervals file must end with .bed, .list, or .interval_list") if (params.step == 'mapping' && params.aligner.contains("dragmap") && !(params.skip_tools && params.skip_tools.split(',').contains("baserecalibrator"))) { log.warn("DragMap was specified as aligner. Base recalibration is not contained in --skip_tools. It is recommended to skip baserecalibration when using DragMap\nhttps://gatk.broadinstitute.org/hc/en-us/articles/4407897446939--How-to-Run-germline-single-sample-short-variant-discovery-in-DRAGEN-mode") @@ -71,12 +71,10 @@ if (params.step == 'mapping' && params.aligner.contains("dragmap") && !(params.s // Fails or warns when missing files or params for ascat if (params.tools && params.tools.split(',').contains('ascat')) { if (!params.ascat_alleles) { - log.error "No allele files were provided for running ASCAT. Please provide a zip folder with allele files." - exit 1 + Nextflow.error("No allele files were provided for running ASCAT. Please provide a zip folder with allele files.") } if (!params.ascat_loci) { - log.error "No loci files were provided for running ASCAT. Please provide a zip folder with loci files." - exit 1 + Nextflow.error("No loci files were provided for running ASCAT. Please provide a zip folder with loci files.") } if (!params.ascat_loci_gc && !params.ascat_loci_rt) { log.warn("No LogRCorrection performed in ASCAT. For LogRCorrection to run, please provide either loci gc files or both loci gc files and loci rt files.") @@ -103,16 +101,14 @@ if (params.tools && params.tools.split(',').contains('mutect2')) { // Warns when missing resources for haplotypecaller if (!params.dbsnp && !params.known_indels) { if (params.step in ['mapping', 'markduplicates', 'prepare_recalibration', 'recalibrate'] && (!params.skip_tools || (params.skip_tools && !params.skip_tools.split(',').contains('baserecalibrator')))) { - log.error "Base quality score recalibration requires at least one resource file. Please provide at least one of `--dbsnp` or `--known_indels`\nYou can skip this step in the workflow by adding `--skip_tools baserecalibrator` to the command." - exit 1 + Nextflow.error("Base quality score recalibration requires at least one resource file. Please provide at least one of `--dbsnp` or `--known_indels`\nYou can skip this step in the workflow by adding `--skip_tools baserecalibrator` to the command.") } if (params.tools && params.tools.split(',').contains('haplotypecaller')) { log.warn "If Haplotypecaller is specified, without `--dbsnp` or `--known_indels no filtering will be done. For filtering, please provide at least one of `--dbsnp` or `--known_indels`.\nFor more information see FilterVariantTranches (single-sample, default): https://gatk.broadinstitute.org/hc/en-us/articles/5358928898971-FilterVariantTranches\nFor more information see VariantRecalibration (--joint_germline): https://gatk.broadinstitute.org/hc/en-us/articles/5358906115227-VariantRecalibrator\nFor more information on GATK Best practice germline variant calling: https://gatk.broadinstitute.org/hc/en-us/articles/360035535932-Germline-short-variant-discovery-SNPs-Indels-" } } if (params.joint_germline && (!params.tools || !params.tools.split(',').contains('haplotypecaller'))) { - log.error "The Haplotypecaller should be specified as one of the tools when doing joint germline variant calling. (The Haplotypecaller could be specified by adding `--tools haplotypecaller` to the nextflow command.) " - exit 1 + Nextflow.error("The Haplotypecaller should be specified as one of the tools when doing joint germline variant calling. (The Haplotypecaller could be specified by adding `--tools haplotypecaller` to the nextflow command.) ") } if (params.joint_germline && (!params.dbsnp || !params.known_indels || !params.known_snps || params.no_intervals)) { log.warn "If Haplotypecaller is specified, without `--dbsnp`, `--known_snps`, `--known_indels` or the associated resource labels (ie `known_snps_vqsr`), no variant recalibration will be done. For recalibration you must provide all of these resources.\nFor more information see VariantRecalibration: https://gatk.broadinstitute.org/hc/en-us/articles/5358906115227-VariantRecalibrator \nJoint germline variant calling also requires intervals in order to genotype the samples. As a result, if `--no_intervals` is set to `true` the joint germline variant calling will not be performed." @@ -120,16 +116,14 @@ if (params.joint_germline && (!params.dbsnp || !params.known_indels || !params.k // Fails when missing tools for variant_calling or annotate if ((params.step == 'variant_calling' || params.step == 'annotate') && !params.tools) { - log.error "Please specify at least one tool when using `--step ${params.step}`.\nhttps://nf-co.re/sarek/parameters#tools" - exit 1 + Nextflow.error("Please specify at least one tool when using `--step ${params.step}`.\nhttps://nf-co.re/sarek/parameters#tools") } // Fails when missing sex information for CNV tools if (params.tools && (params.tools.split(',').contains('ascat') || params.tools.split(',').contains('controlfreec'))) { input_sample.map{ if (it[0].sex == 'NA' ) { - log.error "Please specify sex information for each sample in your samplesheet when using '--tools' with 'ascat' or 'controlfreec'.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - exit 1 + Nextflow.error("Please specify sex information for each sample in your samplesheet when using '--tools' with 'ascat' or 'controlfreec'.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } } } @@ -1103,8 +1097,7 @@ def extract_csv(csv_file) { def line, samplesheet_line_count = 0; while ((line = reader.readLine()) != null) {samplesheet_line_count++} if (samplesheet_line_count < 2) { - log.error "Samplesheet had less than two lines. The sample sheet must be a csv file with a header, so at least two lines." - System.exit(1) + Nextflow.error("Samplesheet had less than two lines. The sample sheet must be a csv file with a header, so at least two lines.") } } @@ -1118,13 +1111,11 @@ def extract_csv(csv_file) { .map{ row -> if (params.step == "mapping") { if ( !row.lane ) { // This also handles the case where the lane is left as an empty string - log.error('The sample sheet should specify a lane for patient "' + row.patient.toString() + '" and sample "' + row.sample.toString() + '".') - System.exit(1) + Nextflow.error('The sample sheet should specify a lane for patient "' + row.patient.toString() + '" and sample "' + row.sample.toString() + '".') } def patient_sample_lane = [row.patient.toString(), row.sample.toString(), row.lane.toString()] if (patient_sample_lane in patient_sample_lane_combinations) { - log.error('The patient-sample-lane combination "' + row.patient.toString() + '", "' + row.sample.toString() + '", and "' + row.lane.toString() + '" is present multiple times in the sample sheet.') - System.exit(1) + Nextflow.error('The patient-sample-lane combination "' + row.patient.toString() + '", "' + row.sample.toString() + '", and "' + row.lane.toString() + '" is present multiple times in the sample sheet.') } else { patient_sample_lane_combinations.add(patient_sample_lane) } @@ -1132,8 +1123,7 @@ def extract_csv(csv_file) { if (!sample2patient.containsKey(row.sample.toString())) { sample2patient[row.sample.toString()] = row.patient.toString() } else if (sample2patient[row.sample.toString()] != row.patient.toString()) { - log.error('The sample "' + row.sample.toString() + '" is registered for both patient "' + row.patient.toString() + '" and "' + sample2patient[row.sample.toString()] + '" in the sample sheet.') - System.exit(1) + Nextflow.error('The sample "' + row.sample.toString() + '" is registered for both patient "' + row.patient.toString() + '" and "' + sample2patient[row.sample.toString()] + '" in the sample sheet.') } } @@ -1146,12 +1136,10 @@ def extract_csv(csv_file) { .map{ row -> sample_count_all++ if (!(row.patient && row.sample)) { - log.error "Missing field in csv file header. The csv file must have fields named 'patient' and 'sample'." - System.exit(1) + Nextflow.error("Missing field in csv file header. The csv file must have fields named 'patient' and 'sample'.") } else if (row.patient.contains(" ") || row.sample.contains(" ")) { - log.error "Invalid value in csv file. Values for 'patient' and 'sample' can not contain space." - System.exit(1) + Nextflow.error("Invalid value in csv file. Values for 'patient' and 'sample' can not contain space.") } [ [ row.patient.toString(), row.sample.toString() ], row ] }.groupTuple() @@ -1192,8 +1180,7 @@ def extract_csv(csv_file) { if (params.tools.split(',').contains(tool)) tools_tumor_asked.add(tool) } if (!tools_tumor_asked.isEmpty()) { - log.error('The sample-sheet only contains normal-samples, but the following tools, which were requested with "--tools", expect at least one tumor-sample : ' + tools_tumor_asked.join(", ")) - System.exit(1) + Nextflow.error('The sample-sheet only contains normal-samples, but the following tools, which were requested with "--tools", expect at least one tumor-sample : ' + tools_tumor_asked.join(", ")) } } else if ((sample_count_tumor == sample_count_all) && params.tools) { // In this case, the sample-sheet contains no normal/germline-samples def tools_requiring_normal_samples = ['ascat', 'deepvariant', 'haplotypecaller', 'msisensorpro'] @@ -1202,8 +1189,7 @@ def extract_csv(csv_file) { if (params.tools.split(',').contains(tool_requiring_normal_samples)) requested_tools_requiring_normal_samples.add(tool_requiring_normal_samples) } if (!requested_tools_requiring_normal_samples.isEmpty()) { - log.error('The sample-sheet only contains tumor-samples, but the following tools, which were requested by the option "tools", expect at least one normal-sample : ' + requested_tools_requiring_normal_samples.join(", ")) - System.exit(1) + Nextflow.error('The sample-sheet only contains tumor-samples, but the following tools, which were requested by the option "tools", expect at least one normal-sample : ' + requested_tools_requiring_normal_samples.join(", ")) } } @@ -1226,14 +1212,13 @@ def extract_csv(csv_file) { if (params.step == 'mapping') return [ meta, [ fastq_1, fastq_2 ] ] else { - log.error "Samplesheet contains fastq files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains fastq files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // start from BAM } else if (row.lane && row.bam) { if (!row.bai) { - log.error "BAM index (bai) should be provided." + Nextflow.error("BAM index (bai) should be provided.") } meta.id = "${row.sample}-${row.lane}".toString() def bam = file(row.bam, checkIfExists: true) @@ -1249,8 +1234,7 @@ def extract_csv(csv_file) { if (params.step != 'annotate') return [ meta, bam, bai ] else { - log.error "Samplesheet contains bam files but step is `annotate`. The pipeline is expecting vcf files for the annotation. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains bam files but step is `annotate`. The pipeline is expecting vcf files for the annotation. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // recalibration @@ -1264,8 +1248,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, cram, crai, table ] else { - log.error "Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // recalibration when skipping MarkDuplicates @@ -1279,8 +1262,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, bam, bai, table ] else { - log.error "Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // prepare_recalibration or variant_calling @@ -1293,8 +1275,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, cram, crai ] else { - log.error "Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // prepare_recalibration when skipping MarkDuplicates or `--step markduplicates` @@ -1307,8 +1288,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, bam, bai ] else { - log.error "Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // annotation @@ -1321,12 +1301,10 @@ def extract_csv(csv_file) { if (params.step == 'annotate') return [ meta, vcf ] else { - log.error "Samplesheet contains vcf files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations" - System.exit(1) + Nextflow.error("Samplesheet contains vcf files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } } else { - log.error "Missing or unknown field in csv file header. Please check your samplesheet" - System.exit(1) + Nextflow.error("Missing or unknown field in csv file header. Please check your samplesheet") } } } From d4d57744c05484cde007f103a801cd2724894a82 Mon Sep 17 00:00:00 2001 From: Rike Date: Wed, 29 Mar 2023 14:18:52 +0200 Subject: [PATCH 2/6] Update changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 46977f0292..6150240071 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -47,6 +47,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - [#941](https://github.com/nf-core/sarek/pull/941) - Fix json validation for `tools`, `skip_tools` and `use_gatk_spark` [#892](https://github.com/nf-core/sarek/issues/892) - [#954](https://github.com/nf-core/sarek/pull/954) - Fix missing annotation keys with snpeff and ensemblvep for `hg19` - [#957](https://github.com/nf-core/sarek/pull/957) - Add `failOnDuplicate` and `failOnMismatch` options to all `join()` operator where it was possible +- [#982](https://github.com/nf-core/sarek/pull/982) - Remove usage of exit statements, using `Nextflow.error` instead ### Deprecated From d3cb23414fd476d97403280d51ef5888311db125 Mon Sep 17 00:00:00 2001 From: Rike Date: Wed, 29 Mar 2023 14:20:02 +0200 Subject: [PATCH 3/6] don't lint since we are ahead of template --- .nf-core.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.nf-core.yml b/.nf-core.yml index 32c76a05b8..93f9c894b2 100644 --- a/.nf-core.yml +++ b/.nf-core.yml @@ -10,4 +10,5 @@ lint: - docs/images/nf-core-sarek_logo_dark.png - docs/images/nf-core-sarek_logo_light.png - lib/NfcoreTemplate.groovy + - lib/NfcoreSchema.groovy template_strings: False From 4b9138c33d87428e50698be56a5cff247b77d9bf Mon Sep 17 00:00:00 2001 From: Rike Date: Thu, 30 Mar 2023 16:14:56 +0200 Subject: [PATCH 4/6] address reviews, remove nextflow.warn, replace with log --- lib/WorkflowMain.groovy | 2 -- lib/WorkflowSarek.groovy | 12 ++++++------ 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/lib/WorkflowMain.groovy b/lib/WorkflowMain.groovy index f14c2b4679..255cbcdf57 100755 --- a/lib/WorkflowMain.groovy +++ b/lib/WorkflowMain.groovy @@ -2,8 +2,6 @@ // This file holds several functions specific to the main.nf workflow in the nf-core/sarek pipeline // -import nextflow.Nextflow - class WorkflowMain { // diff --git a/lib/WorkflowSarek.groovy b/lib/WorkflowSarek.groovy index 0dfd7e8222..2251f6f748 100755 --- a/lib/WorkflowSarek.groovy +++ b/lib/WorkflowSarek.groovy @@ -80,23 +80,23 @@ class WorkflowSarek { switch (params.step) { case 'mapping': Nextflow.error("Can't start with step $params.step without samplesheet") break - case 'markduplicates': Nextflow.warn("Using file ${params.outdir}/csv/mapped.csv") + case 'markduplicates': log.warn("Using file ${params.outdir}/csv/mapped.csv") params.putIfAbsent("input","${params.outdir}/csv/mapped.csv"); break - case 'prepare_recalibration': Nextflow.warn("Using file ${params.outdir}/csv/markduplicates_no_table.csv") + case 'prepare_recalibration': log.warn("Using file ${params.outdir}/csv/markduplicates_no_table.csv") params.putIfAbsent("input", "${params.outdir}/csv/markduplicates_no_table.csv"); break - case 'recalibrate': Nextflow.warn("Using file ${params.outdir}/csv/markduplicates.csv") + case 'recalibrate': log.warn("Using file ${params.outdir}/csv/markduplicates.csv") params.putIfAbsent("input", "${params.outdir}/csv/markduplicates.csv"); break - case 'variant_calling': Nextflow.warn("Using file ${params.outdir}/csv/recalibrated.csv") + case 'variant_calling': log.warn("Using file ${params.outdir}/csv/recalibrated.csv") params.putIfAbsent("input", "${params.outdir}/csv/recalibrated.csv"); break // case 'controlfreec': csv_file = file("${params.outdir}/variant_calling/csv/control-freec_mpileup.csv", checkIfExists: true); break - case 'annotate': Nextflow.warn("Using file ${params.outdir}/csv/variantcalled.csv") + case 'annotate': log.warn("Using file ${params.outdir}/csv/variantcalled.csv") params.putIfAbsent("input","${params.outdir}/csv/variantcalled.csv"); break - default: Nextflow.warn("Please provide an input samplesheet to the pipeline e.g. '--input samplesheet.csv'") + default: log.warn("Please provide an input samplesheet to the pipeline e.g. '--input samplesheet.csv'") Nextflow.error("Unknown step $params.step") } } From 7c76ff3bdfa3f9f089a34beb383876c1cfc096f8 Mon Sep 17 00:00:00 2001 From: Rike Date: Thu, 30 Mar 2023 21:44:55 +0200 Subject: [PATCH 5/6] import nextflow --- workflows/sarek.nf | 1 + 1 file changed, 1 insertion(+) diff --git a/workflows/sarek.nf b/workflows/sarek.nf index 3d382fe34c..958b148c44 100644 --- a/workflows/sarek.nf +++ b/workflows/sarek.nf @@ -4,6 +4,7 @@ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */ +import nextflow.Nextflow def summary_params = NfcoreSchema.paramsSummaryMap(workflow, params) // Validate input parameters From 4b6689b1aa1ac12fa85e0f5b0290e7db62ee7eaf Mon Sep 17 00:00:00 2001 From: Robert Syme Date: Fri, 31 Mar 2023 11:23:54 +0100 Subject: [PATCH 6/6] Apply suggestions from code review We don't need to `import nextflow.Nextflow` inside Nextflow scripts because the methods are already in scope --- workflows/sarek.nf | 51 +++++++++++++++++++++++----------------------- 1 file changed, 25 insertions(+), 26 deletions(-) diff --git a/workflows/sarek.nf b/workflows/sarek.nf index 958b148c44..f3b025909b 100644 --- a/workflows/sarek.nf +++ b/workflows/sarek.nf @@ -4,7 +4,6 @@ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */ -import nextflow.Nextflow def summary_params = NfcoreSchema.paramsSummaryMap(workflow, params) // Validate input parameters @@ -61,9 +60,9 @@ input_sample = params.build_only_index ? Channel.empty() : extract_csv(file(para // Fails when wrongfull extension for intervals file if (params.wes && !params.step == 'annotate') { - if (params.intervals && !params.intervals.endsWith("bed")) Nextflow.error("Target file specified with `--intervals` must be in BED format for targeted data") + if (params.intervals && !params.intervals.endsWith("bed")) error("Target file specified with `--intervals` must be in BED format for targeted data") else log.warn("Intervals file was provided without parameter `--wes`: Pipeline will assume this is Whole-Genome-Sequencing data.") -} else if (params.intervals && !params.intervals.endsWith("bed") && !params.intervals.endsWith("list")) Nextflow.error("Intervals file must end with .bed, .list, or .interval_list") +} else if (params.intervals && !params.intervals.endsWith("bed") && !params.intervals.endsWith("list")) error("Intervals file must end with .bed, .list, or .interval_list") if (params.step == 'mapping' && params.aligner.contains("dragmap") && !(params.skip_tools && params.skip_tools.split(',').contains("baserecalibrator"))) { log.warn("DragMap was specified as aligner. Base recalibration is not contained in --skip_tools. It is recommended to skip baserecalibration when using DragMap\nhttps://gatk.broadinstitute.org/hc/en-us/articles/4407897446939--How-to-Run-germline-single-sample-short-variant-discovery-in-DRAGEN-mode") @@ -72,10 +71,10 @@ if (params.step == 'mapping' && params.aligner.contains("dragmap") && !(params.s // Fails or warns when missing files or params for ascat if (params.tools && params.tools.split(',').contains('ascat')) { if (!params.ascat_alleles) { - Nextflow.error("No allele files were provided for running ASCAT. Please provide a zip folder with allele files.") + error("No allele files were provided for running ASCAT. Please provide a zip folder with allele files.") } if (!params.ascat_loci) { - Nextflow.error("No loci files were provided for running ASCAT. Please provide a zip folder with loci files.") + error("No loci files were provided for running ASCAT. Please provide a zip folder with loci files.") } if (!params.ascat_loci_gc && !params.ascat_loci_rt) { log.warn("No LogRCorrection performed in ASCAT. For LogRCorrection to run, please provide either loci gc files or both loci gc files and loci rt files.") @@ -102,14 +101,14 @@ if (params.tools && params.tools.split(',').contains('mutect2')) { // Warns when missing resources for haplotypecaller if (!params.dbsnp && !params.known_indels) { if (params.step in ['mapping', 'markduplicates', 'prepare_recalibration', 'recalibrate'] && (!params.skip_tools || (params.skip_tools && !params.skip_tools.split(',').contains('baserecalibrator')))) { - Nextflow.error("Base quality score recalibration requires at least one resource file. Please provide at least one of `--dbsnp` or `--known_indels`\nYou can skip this step in the workflow by adding `--skip_tools baserecalibrator` to the command.") + error("Base quality score recalibration requires at least one resource file. Please provide at least one of `--dbsnp` or `--known_indels`\nYou can skip this step in the workflow by adding `--skip_tools baserecalibrator` to the command.") } if (params.tools && params.tools.split(',').contains('haplotypecaller')) { log.warn "If Haplotypecaller is specified, without `--dbsnp` or `--known_indels no filtering will be done. For filtering, please provide at least one of `--dbsnp` or `--known_indels`.\nFor more information see FilterVariantTranches (single-sample, default): https://gatk.broadinstitute.org/hc/en-us/articles/5358928898971-FilterVariantTranches\nFor more information see VariantRecalibration (--joint_germline): https://gatk.broadinstitute.org/hc/en-us/articles/5358906115227-VariantRecalibrator\nFor more information on GATK Best practice germline variant calling: https://gatk.broadinstitute.org/hc/en-us/articles/360035535932-Germline-short-variant-discovery-SNPs-Indels-" } } if (params.joint_germline && (!params.tools || !params.tools.split(',').contains('haplotypecaller'))) { - Nextflow.error("The Haplotypecaller should be specified as one of the tools when doing joint germline variant calling. (The Haplotypecaller could be specified by adding `--tools haplotypecaller` to the nextflow command.) ") + error("The Haplotypecaller should be specified as one of the tools when doing joint germline variant calling. (The Haplotypecaller could be specified by adding `--tools haplotypecaller` to the nextflow command.) ") } if (params.joint_germline && (!params.dbsnp || !params.known_indels || !params.known_snps || params.no_intervals)) { log.warn "If Haplotypecaller is specified, without `--dbsnp`, `--known_snps`, `--known_indels` or the associated resource labels (ie `known_snps_vqsr`), no variant recalibration will be done. For recalibration you must provide all of these resources.\nFor more information see VariantRecalibration: https://gatk.broadinstitute.org/hc/en-us/articles/5358906115227-VariantRecalibrator \nJoint germline variant calling also requires intervals in order to genotype the samples. As a result, if `--no_intervals` is set to `true` the joint germline variant calling will not be performed." @@ -117,14 +116,14 @@ if (params.joint_germline && (!params.dbsnp || !params.known_indels || !params.k // Fails when missing tools for variant_calling or annotate if ((params.step == 'variant_calling' || params.step == 'annotate') && !params.tools) { - Nextflow.error("Please specify at least one tool when using `--step ${params.step}`.\nhttps://nf-co.re/sarek/parameters#tools") + error("Please specify at least one tool when using `--step ${params.step}`.\nhttps://nf-co.re/sarek/parameters#tools") } // Fails when missing sex information for CNV tools if (params.tools && (params.tools.split(',').contains('ascat') || params.tools.split(',').contains('controlfreec'))) { input_sample.map{ if (it[0].sex == 'NA' ) { - Nextflow.error("Please specify sex information for each sample in your samplesheet when using '--tools' with 'ascat' or 'controlfreec'.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Please specify sex information for each sample in your samplesheet when using '--tools' with 'ascat' or 'controlfreec'.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } } } @@ -1098,7 +1097,7 @@ def extract_csv(csv_file) { def line, samplesheet_line_count = 0; while ((line = reader.readLine()) != null) {samplesheet_line_count++} if (samplesheet_line_count < 2) { - Nextflow.error("Samplesheet had less than two lines. The sample sheet must be a csv file with a header, so at least two lines.") + error("Samplesheet had less than two lines. The sample sheet must be a csv file with a header, so at least two lines.") } } @@ -1112,11 +1111,11 @@ def extract_csv(csv_file) { .map{ row -> if (params.step == "mapping") { if ( !row.lane ) { // This also handles the case where the lane is left as an empty string - Nextflow.error('The sample sheet should specify a lane for patient "' + row.patient.toString() + '" and sample "' + row.sample.toString() + '".') + error('The sample sheet should specify a lane for patient "' + row.patient.toString() + '" and sample "' + row.sample.toString() + '".') } def patient_sample_lane = [row.patient.toString(), row.sample.toString(), row.lane.toString()] if (patient_sample_lane in patient_sample_lane_combinations) { - Nextflow.error('The patient-sample-lane combination "' + row.patient.toString() + '", "' + row.sample.toString() + '", and "' + row.lane.toString() + '" is present multiple times in the sample sheet.') + error('The patient-sample-lane combination "' + row.patient.toString() + '", "' + row.sample.toString() + '", and "' + row.lane.toString() + '" is present multiple times in the sample sheet.') } else { patient_sample_lane_combinations.add(patient_sample_lane) } @@ -1124,7 +1123,7 @@ def extract_csv(csv_file) { if (!sample2patient.containsKey(row.sample.toString())) { sample2patient[row.sample.toString()] = row.patient.toString() } else if (sample2patient[row.sample.toString()] != row.patient.toString()) { - Nextflow.error('The sample "' + row.sample.toString() + '" is registered for both patient "' + row.patient.toString() + '" and "' + sample2patient[row.sample.toString()] + '" in the sample sheet.') + error('The sample "' + row.sample.toString() + '" is registered for both patient "' + row.patient.toString() + '" and "' + sample2patient[row.sample.toString()] + '" in the sample sheet.') } } @@ -1137,10 +1136,10 @@ def extract_csv(csv_file) { .map{ row -> sample_count_all++ if (!(row.patient && row.sample)) { - Nextflow.error("Missing field in csv file header. The csv file must have fields named 'patient' and 'sample'.") + error("Missing field in csv file header. The csv file must have fields named 'patient' and 'sample'.") } else if (row.patient.contains(" ") || row.sample.contains(" ")) { - Nextflow.error("Invalid value in csv file. Values for 'patient' and 'sample' can not contain space.") + error("Invalid value in csv file. Values for 'patient' and 'sample' can not contain space.") } [ [ row.patient.toString(), row.sample.toString() ], row ] }.groupTuple() @@ -1181,7 +1180,7 @@ def extract_csv(csv_file) { if (params.tools.split(',').contains(tool)) tools_tumor_asked.add(tool) } if (!tools_tumor_asked.isEmpty()) { - Nextflow.error('The sample-sheet only contains normal-samples, but the following tools, which were requested with "--tools", expect at least one tumor-sample : ' + tools_tumor_asked.join(", ")) + error('The sample-sheet only contains normal-samples, but the following tools, which were requested with "--tools", expect at least one tumor-sample : ' + tools_tumor_asked.join(", ")) } } else if ((sample_count_tumor == sample_count_all) && params.tools) { // In this case, the sample-sheet contains no normal/germline-samples def tools_requiring_normal_samples = ['ascat', 'deepvariant', 'haplotypecaller', 'msisensorpro'] @@ -1190,7 +1189,7 @@ def extract_csv(csv_file) { if (params.tools.split(',').contains(tool_requiring_normal_samples)) requested_tools_requiring_normal_samples.add(tool_requiring_normal_samples) } if (!requested_tools_requiring_normal_samples.isEmpty()) { - Nextflow.error('The sample-sheet only contains tumor-samples, but the following tools, which were requested by the option "tools", expect at least one normal-sample : ' + requested_tools_requiring_normal_samples.join(", ")) + error('The sample-sheet only contains tumor-samples, but the following tools, which were requested by the option "tools", expect at least one normal-sample : ' + requested_tools_requiring_normal_samples.join(", ")) } } @@ -1213,13 +1212,13 @@ def extract_csv(csv_file) { if (params.step == 'mapping') return [ meta, [ fastq_1, fastq_2 ] ] else { - Nextflow.error("Samplesheet contains fastq files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains fastq files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // start from BAM } else if (row.lane && row.bam) { if (!row.bai) { - Nextflow.error("BAM index (bai) should be provided.") + error("BAM index (bai) should be provided.") } meta.id = "${row.sample}-${row.lane}".toString() def bam = file(row.bam, checkIfExists: true) @@ -1235,7 +1234,7 @@ def extract_csv(csv_file) { if (params.step != 'annotate') return [ meta, bam, bai ] else { - Nextflow.error("Samplesheet contains bam files but step is `annotate`. The pipeline is expecting vcf files for the annotation. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains bam files but step is `annotate`. The pipeline is expecting vcf files for the annotation. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // recalibration @@ -1249,7 +1248,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, cram, crai, table ] else { - Nextflow.error("Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // recalibration when skipping MarkDuplicates @@ -1263,7 +1262,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, bam, bai, table ] else { - Nextflow.error("Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // prepare_recalibration or variant_calling @@ -1276,7 +1275,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, cram, crai ] else { - Nextflow.error("Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains cram files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // prepare_recalibration when skipping MarkDuplicates or `--step markduplicates` @@ -1289,7 +1288,7 @@ def extract_csv(csv_file) { if (!(params.step == 'mapping' || params.step == 'annotate')) return [ meta, bam, bai ] else { - Nextflow.error("Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains bam files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } // annotation @@ -1302,10 +1301,10 @@ def extract_csv(csv_file) { if (params.step == 'annotate') return [ meta, vcf ] else { - Nextflow.error("Samplesheet contains vcf files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") + error("Samplesheet contains vcf files but step is `$params.step`. Please check your samplesheet or adjust the step parameter.\nhttps://nf-co.re/sarek/usage#input-samplesheet-configurations") } } else { - Nextflow.error("Missing or unknown field in csv file header. Please check your samplesheet") + error("Missing or unknown field in csv file header. Please check your samplesheet") } } }