Skip to content

Conversation

@solvingj
Copy link

@solvingj solvingj commented Feb 3, 2026

Relates to #669
Alternative Approach to #2677

Summary

This PR adds a new inherit_outdated attribute to task dependencies in the Taskfile. When set to true on a dependency, the parent task will be considered "not up-to-date" if that dependency (or any of its transitive dependencies marked with inherit_outdated) is not up-to-date.

Motivation

Currently, task --status my-task only checks if my-task itself is up-to-date, ignoring whether its dependencies are up-to-date. This makes it difficult to express tasks where the parent should be considered outdated when specific critical dependencies are outdated.

For software development cases, it's common to model this relationship via "generates" and "sources". This is how it was done canonically in Makefiles as well. However, "go-task" intends more general purpose, and has found purchase in many devops scenarios. In many non-development scenarios, tasks don't generate sources naturally so there's no native way to express this relationship. As a workaround, tasks can be engineered to generate "artificial files" like "stamp" files, but this is tedious and awkward and has holes.

This approach provides first-class, declarative control at the Taskfile level, allowing task authors to specify which dependencies should propagate their outdated status.

Comparison to Flag-Based Approach

This is an alternative to adding a --include-deps CLI flag. Key differences:

Flag-based approach (--include-deps):

  • Global behavior controlled at runtime via CLI flag
  • Applies to all dependencies of the specified task
  • User decides at execution time whether to check dependencies

Attribute-based approach (inherit_outdated):

  • Declarative behavior specified in the Taskfile
  • Selective - only specific dependencies are checked
  • Task author decides which dependencies are critical for up-to-date status
  • More flexible for complex dependency graphs

Changes

  • Add InheritOutdated field to Dep struct in taskfile/ast/dep.go
  • Update UnmarshalYAML to parse inherit_outdated from YAML
  • Update DeepCopy to preserve InheritOutdated field
  • Extract checkTaskStatus helper for reusable status checking
  • Add traverseInheritOutdated using same pattern as existing traverse function
  • Only traverse and check dependencies marked with inherit_outdated
  • Modify Status method to check dependencies with inherit_outdated attribute
  • Add comprehensive test suite with 7 test scenarios
  • Add testdata with tasks using inherit_outdated in various configurations
  • Support transitive dependency checking through nested inherit_outdated

Usage

Define dependencies with inherit_outdated: true in your Taskfile:

version: '3'

tasks:
  build:
    deps:
      - task: generate-code
        inherit_outdated: true  # If generate-code is outdated, build is outdated
      - task: install-tools     # No inherit_outdated, so only runs but doesn't affect build's status
    cmds:
      - go build
    sources:
      - "*.go"
    generates:
      - app

  generate-code:
    cmds:
      - protoc --go_out=. api.proto
    sources:
      - api.proto
    generates:
      - api.pb.go

  install-tools:
    cmds:
      - go install google.golang.org/protobuf/cmd/protoc-gen-go@latest
    status:
      - which protoc-gen-go

Then check status normally:

# Check if build is up-to-date
# This will check:
# - build's own sources/generates
# - generate-code's sources/generates (because of inherit_outdated)
# But will NOT check install-tools (no inherit_outdated)
$ task --status build

Use Cases

This is particularly useful when:

  1. Code generation: Parent task should be outdated if generated files need regeneration
  2. Build dependencies: Compilation should be considered outdated if generated assets are stale
  3. Selective checking: Only some dependencies affect the parent's up-to-date status
  4. Complex graphs: Different parts of the dependency tree have different relevance

Example: Multi-level Inheritance

version: '3'

tasks:
  deploy:
    deps:
      - task: build
        inherit_outdated: true
      - task: lint  # Optional, doesn't affect deploy status
    cmds:
      - kubectl apply -f deployment.yml

  build:
    deps:
      - task: compile
        inherit_outdated: true
      - task: test  # Tests run but don't affect build status
    cmds:
      - docker build -t myapp .

  compile:
    cmds:
      - go build
    sources:
      - "*.go"

With this setup, task --status deploy will check:

  • deploy's own status
  • build's status (inherit_outdated)
  • compile's status (transitive inherit_outdated through build)

But will NOT check lint or test tasks.

Implementation Details

  • Uses traverseInheritOutdated function that follows the same pattern as existing traverse function
  • Only traverses dependencies where InheritOutdated is true
  • Tracks visited tasks to avoid duplicate checks when tasks share dependencies
  • Uses the same checkTaskStatus logic that checks both status commands and sources/generates
  • Reports which specific dependency caused the parent to be outdated
  • Supports transitive checking through nested inherit_outdated dependencies

Testing

  • Added TestInheritOutdated with 7 comprehensive test scenarios
  • Tests cover dependencies with and without inherit_outdated
  • Tests verify transitive dependency checking
  • Tests verify mixed dependencies (some with, some without inherit_outdated)
  • All existing tests continue to pass

Backwards Compatibility

This change is fully backwards compatible:

  • The inherit_outdated attribute is optional and defaults to false
  • Existing Taskfiles work without any modifications
  • No changes to existing CLI flags or behavior

- Add InheritOutdated field to Dep struct in taskfile/ast/dep.go
- Update UnmarshalYAML to parse inherit_outdated from YAML
- Update DeepCopy to preserve InheritOutdated field
- Extract checkTaskStatus helper for reusable status checking
- Add traverseInheritOutdated using same pattern as existing traverse function
- Only traverse and check dependencies marked with inherit_outdated
- Modify Status method to check dependencies with inherit_outdated attribute
- Add comprehensive test suite with 7 test scenarios
- Add testdata with tasks using inherit_outdated in various configurations
- Support transitive dependency checking through nested inherit_outdated

Co-authored-by: Cursor <cursoragent@cursor.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant