You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
This is a complete workflow, with a structure similar to the ones you saw in the 'Hello Nextflow' tutorial, that we can test independently. Let's try that now:
include { VALIDATE_NAME } from '../modules/validate_name'
116
+
include { SAY_HELLO } from '../modules/say_hello'
117
+
include { TIMESTAMP_GREETING } from '../modules/timestamp_greeting'
118
+
75
119
workflow GREETING_WORKFLOW {
76
120
take:
77
121
names_ch // Input channel with names
@@ -88,9 +132,56 @@ workflow GREETING_WORKFLOW {
88
132
}
89
133
```
90
134
91
-
This is already a complete workflow that we can test independently. You might notice that it's very similar to the `hello` workflow from the 'Hello Nextflow' tutorial, but with some additional syntax to allow it to receive input ('take:') and produce output ('emit:'). These are the connections we will use to compose a higher level workflow.
135
+
You can see that the workflow is now named and has a `take:` and `emit:` block, and these are the connections we will use to compose a higher level workflow.
136
+
The workflow content is also placed inside the `main:` block. Note also that we have removed the `names_ch` input channel declaration, as it's now passed as an argument to the workflow.
137
+
138
+
Let's test the workflow again to see if it works as expected:
This tells you about another new concept, an 'entry workflow'. The entry workflow is the workflow that gets called when you run a Nextflow script. By default, Nextflow will use an un-named workflow as the entry workflow, when present, and that's what you've been doing so far, with workflow blocks starting like this:
153
+
154
+
```groovy title="hello.nf" linenums="1"
155
+
workflow {
156
+
```
157
+
158
+
But our greeting workflow doesn't have an un-named workflow, rather we have a named workflow:
... so Nextflow will throw an error. We can actually tell Nextflow to use our named workflow as the entry workflow by adding this line to Nextflow's command line:
165
+
166
+
```bash title="Run the greeting workflow"
167
+
nextflow run workflows/greeting.nf -entry GREETING_WORKFLOW
168
+
```
169
+
170
+
This will also throw an error, because the workflow is expecting an input channel:
ERROR ~ Workflow `GREETING_WORKFLOW` declares 1 input channels but 0 were given
176
+
177
+
-- Check '.nextflow.log' file for details
178
+
```
179
+
180
+
... but if you wanted to call a named workflow that didn't require inputs, you could call it this way.
181
+
182
+
But we didn't add that syntax so we could call the workflow directly, we did it so we could compose it with other workflows. Let's start by creating a main workflow that imports and uses the `greeting` workflow.
92
183
93
-
### 1.3. Create and test the main workflow
184
+
### 1.4. Create and test the main workflow
94
185
95
186
Now we will create a main workflow that imports and uses the `greeting` workflow.
96
187
@@ -109,14 +200,16 @@ workflow {
109
200
110
201
```
111
202
203
+
Note that our workflow entry in this file is un-named, and that's because we're going to use it as an entry workflow.
It works! We've wrapped the named greeting workflow in a main workflow with an un-named entry `workflow` block. The main workflow is using the `GREETING_WORKFLOW` workflow almost (not quite) like a process, and passing the `names` channel as an argument.
227
+
133
228
### Takeaway
134
229
135
-
You should now have a working greeting workflow that:
230
+
In this section, you've learned several important concepts:
231
+
232
+
-**Named Workflows**: Creating a named workflow (`GREETING_WORKFLOW`) that can be imported and reused
233
+
-**Workflow Interfaces**: Defining clear inputs with `take:` and outputs with `emit:` to create a composable workflow
234
+
-**Entry Points**: Understanding that Nextflow needs an entry workflow (either unnamed or specified with `-entry`)
235
+
-**Workflow Composition**: Importing and using a named workflow within another workflow
236
+
-**Workflow Namespaces**: Accessing workflow outputs using the `.out` namespace (`GREETING_WORKFLOW.out.greetings`)
237
+
238
+
You now have a working greeting workflow that:
136
239
137
240
- Takes a channel of names as input
138
241
- Validates each name
139
242
- Creates a greeting for each valid name
140
243
- Adds timestamps to the greetings
244
+
- Exposes both original and timestamped greetings as outputs
245
+
246
+
This modular approach allows you to test the greeting workflow independently or use it as a component in larger pipelines.
We won't repeat the explanation of the composable syntax here, but note the named workflow is again declared with a `take:` and `emit:` block, and the workflow content is placed inside the `main:` block.
284
+
177
285
### 2.3. Update the main workflow
178
286
179
287
Update `main.nf` to use both workflows:
180
288
181
289
```groovy title="main.nf" linenums="1"
182
-
include { SAY_HELLO_UPPER } from '../modules/say_hello_upper'
183
-
include { REVERSE_TEXT } from '../modules/reverse_text'
290
+
include { GREETING_WORKFLOW } from './workflows/greeting'
291
+
include { TRANSFORM_WORKFLOW } from './workflows/transform'
@@ -255,14 +364,19 @@ In this side quest, we've explored the powerful concept of workflow composition
255
364
256
365
5.**Practiced Modular Design**: We experienced firsthand how breaking a pipeline into logical components makes the code more maintainable and easier to understand.
257
366
367
+
6.**Worked with Entry Points**: We learned that Nextflow requires an entry workflow (either unnamed or specified with `-entry`) to know where to start execution.
368
+
369
+
7.**Structured Workflow Content**: We wrapped workflow logic within the `main:` block.
370
+
258
371
This modular approach offers several advantages over monolithic pipelines:
259
372
260
373
- Each workflow can be developed, tested, and debugged independently
261
374
- Workflows can be reused across different pipelines
262
375
- The overall pipeline structure becomes more readable and maintainable
263
376
- Changes to one workflow don't necessarily affect others if the interfaces remain consistent
377
+
- Entry points can be configured to run different parts of your pipeline as needed
264
378
265
-
It's important to note that while calling workflows is a bit like calling processes, it's not the same. You can't, for example, run a workflow n times by calling it with a channel of size n- you would need to pass a channel of size n to the workflow and iterate internally.
379
+
It's important to note that while calling workflows is a bit like calling processes, it's not the same. You can't, for example, run a workflow n times by calling it with a channel of size n- you would need to pass a channel of size n to the workflow and iterate internally.
266
380
267
381
By mastering workflow composition, you're now equipped to build more sophisticated Nextflow pipelines that can handle complex bioinformatics tasks while remaining maintainable and scalable.
268
382
@@ -292,13 +406,50 @@ By mastering workflow composition, you're now equipped to build more sophisticat
292
406
}
293
407
```
294
408
295
-
3. **Workflow Composition**
409
+
3.**Main Block Structure**
410
+
411
+
```nextflow
412
+
workflow EXAMPLE_WORKFLOW {
413
+
take:
414
+
// Input channels are declared here
415
+
input_ch
416
+
417
+
main:
418
+
// Workflow logic goes here
419
+
// This is where processes are called and channels are manipulated
420
+
result_ch = SOME_PROCESS(input_ch)
421
+
422
+
emit:
423
+
// Output channels are declared here
424
+
output_ch = result_ch
425
+
}
426
+
```
427
+
428
+
4.**Workflow Composition**
429
+
296
430
```nextflow
297
431
// Using explicit connections
298
432
WORKFLOW_A(input_ch)
299
433
WORKFLOW_B(WORKFLOW_A.out.some_channel)
300
434
```
301
435
436
+
5.**Entry Points**
437
+
438
+
```nextflow
439
+
// Unnamed workflow (default entry point)
440
+
workflow {
441
+
// This is automatically the entry point when the script is run
0 commit comments