Repository: go-task/task

Issue #475: Ability to run certain commands even if other commands have failed
Created: 2021-04-20T12:20:12Z
As usual, I am loving this tool and I use it frequently. This has been a minor pain point (there is a work-around), but I would love to see a feature added which would reduce friction around cleaning up after a command or task.
The use case I've encountered is cleaning up test resources after running tests, regardless of whether or not the tests passed.
Here is a trimmed down version of something I have in a Taskfile currently:
test:setup:
  - echo "set up docker containers"
test:run:
  - echo "execute tests"
test:cleanup:
  - echo "remove docker containers"
test:
  - |
     (task test:setup test:run);
     EXIT_CODE=$?;
     task test:cleanup;
     exit $EXIT_CODE;
It is clearly possible to achieve the desired result with the current implementation, but it's not ideal, since the cleanup doesn't run if I terminate execution with CTRL-C or if some other interrupt mechanism kills the task.
I also have nested task output because I call task blah:blah from the shell within a task, which doesn't hurt anything but can be kind of annoying with longer task names.
I'm not 100% sure what form the solution should take, but I have a couple of ideas:
1. always flag for commands
Allow commands (both task: ... and cmd: ... forms) to have a property always that can be set to true to indicate that the command should run even if a previous command within the same task has failed.
Example:
test:
  - task: test:setup
  - task: test:run
  - task: test:cleanup
    always: true
2. cleanup for commands
Allow commands (both task: ... and cmd: ... forms) to accept a cleanup property which specifies one or more commands to be run as cleanup at the end of task execution (success or fail) once that command has been successfully executed. This is sort of analogous to defer in go, in the sense that once the top-level command is executed, successfully, the cleanup command is guaranteed to run regardless of whether or not the containing task succeeds or fails.
Example:
test:
  - task: test:setup
    cleanup:
      - task: test:cleanup
  - task: test: run
I have opened a PR (#474) to show how option 1 might be implemented, but ultimately I'd love to find a solution that the maintainers feel fits best with the tool. As long as I can avoid using sub-shells and long sections of bash to ensure cleanup is run, I will be happy :)

Duplicate issue #344: Add task pre and post operations (before, after)
Created: 2020-06-12T14:06:34Z
Be great if there was a way to add post processing similar in concept to preconditions but a bit more flexible.
The goal is to be able to have pre- and post- operations surround a task sequence.
For example, the pre- would be the setup (much like a test runner), and the post- would be the cleanup.
It's conceivable it can be done with sequential tasks under cmds: , but it gets messy because of the added bash code to track exit codes, shove in variables, add ignore_errors (which you may or may not forget to add or remove at times), and test those to abort follow on tasks but not the cleanup task.
It would be cleaner to have a pre- and post- sequence that could surround the cmd, instead of writing nuance around cmd sequences or adding additional tasks.
Thinking something like...
task:
  example:
    before:
      - docker run -d --name server -p 8080:80 nginx
    cmds:
      - curl http://localhost:8080 | awk '{print}/error/{exit 1}'
      - echo "I may or may not get here"
    after:
      - docker rm server -f

To extend it further, you could conceivably have different flags that could determine which operations in after should/should not run depending on the eventual exit result (it could even be a number, or simply a success/failure) ...
after:
   - echo "Fires only if the cmds sequence failed"
   if_errors: true
   - echo "Fires if no error"
   if_errors: false
   - echo "Fires regardless"
   - echo "Send message to slack if we got a 25, as we know where that came from"
   if_error: 25

Closing comment (2023-02-11T22:21:27Z): I'm going to close this as a duplicate of #475 now that defer: is implemented:

#626
https://taskfile.dev/usage/#doing-task-cleanup-with-defer

The ability to run something on error is being track on #141.