Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -568,6 +568,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

### Fixed

- When `cel-python` or `tree-sitter-language-pack` fails to import, the
error now gives the real cause. Both guards said "not installed" for any
import error, which was wrong for an installed package with a missing
dependency or a broken release (#573).
- Installs without the development dependencies work again (`uv tool install`
from a checkout, and any install from a built wheel). Two things broke
them: `tree-sitter-language-pack` 1.6.3, the newest release the old
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,15 +29,18 @@
from tree_sitter_language_pack import get_language, get_parser

TREE_SITTER_AVAILABLE = True
except ImportError: # pragma: no cover — dependency is required in pyproject.toml
except ImportError as _import_error: # pragma: no cover — dependency is required in pyproject.toml
TREE_SITTER_AVAILABLE = False
ts = None # type: ignore[assignment]
# Keep the real cause. A release that installs without an importable module
# (tree-sitter-language-pack 1.6.3, #573) is not "not installed".
_IMPORT_FAILURE = f"tree-sitter-language-pack could not be imported: {_import_error}"

def get_language(name: str) -> Any: # type: ignore[misc]
raise ImportError("tree-sitter-language-pack is not installed")
raise ImportError(_IMPORT_FAILURE)

def get_parser(name: str) -> Any: # type: ignore[misc]
raise ImportError("tree-sitter-language-pack is not installed")
raise ImportError(_IMPORT_FAILURE)


logger = logging.getLogger("darnit_baseline.threat_model.parsing")
Expand Down
6 changes: 3 additions & 3 deletions packages/darnit/src/darnit/sieve/cel_evaluator.py
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,7 @@ def _get_environment(self) -> Any:
from celpy.c7nlib import C7N_Interpreted_Runner
except ImportError as e:
raise CELCompilationError(
"cel-python not installed. Install with: pip install cel-python"
f"cel-python could not be imported: {e}"
) from e

# Create environment with C7N runner that supports custom functions
Expand Down Expand Up @@ -275,7 +275,7 @@ def compile(self, expression: str) -> CELProgram:
import celpy
except ImportError as e:
raise CELCompilationError(
"cel-python not installed. Install with: pip install cel-python"
f"cel-python could not be imported: {e}"
) from e

env = self._get_environment()
Expand Down Expand Up @@ -344,7 +344,7 @@ def _evaluate_with_timeout(
import celpy
except ImportError as e:
raise CELEvaluationError(
"cel-python not installed. Install with: pip install cel-python"
f"cel-python could not be imported: {e}"
) from e

result_container: list[Any] = []
Expand Down
27 changes: 27 additions & 0 deletions tests/darnit/sieve/test_cel_import_failure.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
"""An import failure inside cel-python reports its real cause, not "not installed"."""

from __future__ import annotations

import builtins

import pytest

from darnit.sieve.cel_evaluator import CELCompilationError, evaluate_cel


def test_cel_import_failure_names_the_real_cause(monkeypatch) -> None:
real_import = builtins.__import__

def failing_import(name, *args, **kwargs):
if name == "celpy" or name.startswith("celpy."):
raise ImportError("No module named 'packaging.version'")
return real_import(name, *args, **kwargs)

monkeypatch.setattr(builtins, "__import__", failing_import)

with pytest.raises(CELCompilationError) as excinfo:
evaluate_cel("1 == 1", {})

message = str(excinfo.value)
assert "packaging.version" in message
assert "not installed" not in message
Loading