Skip to content

fix: Raise WorkflowError on empty file path in _IOFile.check#3769

Merged
johanneskoester merged 12 commits into
mainfrom
fix/empty-file
Oct 3, 2025
Merged

fix: Raise WorkflowError on empty file path in _IOFile.check#3769
johanneskoester merged 12 commits into
mainfrom
fix/empty-file

Conversation

@Hocnonsense

@Hocnonsense Hocnonsense commented Oct 2, 2025

Copy link
Copy Markdown
Contributor

fix #341

Now the file with empty string will never pass the check.
Or should this be a warning instead of a WorkflowError?

QC

  • The PR contains a test case for the changes or the changes are already covered by an existing test case.
  • The documentation (docs/) is updated to reflect the changes or this is not necessary (e.g. if the change does neither modify the language nor the behavior or functionalities of Snakemake).

Summary by CodeRabbit

  • Bug Fixes

    • Added an early, clear error when an empty file path is provided, preventing downstream confusion.
  • Tests

    • Updated a conda-related test to use the conda-forge channel and assert successful execution.
  • Chores

    • Removed unused imports to reduce overhead.

@coderabbitai

coderabbitai Bot commented Oct 2, 2025

Copy link
Copy Markdown
Contributor
📝 Walkthrough

Walkthrough

Introduces an early validation in _IOFile.check to raise WorkflowError when a file path is an empty string. Removes unused ABC-related imports. Updates a conda-related test to use the conda-forge channel and assert a successful subprocess return code.

Changes

Cohort / File(s) Change summary
IO path validation
src/snakemake/io/__init__.py
Added guard in _IOFile.check to raise WorkflowError on empty string paths; removed unused ABC/abstractmethod imports. No public API changes.
Conda test invocation
tests/tests_using_conda.py
In test_issue_3192, added -c conda-forge to sp.run call and asserted returncode == 0; subsequent invocation of run unchanged.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  actor User
  participant Workflow as Workflow
  participant IOFile as _IOFile.check

  User->>Workflow: Define rule with output path
  Workflow->>IOFile: check(path)
  alt path is empty string
    IOFile-->>Workflow: raise WorkflowError (early)
    Workflow-->>User: Error surfaced
  else valid path
    IOFile-->>Workflow: proceed
    Workflow-->>User: Continue execution
  end
Loading

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

Pre-merge checks and finishing touches

❌ Failed checks (3 warnings)
Check name Status Explanation Resolution
Out of Scope Changes Check ⚠️ Warning The pull request includes unrelated changes such as removing unused imports of ABC and abstractmethod and modifying a test for issue 3192 in tests_using_conda.py, which are outside the scope of handling empty file paths for issue #341. Please remove or separate the unrelated import cleanup and test modifications into a separate pull request so that this change set focuses solely on the empty file path guard for issue #341.
Description Check ⚠️ Warning The PR description uses the QC section from the template but fails to indicate whether a test case has been added or the documentation has been updated, and it provides minimal detail about the implementation beyond referencing the issue number. Please update the description to confirm that a relevant test case for the new empty path guard has been added or already exists and specify any documentation updates made or note why none are needed.
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Title Check ✅ Passed The title clearly and concisely summarizes the primary change of raising a WorkflowError when an empty file path is encountered in _IOFile.check, matching the main purpose of the pull request without extraneous details.
Linked Issues Check ✅ Passed The changes add a guard in _IOFile.check to raise a WorkflowError for empty file paths, which directly addresses the linked issue’s goal of avoiding cryptic errors by explicitly handling empty outputs.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch fix/empty-file

📜 Recent review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between f1efc01 and 0ffc140.

📒 Files selected for processing (1)
  • tests/tests_using_conda.py (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.py

⚙️ CodeRabbit configuration file

**/*.py: Do not try to improve formatting.
Do not suggest type annotations for functions that are defined inside of functions or methods.
Do not suggest type annotation of the self argument of methods.
Do not suggest type annotation of the cls argument of classmethods.
Do not suggest return type annotation if a function or method does not contain a return statement.

Files:

  • tests/tests_using_conda.py
🪛 Ruff (0.13.2)
tests/tests_using_conda.py

327-327: subprocess call with shell=True seems safe, but may be changed in the future; consider rewriting without shell

(S602)


328-328: Starting a process with a partial executable path

(S607)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (44)
  • GitHub Check: tests (8, ubuntu-latest, py313)
  • GitHub Check: tests (10, ubuntu-latest, py313)
  • GitHub Check: tests (10, ubuntu-latest, py311)
  • GitHub Check: tests (10, ubuntu-latest, py312)
  • GitHub Check: tests (9, ubuntu-latest, py313)
  • GitHub Check: tests (8, ubuntu-latest, py312)
  • GitHub Check: tests (10, windows-2022, py313)
  • GitHub Check: tests (9, ubuntu-latest, py311)
  • GitHub Check: tests (9, windows-2022, py313)
  • GitHub Check: tests (7, ubuntu-latest, py313)
  • GitHub Check: tests (8, windows-2022, py313)
  • GitHub Check: tests (7, ubuntu-latest, py312)
  • GitHub Check: tests (9, ubuntu-latest, py312)
  • GitHub Check: tests (8, ubuntu-latest, py311)
  • GitHub Check: tests (5, macos-latest, py313)
  • GitHub Check: tests (7, windows-2022, py313)
  • GitHub Check: tests (6, macos-latest, py313)
  • GitHub Check: tests (5, ubuntu-latest, py313)
  • GitHub Check: tests (6, ubuntu-latest, py313)
  • GitHub Check: tests (7, macos-latest, py313)
  • GitHub Check: tests (6, windows-2022, py313)
  • GitHub Check: tests (7, ubuntu-latest, py311)
  • GitHub Check: tests (5, windows-2022, py313)
  • GitHub Check: tests (6, ubuntu-latest, py311)
  • GitHub Check: tests (5, ubuntu-latest, py312)
  • GitHub Check: tests (4, ubuntu-latest, py313)
  • GitHub Check: tests (6, ubuntu-latest, py312)
  • GitHub Check: tests (4, windows-2022, py313)
  • GitHub Check: tests (5, ubuntu-latest, py311)
  • GitHub Check: tests (4, ubuntu-latest, py311)
  • GitHub Check: tests (2, ubuntu-latest, py312)
  • GitHub Check: tests (4, ubuntu-latest, py312)
  • GitHub Check: tests (3, ubuntu-latest, py312)
  • GitHub Check: tests (3, ubuntu-latest, py311)
  • GitHub Check: tests (2, ubuntu-latest, py311)
  • GitHub Check: tests (2, windows-2022, py313)
  • GitHub Check: tests (3, windows-2022, py313)
  • GitHub Check: tests (2, ubuntu-latest, py313)
  • GitHub Check: tests (1, ubuntu-latest, py312)
  • GitHub Check: tests (3, ubuntu-latest, py313)
  • GitHub Check: tests (1, windows-2022, py313)
  • GitHub Check: tests (1, ubuntu-latest, py313)
  • GitHub Check: tests (1, macos-latest, py313)
  • GitHub Check: tests (1, ubuntu-latest, py311)
🔇 Additional comments (1)
tests/tests_using_conda.py (1)

326-332: LGTM! Improved test robustness.

The addition of the -c conda-forge channel flag and the assertion on returncode == 0 improve the reliability of the test by explicitly specifying the package source and ensuring the conda environment creation succeeds before proceeding.

Regarding the static analysis hints (S602, S607): These are false positives in this test context. The hardcoded command string with shell=True is safe, and using conda without a full path is standard practice when conda is on PATH (which is guaranteed by the @conda decorator).


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

🧹 Nitpick comments (1)
src/snakemake/io/__init__.py (1)

459-463: LGTM! Excellent fix for issue #341.

The empty-string check correctly prevents the cryptic IndexError downstream by raising a clear, actionable WorkflowError early. The placement after the callable check is correct, and passing rule=self.rule provides helpful context.

Optional style note: Ruff suggests avoiding long messages outside the exception class (TRY003). While the message is clear and not excessively long, you could optionally extract it to a constant or use a shorter inline message if you want to align with this guideline. However, this is a minor style preference and not a blocker.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 1549c8b and cec8526.

📒 Files selected for processing (1)
  • src/snakemake/io/__init__.py (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.py

⚙️ CodeRabbit configuration file

**/*.py: Do not try to improve formatting.
Do not suggest type annotations for functions that are defined inside of functions or methods.
Do not suggest type annotation of the self argument of methods.
Do not suggest type annotation of the cls argument of classmethods.
Do not suggest return type annotation if a function or method does not contain a return statement.

Files:

  • src/snakemake/io/__init__.py
🪛 Ruff (0.13.2)
src/snakemake/io/__init__.py

460-463: Avoid specifying long messages outside the exception class

(TRY003)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (34)
  • GitHub Check: tests (9, windows-2022, py313)
  • GitHub Check: tests (9, ubuntu-latest, py311)
  • GitHub Check: tests (10, windows-2022, py313)
  • GitHub Check: tests (7, windows-2022, py313)
  • GitHub Check: tests (9, ubuntu-latest, py312)
  • GitHub Check: tests (8, ubuntu-latest, py312)
  • GitHub Check: tests (8, windows-2022, py313)
  • GitHub Check: tests (7, ubuntu-latest, py311)
  • GitHub Check: tests (8, ubuntu-latest, py313)
  • GitHub Check: tests (5, ubuntu-latest, py311)
  • GitHub Check: tests (8, ubuntu-latest, py311)
  • GitHub Check: tests (6, windows-2022, py313)
  • GitHub Check: tests (6, ubuntu-latest, py312)
  • GitHub Check: tests (6, ubuntu-latest, py313)
  • GitHub Check: tests (4, windows-2022, py313)
  • GitHub Check: tests (5, ubuntu-latest, py312)
  • GitHub Check: tests (4, ubuntu-latest, py312)
  • GitHub Check: tests (6, ubuntu-latest, py311)
  • GitHub Check: tests (2, ubuntu-latest, py312)
  • GitHub Check: tests (5, ubuntu-latest, py313)
  • GitHub Check: tests (4, ubuntu-latest, py311)
  • GitHub Check: tests (5, windows-2022, py313)
  • GitHub Check: tests (3, ubuntu-latest, py311)
  • GitHub Check: tests (4, ubuntu-latest, py313)
  • GitHub Check: tests (2, windows-2022, py313)
  • GitHub Check: tests (3, ubuntu-latest, py312)
  • GitHub Check: tests (3, windows-2022, py313)
  • GitHub Check: tests (2, ubuntu-latest, py311)
  • GitHub Check: tests (1, ubuntu-latest, py312)
  • GitHub Check: tests (1, ubuntu-latest, py311)
  • GitHub Check: tests (2, ubuntu-latest, py313)
  • GitHub Check: tests (1, macos-latest, py313)
  • GitHub Check: tests (1, ubuntu-latest, py313)
  • GitHub Check: tests (1, windows-2022, py313)

@Hocnonsense Hocnonsense changed the title fix: clearly give a hint that there was an empty string fix: Raise WorkflowError on empty file path in _IOFile.check Oct 2, 2025

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
.github/workflows/main.yml (1)

50-113: Restore the full CI matrix and test suite.

This change collapses the matrix to a single Ubuntu/py313 run and limits pytest to -k test_issue_3192, effectively dropping all other OS/Python combinations and most of the test suite. That guts our CI coverage and will let regressions slip through. Please bring back the previous matrix breadth and full test run before merging.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 2a66570 and a45337f.

📒 Files selected for processing (4)
  • .github/workflows/main.yml (2 hunks)
  • src/snakemake/dag.py (1 hunks)
  • src/snakemake/deployment/conda.py (2 hunks)
  • tests/test_prebuilt_conda_script/env.yaml (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • tests/test_prebuilt_conda_script/env.yaml
🧰 Additional context used
📓 Path-based instructions (1)
**/*.py

⚙️ CodeRabbit configuration file

**/*.py: Do not try to improve formatting.
Do not suggest type annotations for functions that are defined inside of functions or methods.
Do not suggest type annotation of the self argument of methods.
Do not suggest type annotation of the cls argument of classmethods.
Do not suggest return type annotation if a function or method does not contain a return statement.

Files:

  • src/snakemake/deployment/conda.py
  • src/snakemake/dag.py
🪛 GitHub Actions: CI
src/snakemake/deployment/conda.py

[error] 178-178: WorkflowError: Error exporting conda environment --name '/home/runner/work/snakemake/snakemake/.pixi/envs/py313/envs/test_issue3192': CondaValueError: Environment names cannot contain path separators.

Comment thread src/snakemake/dag.py Outdated
Comment thread src/snakemake/deployment/conda.py Outdated
Comment thread src/snakemake/deployment/conda.py Outdated

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 6340895 and c4924c6.

📒 Files selected for processing (3)
  • src/snakemake/deployment/conda.py (1 hunks)
  • src/snakemake/rules.py (1 hunks)
  • tests/tests_using_conda.py (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • src/snakemake/deployment/conda.py
🧰 Additional context used
📓 Path-based instructions (1)
**/*.py

⚙️ CodeRabbit configuration file

**/*.py: Do not try to improve formatting.
Do not suggest type annotations for functions that are defined inside of functions or methods.
Do not suggest type annotation of the self argument of methods.
Do not suggest type annotation of the cls argument of classmethods.
Do not suggest return type annotation if a function or method does not contain a return statement.

Files:

  • src/snakemake/rules.py
  • tests/tests_using_conda.py
🪛 GitHub Actions: CI
src/snakemake/rules.py

[error] 1205-1205: AssertionError: CondaEnvSpecType.from_spec(conda_env) did not yield DIR as expected. Expected a directory-based Conda env spec, but got a different spec type (NAME). This causes conda environment expansion to fail during DAG initialization.

🪛 Ruff (0.13.2)
tests/tests_using_conda.py

327-327: Starting a process with a partial executable path

(S607)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: apidocs
🔇 Additional comments (1)
tests/tests_using_conda.py (1)

327-327: LGTM! Auto-confirm flag improves test reliability.

The addition of -y to auto-confirm the conda environment creation is appropriate for non-interactive test execution.

Note: The static analysis warning (S607) about partial executable path is a false positive in this test context where the command is hardcoded and controlled.

Comment thread src/snakemake/rules.py Outdated

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between adde7e6 and f1efc01.

📒 Files selected for processing (1)
  • src/snakemake/deployment/conda.py (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.py

⚙️ CodeRabbit configuration file

**/*.py: Do not try to improve formatting.
Do not suggest type annotations for functions that are defined inside of functions or methods.
Do not suggest type annotation of the self argument of methods.
Do not suggest type annotation of the cls argument of classmethods.
Do not suggest return type annotation if a function or method does not contain a return statement.

Files:

  • src/snakemake/deployment/conda.py
🧬 Code graph analysis (1)
src/snakemake/deployment/conda.py (1)
src/snakemake/common/__init__.py (1)
  • is_local_file (127-128)
🪛 GitHub Actions: CI
src/snakemake/deployment/conda.py

[error] 1022-1022: Conda environment spec path is not a directory: '/home/runner/work/snakemake/snakemake/.pixi/envs/py313/envs/test_issue3192'. The code asserts the path exists; environment not created, leading to AssertionError during CondaEnvSpecType.from_spec.

🪛 Ruff (0.13.2)
src/snakemake/deployment/conda.py

1021-1021: Do not assert False (python -O removes these calls), raise AssertionError()

Replace assert False

(B011)

Comment thread src/snakemake/deployment/conda.py Outdated
@Hocnonsense

Copy link
Copy Markdown
Contributor Author

Done! If conda install without channels selected, it will fail.

@johanneskoester johanneskoester merged commit 4249ff7 into main Oct 3, 2025
60 checks passed
@johanneskoester johanneskoester deleted the fix/empty-file branch October 3, 2025 15:58
@johanneskoester

Copy link
Copy Markdown
Contributor

Great work!

johanneskoester pushed a commit that referenced this pull request Oct 3, 2025
🤖 I have created a release *beep* *boop*
---


##
[9.11.9](v9.11.8...v9.11.9)
(2025-10-03)


### Bug Fixes

* Raise WorkflowError on empty file path in _IOFile.check
([#3769](#3769))
([4249ff7](4249ff7))
* remove id field in notebook cells created by nbformat, thereby
increasing compatibility with different jupyter versions
([#3767](#3767))
([46cf3ed](46cf3ed))
* show failed logs in generated unit tests
([#3771](#3771))
([61f4e9b](61f4e9b))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).
kjohnsen pushed a commit to kjohnsen/snakemake that referenced this pull request Dec 15, 2025
…ke#3769)

fix snakemake#341

Now the file with empty string will never pass the check.
Or should this be a warning instead of a WorkflowError?

### QC
<!-- Make sure that you can tick the boxes below. -->

* [ ] The PR contains a test case for the changes or the changes are
already covered by an existing test case.
* [ ] The documentation (`docs/`) is updated to reflect the changes or
this is not necessary (e.g. if the change does neither modify the
language nor the behavior or functionalities of Snakemake).


<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit

* **Bug Fixes**
* Added an early, clear error when an empty file path is provided,
preventing downstream confusion.

* **Tests**
* Updated a conda-related test to use the conda-forge channel and assert
successful execution.

* **Chores**
  * Removed unused imports to reduce overhead.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
kjohnsen pushed a commit to kjohnsen/snakemake that referenced this pull request Dec 15, 2025
🤖 I have created a release *beep* *boop*
---


##
[9.11.9](snakemake/snakemake@v9.11.8...v9.11.9)
(2025-10-03)


### Bug Fixes

* Raise WorkflowError on empty file path in _IOFile.check
([snakemake#3769](snakemake#3769))
([4249ff7](snakemake@4249ff7))
* remove id field in notebook cells created by nbformat, thereby
increasing compatibility with different jupyter versions
([snakemake#3767](snakemake#3767))
([46cf3ed](snakemake@46cf3ed))
* show failed logs in generated unit tests
([snakemake#3771](snakemake#3771))
([61f4e9b](snakemake@61f4e9b))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).
@Hocnonsense Hocnonsense self-assigned this Mar 18, 2026
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.

Cryptic error if the output is an empty string

2 participants