-
Notifications
You must be signed in to change notification settings - Fork 7
fix: remove undeclared dotenv dependency from KG rebuild #637
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -309,3 +309,23 @@ def test_groq_rebuild_entity_payload_preserves_source_subtype(): | |
| assert entity.entity_type == "source" | ||
| assert entity.entity_subtype == "channel" | ||
| assert entity.start == 6 | ||
|
|
||
|
|
||
| def test_kg_rebuild_module_import_does_not_require_python_dotenv(monkeypatch): | ||
| import builtins | ||
| import importlib | ||
| import sys | ||
|
|
||
| real_import = builtins.__import__ | ||
|
|
||
| def import_without_dotenv(name, *args, **kwargs): | ||
| if name == "dotenv" or name.startswith("dotenv."): | ||
| raise ModuleNotFoundError("No module named 'dotenv'") | ||
| return real_import(name, *args, **kwargs) | ||
|
|
||
| monkeypatch.setattr(builtins, "__import__", import_without_dotenv) | ||
| sys.modules.pop("scripts.kg_rebuild", None) | ||
|
|
||
| module = importlib.import_module("scripts.kg_rebuild") | ||
|
Comment on lines
+327
to
+329
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🩺 Stability & Availability | 🟡 Minor | ⚡ Quick win 🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
echo "== files =="
git ls-files | rg '(^|/)tests/test_kg_rebuild\.py$|(^|/)scripts/kg_rebuild\.py$|(^|/)pytest|\.ini$|pyproject\.toml' || true
echo "== relevant test section =="
if [ -f tests/test_kg_rebuild.py ]; then
nl -ba tests/test_kg_rebuild.py | sed -n '280,360p'
fi
echo "== references to monkeypatch/sys.modules/import hook and scripts.kg_rebuild =="
rg -n "builtins\.__import__|sys\.modules\['scripts\.kg_rebuild'\]|sys\.modules\.pop|importlib\.import_module|scripts\.kg_rebuild|BRAINLAYER_BACKUP_LOG_PATH|pytest" tests/test_kg_rebuild.py | sed -n '1,220p'Repository: EtanHey/brainlayer Length of output: 298 🏁 Script executed: #!/bin/bash
set -euo pipefail
python3 - <<'PY'
import os, re
for path in ["tests/test_kg_rebuild.py", "scripts/kg_rebuild.py"]:
print(f"== {path} size/exists ==")
print(f"exists={os.path.exists(path)}")
if os.path.exists(path):
with open(path, encoding="utf-8") as f:
lines = f.read().splitlines()
print(f"lines={len(lines)}")
start=max(1,280) if path=="tests/test_kg_rebuild.py" else 1
end=min(len(lines),360) if path=="tests/test_kg_rebuild.py" else 170
for i in range(start,min(end+1,len(lines))+1):
print(f"{i:04d}\t{lines[i-1]}")
PY
echo "== focused references =="
rg -n "builtins\.__import__|sys\.modules\['scripts\.kg_rebuild'\]|sys\.modules\.pop|importlib\.import_module|scripts\.kg_rebuild|BRAINLAYER_BACKUP_LOG_PATH|pytest|monkeypatch" tests/test_kg_rebuild.py | head -n 220 || true
echo "== pytest config =="
for f in pyproject.toml pytest.ini; do
if [ -f "$f" ]; then
echo "--- $f ---"
sed -n '1,220p' "$f"
fi
doneRepository: EtanHey/brainlayer Length of output: 14148 🏁 Script executed: #!/bin/bash
set -euo pipefail
python3 - <<'PY'
import ast
from pathlib import Path
path = Path("tests/test_kg_rebuild.py")
src = path.read_text(encoding="utf-8")
tree = ast.parse(src)
for node in ast.walk(tree):
if isinstance(node, ast.ClassDef) or isinstance(node, ast.FunctionDef) or isinstance(node, ast.AsyncFunctionDef):
if "test_" in str(node.name):
print(f"Function {node.name} at lines {node.lineno}-{getattr(node, 'end_lineno', '?')}")
test = next(n for n in tree.body if isinstance(n, ast.FunctionDef) and n.name == "test_kg_rebuild_module_import_does_not_require_python_dotenv")
print("\nBody nodes:")
for n in test.body:
print(type(n).__name__, getattr(n, "lineno", "?"), getattr(n, "end_lineno", "?"), ast.unparse(n)[:260])
print("\nsys.modules.pop occurrences:")
for n in ast.walk(test):
if isinstance(n, ast.Call):
func = n.func
if isinstance(getattr(func, "value", None), ast.Attribute) and getattr(func, "attr", None) == "pop":
print(ast.unparse(n))
print("\nsys.modules.pop with cleanup occurrences:")
for n in ast.walk(test):
if isinstance(n, ast.Try):
for stmt in n.body:
print("try body first:", ast.unparse(stmt)[:240])
cleanup = []
for h in n.handlers:
for stmt in h.body:
cleanup.append(ast.unparse(stmt)[:240])
for stmt in n.finalbody:
cleanup.append(ast.unparse(stmt)[:240])
if any("sys.modules" in s or "builtins" in s for s in cleanup):
print("cleanup:")
for s in cleanup:
print(" " + s)
PYRepository: EtanHey/brainlayer Length of output: 2051 Restore
🤖 Prompt for AI Agents |
||
|
|
||
| assert callable(module.extracted_entity_from_groq_payload) | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When a developer keeps
BRAINLAYER_DBin the repo.env, removing this load makesmain()silently fall back to the canonical database viaget_db_path(). Running either rebuild tier then writes entities and relations to the live canonical DB instead of the configured sandbox/custom DB; replace the dotenv dependency with dependency-free loading that preserves the prior override, or require an explicit DB argument rather than silently changing targets.AGENTS.md reference: AGENTS.md:L5-L8
Useful? React with 👍 / 👎.