-
Notifications
You must be signed in to change notification settings - Fork 404
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversion to DSL2 #234
Merged
Merged
Conversion to DSL2 #234
Changes from all commits
Commits
Show all changes
12 commits
Select commit
Hold shift + click to select a range
5a09706
getting functions into groovy libs
ggabernet c721801
first workflow draft
ggabernet 1981679
update NXF version
ggabernet 442ad0d
move sarek functions to functions.nf
ggabernet 07c2d1b
clean nextflow functions
ggabernet 8e1d0b2
commenting out unnecessary stuff for now
ggabernet 9dee363
Making Fastqc work
ggabernet a49492e
update get_software_versions
ggabernet 966ab2a
Co-authored-by: FriederikeHanssen <friederike.hanssen@student.uni-tue…
ggabernet ab7ed26
work on indices
ggabernet 0cfffa6
buildindices subworkflow
ggabernet ca5e36d
Merge branch 'dsl2' into dsl2
maxulysse File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
123,125 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
/* | ||
* This file holds several functions used to perform standard checks for the nf-core pipeline template. | ||
*/ | ||
|
||
class Checks { | ||
|
||
static void aws_batch(workflow, params) { | ||
if (workflow.profile.contains('awsbatch')) { | ||
assert !params.awsqueue || !params.awsregion : "Specify correct --awsqueue and --awsregion parameters on AWSBatch!" | ||
// Check outdir paths to be S3 buckets if running on AWSBatch | ||
// related: https://github.com/nextflow-io/nextflow/issues/813 | ||
assert !params.outdir.startsWith('s3:') : "Outdir not on S3 - specify S3 Bucket to run on AWSBatch!" | ||
// Prevent trace files to be stored on S3 since S3 does not support rolling files. | ||
assert params.tracedir.startsWith('s3:') : "Specify a local tracedir or run without trace! S3 cannot be used for tracefiles." | ||
} | ||
} | ||
|
||
static void hostname(workflow, params, log) { | ||
Map colors = Headers.log_colours(params.monochrome_logs) | ||
if (params.hostnames) { | ||
def hostname = "hostname".execute().text.trim() | ||
params.hostnames.each { prof, hnames -> | ||
hnames.each { hname -> | ||
if (hostname.contains(hname) && !workflow.profile.contains(prof)) { | ||
log.info "=${colors.yellow}====================================================${colors.reset}=\n" + | ||
"${colors.yellow}WARN: You are running with `-profile $workflow.profile`\n" + | ||
" but your machine hostname is ${colors.white}'$hostname'${colors.reset}.\n" + | ||
" ${colors.yellow_bold}Please use `-profile $prof${colors.reset}`\n" + | ||
"=${colors.yellow}====================================================${colors.reset}=" | ||
} | ||
} | ||
} | ||
} | ||
} | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,119 @@ | ||
/* | ||
* Functions to be run on completion of pipeline | ||
*/ | ||
|
||
class Completion { | ||
static void email(workflow, params, summary, run_name, baseDir, multiqc_report, log) { | ||
|
||
// Set up the e-mail variables | ||
def subject = "[$workflow.manifest.name] Successful: $workflow.runName" | ||
if (!workflow.success) { | ||
subject = "[$workflow.manifest.name] FAILED: $workflow.runName" | ||
} | ||
|
||
def email_fields = [:] | ||
email_fields['version'] = workflow.manifest.version | ||
email_fields['runName'] = run_name ?: workflow.runName | ||
email_fields['success'] = workflow.success | ||
email_fields['dateComplete'] = workflow.complete | ||
email_fields['duration'] = workflow.duration | ||
email_fields['exitStatus'] = workflow.exitStatus | ||
email_fields['errorMessage'] = (workflow.errorMessage ?: 'None') | ||
email_fields['errorReport'] = (workflow.errorReport ?: 'None') | ||
email_fields['commandLine'] = workflow.commandLine | ||
email_fields['projectDir'] = workflow.projectDir | ||
email_fields['summary'] = summary | ||
email_fields['summary']['Date Started'] = workflow.start | ||
email_fields['summary']['Date Completed'] = workflow.complete | ||
email_fields['summary']['Pipeline script file path'] = workflow.scriptFile | ||
email_fields['summary']['Pipeline script hash ID'] = workflow.scriptId | ||
if (workflow.repository) email_fields['summary']['Pipeline repository Git URL'] = workflow.repository | ||
if (workflow.commitId) email_fields['summary']['Pipeline repository Git Commit'] = workflow.commitId | ||
if (workflow.revision) email_fields['summary']['Pipeline Git branch/tag'] = workflow.revision | ||
email_fields['summary']['Nextflow Version'] = workflow.nextflow.version | ||
email_fields['summary']['Nextflow Build'] = workflow.nextflow.build | ||
email_fields['summary']['Nextflow Compile Timestamp'] = workflow.nextflow.timestamp | ||
|
||
// TODO nf-core: If not using MultiQC, strip out this code (including params.max_multiqc_email_size) | ||
// On success try attach the multiqc report | ||
def mqc_report = null | ||
try { | ||
if (workflow.success) { | ||
mqc_report = multiqc_report.getVal() | ||
if (mqc_report.getClass() == ArrayList) { | ||
log.warn "[$workflow.manifest.name] Found multiple reports from process 'MULTIQC', will use only one" | ||
mqc_report = mqc_report[0] | ||
} | ||
} | ||
} catch (all) { | ||
log.warn "[$workflow.manifest.name] Could not attach MultiQC report to summary email" | ||
} | ||
|
||
// Check if we are only sending emails on failure | ||
def email_address = params.email | ||
if (!params.email && params.email_on_fail && !workflow.success) { | ||
email_address = params.email_on_fail | ||
} | ||
|
||
// Render the TXT template | ||
def engine = new groovy.text.GStringTemplateEngine() | ||
def tf = new File("$baseDir/assets/email_template.txt") | ||
def txt_template = engine.createTemplate(tf).make(email_fields) | ||
def email_txt = txt_template.toString() | ||
|
||
// Render the HTML template | ||
def hf = new File("$baseDir/assets/email_template.html") | ||
def html_template = engine.createTemplate(hf).make(email_fields) | ||
def email_html = html_template.toString() | ||
|
||
// Render the sendmail template | ||
def smail_fields = [ email: email_address, subject: subject, email_txt: email_txt, email_html: email_html, baseDir: "$baseDir", mqcFile: mqc_report, mqcMaxSize: params.max_multiqc_email_size.toBytes() ] | ||
def sf = new File("$baseDir/assets/sendmail_template.txt") | ||
def sendmail_template = engine.createTemplate(sf).make(smail_fields) | ||
def sendmail_html = sendmail_template.toString() | ||
|
||
// Send the HTML e-mail | ||
if (email_address) { | ||
try { | ||
if (params.plaintext_email) { throw GroovyException('Send plaintext e-mail, not HTML') } | ||
// Try to send HTML e-mail using sendmail | ||
[ 'sendmail', '-t' ].execute() << sendmail_html | ||
log.info "[$workflow.manifest.name] Sent summary e-mail to $email_address (sendmail)" | ||
} catch (all) { | ||
// Catch failures and try with plaintext | ||
def mail_cmd = [ 'mail', '-s', subject, '--content-type=text/html', email_address ] | ||
if ( mqc_report.size() <= params.max_multiqc_email_size.toBytes() ) { | ||
mail_cmd += [ '-A', mqc_report ] | ||
} | ||
mail_cmd.execute() << email_html | ||
log.info "[$workflow.manifest.name] Sent summary e-mail to $email_address (mail)" | ||
} | ||
} | ||
|
||
// Write summary e-mail HTML to a file | ||
def output_d = new File("${params.outdir}/pipeline_info/") | ||
if (!output_d.exists()) { | ||
output_d.mkdirs() | ||
} | ||
def output_hf = new File(output_d, "pipeline_report.html") | ||
output_hf.withWriter { w -> w << email_html } | ||
def output_tf = new File(output_d, "pipeline_report.txt") | ||
output_tf.withWriter { w -> w << email_txt } | ||
} | ||
|
||
static void summary(workflow, params, log) { | ||
Map colors = Headers.log_colours(params.monochrome_logs) | ||
if (workflow.stats.ignoredCount > 0 && workflow.success) { | ||
log.info "-${colors.purple}Warning, pipeline completed, but with errored process(es) ${colors.reset}-" | ||
log.info "-${colors.red}Number of ignored errored process(es) : ${workflow.stats.ignoredCount} ${colors.reset}-" | ||
log.info "-${colors.green}Number of successfully ran process(es) : ${workflow.stats.succeedCount} ${colors.reset}-" | ||
} | ||
if (workflow.success) { | ||
log.info "-${colors.purple}[$workflow.manifest.name]${colors.green} Pipeline completed successfully${colors.reset}-" | ||
} else { | ||
Checks.hostname() | ||
log.info "-${colors.purple}[$workflow.manifest.name]${colors.red} Pipeline completed with errors${colors.reset}-" | ||
} | ||
} | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
/* | ||
* This file holds several functions used to render the nf-core ANSI header. | ||
*/ | ||
|
||
class Headers { | ||
|
||
private static Map log_colours(Boolean monochrome_logs) { | ||
Map colorcodes = [:] | ||
colorcodes['reset'] = monochrome_logs ? '' : "\033[0m" | ||
colorcodes['dim'] = monochrome_logs ? '' : "\033[2m" | ||
colorcodes['black'] = monochrome_logs ? '' : "\033[0;30m" | ||
colorcodes['green'] = monochrome_logs ? '' : "\033[0;32m" | ||
colorcodes['yellow'] = monochrome_logs ? '' : "\033[0;33m" | ||
colorcodes['yellow_bold'] = monochrome_logs ? '' : "\033[1;93m" | ||
colorcodes['blue'] = monochrome_logs ? '' : "\033[0;34m" | ||
colorcodes['purple'] = monochrome_logs ? '' : "\033[0;35m" | ||
colorcodes['cyan'] = monochrome_logs ? '' : "\033[0;36m" | ||
colorcodes['white'] = monochrome_logs ? '' : "\033[0;37m" | ||
colorcodes['red'] = monochrome_logs ? '' : "\033[1;91m" | ||
return colorcodes | ||
} | ||
|
||
static String nf_core(workflow, monochrome_logs) { | ||
Map colors = log_colours(monochrome_logs) | ||
String.format( | ||
"""\n | ||
-${colors.dim}----------------------------------------------------${colors.reset}- | ||
${colors.green},--.${colors.black}/${colors.green},-.${colors.reset} | ||
${colors.blue} ___ __ __ __ ___ ${colors.green}/,-._.--~\'${colors.reset} | ||
${colors.blue} |\\ | |__ __ / ` / \\ |__) |__ ${colors.yellow}} {${colors.reset} | ||
${colors.blue} | \\| | \\__, \\__/ | \\ |___ ${colors.green}\\`-._,-`-,${colors.reset} | ||
${colors.green}`._,._,\'${colors.reset} | ||
${colors.purple} ${workflow.manifest.name} v${workflow.manifest.version}${colors.reset} | ||
-${colors.dim}----------------------------------------------------${colors.reset}- | ||
""".stripIndent() | ||
) | ||
} | ||
} | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,128 @@ | ||
/* | ||
* This file holds several functions used to perform JSON parameter validation, help and summary rendering for the nf-core pipeline template. | ||
*/ | ||
|
||
import groovy.json.JsonSlurper | ||
|
||
class JSON { | ||
/* | ||
* This method tries to read a JSON params file | ||
*/ | ||
private static LinkedHashMap params_get(String path) { | ||
def usage = new LinkedHashMap() | ||
try { | ||
usage = params_try(path) | ||
} catch (Exception e) { | ||
println "Could not read parameters settings from JSON. $e" | ||
usage = new LinkedHashMap() | ||
} | ||
return usage | ||
} | ||
|
||
/* | ||
Method to actually read in JSON file using Groovy. | ||
Group (as Key), values are all parameters | ||
- Parameter1 as Key, Description as Value | ||
- Parameter2 as Key, Description as Value | ||
.... | ||
Group | ||
- | ||
*/ | ||
private static LinkedHashMap params_try(String path) throws Exception { | ||
|
||
def json = new File(path).text | ||
def Map usage = (Map) new JsonSlurper().parseText(json).get('properties') | ||
|
||
/* Tree looks like this in nf-core schema | ||
* properties <- this is what the first get('properties') gets us | ||
group 1 | ||
properties | ||
description | ||
group 2 | ||
properties | ||
description | ||
group 3 | ||
properties | ||
description | ||
*/ | ||
def output_map = new LinkedHashMap() | ||
|
||
// Lets go deeper | ||
usage.each { key, val -> | ||
def Map submap = usage."$key".properties // Gets the property object of the group | ||
def sub_params = new LinkedHashMap() | ||
submap.each { innerkey, value -> | ||
sub_params.put("$innerkey", "$value.description") | ||
} | ||
output_map.put("$key", sub_params) | ||
} | ||
return output_map | ||
} | ||
|
||
static String params_help(path, command) { | ||
String output = "Typical pipeline command:\n\n" | ||
output += " ${command}\n\n" | ||
output += params_beautify(params_get(path)) | ||
} | ||
|
||
static String params_beautify(usage) { | ||
String output = "" | ||
for (group in usage.keySet()) { | ||
output += group + "\n" | ||
def params = usage.get(group) // This gets the parameters of that particular group | ||
for (par in params.keySet()) { | ||
output+= " \u001B[1m" + par.padRight(27) + "\u001B[1m" + params.get(par) + "\n" | ||
} | ||
output += "\n" | ||
} | ||
return output | ||
} | ||
|
||
private static LinkedHashMap params_summary(workflow, params, run_name) { | ||
def Map summary = [:] | ||
if (workflow.revision) summary['Pipeline Release'] = workflow.revision | ||
summary['Run Name'] = run_name ?: workflow.runName | ||
// TODO nf-core: Report custom parameters here | ||
summary['Input'] = params.input | ||
summary['Fasta File'] = params.fasta | ||
summary['Max Resources'] = "$params.max_memory memory, $params.max_cpus cpus, $params.max_time time per job" | ||
if (workflow.containerEngine) summary['Container'] = "$workflow.containerEngine - $workflow.container" | ||
summary['Output dir'] = params.outdir | ||
summary['Launch dir'] = workflow.launchDir | ||
summary['Working dir'] = workflow.workDir | ||
summary['Script dir'] = workflow.projectDir | ||
summary['User'] = workflow.userName | ||
if (workflow.profile.contains('awsbatch')) { | ||
summary['AWS Region'] = params.awsregion | ||
summary['AWS Queue'] = params.awsqueue | ||
summary['AWS CLI'] = params.awscli | ||
} | ||
summary['Config Profile'] = workflow.profile | ||
if (params.config_profile_description) summary['Config Profile Descr'] = params.config_profile_description | ||
if (params.config_profile_contact) summary['Config Profile Contact'] = params.config_profile_contact | ||
if (params.config_profile_url) summary['Config Profile URL'] = params.config_profile_url | ||
summary['Config Files'] = workflow.configFiles.join(', ') | ||
if (params.email || params.email_on_fail) { | ||
summary['E-mail Address'] = params.email | ||
summary['E-mail on failure'] = params.email_on_fail | ||
summary['MultiQC maxsize'] = params.max_multiqc_email_size | ||
} | ||
return summary | ||
} | ||
|
||
static String params_mqc_summary(summary) { | ||
String yaml_file_text = """ | ||
id: 'nf-core-tcrseq-summary' | ||
description: " - this information is collected when the pipeline is started." | ||
section_name: 'nf-core/tcrseq Workflow Summary' | ||
section_href: 'https://github.com/nf-core/tcrseq' | ||
plot_type: 'html' | ||
data: | | ||
<dl class=\"dl-horizontal\"> | ||
${summary.collect { k,v -> " <dt>$k</dt><dd><samp>${v ?: '<span style=\"color:#999999;\">N/A</a>'}</samp></dd>" }.join("\n")} | ||
</dl> | ||
""".stripIndent() | ||
|
||
return yaml_file_text | ||
} | ||
} |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we keep the sarek ascii art?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
oh yes right you have the Sarek logo there as well! Of course!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I was thinking we could merge this PR and then work on these things in parallel?