Skip to content

Defining rules

Romain Feron edited this page Oct 23, 2019 · 8 revisions

Rules are the basic blocks of a Snakemake workflow. A rule is like a recipe indicating how to produce a specific output; the actual application of a rule to create an output is called a job.

A rule is defined in Snakefile with the keyword rule, and contains directives which indicate the rule's properties. We will learn about directives over the course of the workshop.

To create a basic rule, we need two directives:

  • output: path of the output file for this rule
  • shell: shell command to execute in order to generate the output

The following example shows the syntax to implement a basic rule using these two directives. The rule defined in this example creates a file first_step.txt containing the line "snakemake" and located in a results folder, using the echo shell command:

rule first_step:
    output:
        'results/first_step.txt'
    shell:
        'echo “snakemake” > {output}'

As this example shows, values for these two directives are strings. For the shell directive, the string can be written on multiple lines for clarity, simply using a set of quotes for each line. In addition, values from other directives can be accessed in the shell command with the syntax {directive}, and Snakemake will automatically insert the value when running a job for this rule; in the example, the value of output was obtained with {output}. Note that Snakemake automatically creates all missing folders in the output path.

The next directive used by most rules is input. Like output, input indicates the path to a file that is required by the rule to generate the output. In the following example, we modified the previous rule to use an input file first_step.tsv in a data folder and copy this file to results/first_step.txt:

rule first_step:
    input:
        'data/first_step.tsv'
    output:
        'results/first_step.txt'
    shell:
        'cp {input} {output}'

Note that with this rule definition, Snakemake will not run if data/first_step.tsv does not exist.

Rules can have multiple input and/or output files, with each file on a single line ending with a comma. In the shell command, multiple input will be unpacked, meaning {input} will be replaced with a space-separated list of input files. Alternatively, individual input files can be accessed by index with the syntax {input[N]}. In the following example, the rule was modified to concatenate the two inputs in the output file with cat and print the content of the first one:

rule first_step:
    input:
        'data/first_step_1.tsv',
        'data/first_step_2.tsv'
    output:
        'results/first_step.txt'
    shell:
        'cat {input} > {output};'
        'echo {input[0]}'

Do not forget the commas between input / output files ! It's the source of many errors when starting to write workflows.

Clone this wiki locally