refactor: organize loot directory with subdirectories

This commit is contained in:
GH05TCREW
2025-12-11 07:02:43 -07:00
parent e1fd7c4f09
commit c022dc8047
6 changed files with 22 additions and 15 deletions

View File

@@ -21,7 +21,10 @@ The task is not complete until you explicitly call `finish`.
- OS: {{ environment.os }} ({{ environment.os_version }})
- Architecture: {{ environment.architecture }}
- Shell: {{ environment.shell }}
- Output: loot/
- Output directories:
- loot/notes.json (working notes)
- loot/reports/ (generated reports)
- loot/artifacts/ (screenshots, captured files)
{% endif %}
{% if target %}

View File

@@ -35,7 +35,7 @@ async def run_cli(
target: Target to test
model: LLM model to use
task: Optional task description
report: Report path ("auto" for loot/<target>_<timestamp>.md)
report: Report path ("auto" for loot/reports/<target>_<timestamp>.md)
max_tools: Max tool calls before stopping
use_docker: Run tools in Docker container
"""
@@ -253,11 +253,11 @@ async def run_cli(
# Determine path
if report == "auto":
loot_dir = Path("loot")
loot_dir.mkdir(exist_ok=True)
reports_dir = Path("loot/reports")
reports_dir.mkdir(parents=True, exist_ok=True)
safe_target = target.replace("://", "_").replace("/", "_").replace(":", "_")
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
report_path = loot_dir / f"{safe_target}_{timestamp}.md"
report_path = reports_dir / f"{safe_target}_{timestamp}.md"
else:
report_path = Path(report)
report_path.parent.mkdir(parents=True, exist_ok=True)

View File

@@ -75,13 +75,13 @@ Examples:
# Task for non-interactive mode
parser.add_argument("--task", help="Task to run in non-interactive mode")
# Report output (saves to loot/ by default)
# Report output (saves to loot/reports/ by default)
parser.add_argument(
"--report",
"-r",
nargs="?",
const="auto",
help="Generate report (default: loot/<target>_<timestamp>.md)",
help="Generate report (default: loot/reports/<target>_<timestamp>.md)",
)
# Max tool calls limit

View File

@@ -926,6 +926,7 @@ class GhostCrewTUI(App):
else:
lines.append(f"[{key}] {value}")
lines.append("\nFile: loot/notes.json")
lines.append("Reports: loot/reports/")
self._add_system("\n".join(lines))
@@ -1080,12 +1081,12 @@ Be concise. Use the actual data from notes."""
)
return
# Save to loot/
loot_dir = Path("loot")
loot_dir.mkdir(exist_ok=True)
# Save to loot/reports/
reports_dir = Path("loot/reports")
reports_dir.mkdir(parents=True, exist_ok=True)
timestamp = datetime.now().strftime("%Y-%m-%d_%H%M%S")
report_path = loot_dir / f"report_{timestamp}.md"
report_path = reports_dir / f"report_{timestamp}.md"
report_path.write_text(report_content, encoding="utf-8")
self._add_system(f"+ Report saved: {report_path}")

View File

@@ -174,8 +174,11 @@ class LocalRuntime(Runtime):
async def start(self):
"""Start the local runtime."""
self._running = True
# Create loot directory for scan output
# Create organized loot directory structure
Path("loot").mkdir(exist_ok=True)
Path("loot/reports").mkdir(exist_ok=True)
Path("loot/artifacts").mkdir(exist_ok=True)
Path("loot/artifacts/screenshots").mkdir(exist_ok=True)
async def stop(self):
"""Stop the local runtime gracefully."""
@@ -315,8 +318,8 @@ class LocalRuntime(Runtime):
kwargs["url"], timeout=timeout, wait_until="domcontentloaded"
)
# Save screenshot to loot directory
output_dir = Path("loot/screenshots")
# Save screenshot to loot/artifacts/screenshots/
output_dir = Path("loot/artifacts/screenshots")
output_dir.mkdir(parents=True, exist_ok=True)
filename = f"screenshot_{int(__import__('time').time())}.png"

View File

@@ -6,7 +6,7 @@ from typing import Dict
from ..registry import ToolSchema, register_tool
# Notes storage
# Notes storage - kept at loot root for easy access
_notes: Dict[str, str] = {}
_notes_file: Path = Path("loot/notes.json")