Back to skill

Security audit

Kitchen Compass

Security checks for vulnerabilities and agentic risk

Overview

Kitchen Compass is a local meal-planning skill that stores and updates household cooking data in a user-chosen data folder, with no evidence of hidden execution, exfiltration, or destructive behavior.

Install only if you are comfortable letting an agent read and write a local Kitchen Compass data folder containing household recipes, preferences, inventory, meal history, store notes, and generated planning/deal reports. Keep the data root private, review imported recipe links before saving them, and leave validation enabled during normal catalog builds.

Vulnerability Patterns
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
  • Unauthorized Access and Privilege EscalationObtains permissions beyond the task's legitimate needs
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
Findings (23)

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding
The supplied code is focused on a 'weekly deal brief' subsystem, not the declared core meal-planning functions. It reads/writes household store configuration, validates source and retrieval metadata, processes sale items with pricing/discount logic, infers display categories, and renders markdown reports for grocery deals. While this lives in the broader Kitchen Compass domain and uses household-specific data roots, it does not implement recipe conversion, dinner/side catalog querying, weekly dinner plan generation, or meal history recording as described. The actual primary purpose is materially different and introduces undeclared deal-tracking/reporting capabilities.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
The declared description focuses on meal-planning workspace functions: household data root setup, recipe conversion into a markdown contract, dinner-and-side catalog management, weekly dinner plan generation, and meal history recording. The supplied code instead implements a specific weekly deals pipeline: it resolves a Kitchen Compass data root, loads store configuration, reads per-store weekly deal brief JSON files, normalizes and combines them, writes generated combined deal sheet JSON/markdown files, and prints the result. While it operates within the Kitchen Compass data-root model, its primary purpose is weekly store-deal aggregation/rendering, which is not represented in the declared purpose. This is a material description-behavior mismatch.

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding
The code’s primary function is not meal-plan generation, recipe conversion, catalog querying, or meal-history recording. Instead, it renders a weekly deal brief based on store configuration and curated deal input. While it does use the Kitchen Compass data-root pattern consistent with the broader workspace, the actual capability is a separate deals-oriented workflow that is not represented in the declared description. This is a material purpose mismatch rather than a minor implementation detail.

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding
The declared description centers on meal-planning workspace operations such as household setup, recipe conversion, catalog building/querying, plan generation, and meal history recording. The actual code does none of those tasks. Instead, it is a test utility for ensuring consistency between documentation and code-level enum definitions. That is a materially different primary purpose and represents an undeclared capability focused on contract/documentation validation rather than Kitchen Compass workspace operation.

Tool Parameter Abuse

High
Category
Tool Misuse
Content
python3 scripts/build_recipe_query_index.py --data-root /path/to/kitchen-compass-data
```

The index builder validates every recipe against the frozen contract before writing the catalog and exits nonzero on any failure. Pass `--skip-validation` to bypass in a pinch; normal usage should leave it on.

### Query recipes
Confidence
87% confidence
Finding
Documenting a `--skip-validation` flag creates an easy path to bypass integrity checks before catalog generation. In this skill’s context, validation is the main guard preserving the recipe contract; bypassing it can let malformed or adversarial recipe content flow into downstream planning, rendering, or automation steps and undermine trust in generated outputs.

Tool Parameter Abuse

High
Category
Tool Misuse
Content
def parse_args() -> argparse.Namespace:
    parser = argparse.ArgumentParser(description="Build the portable Kitchen Compass dinner + side query catalog.")
    parser.add_argument("--data-root", help="Household data root. Defaults to ./kitchen-compass-data, except when run from the installed skill root it defaults to ../kitchen-compass-data so household data stays outside the skill.")
    parser.add_argument("--skip-validation", action="store_true", help="Skip the pre-build validation pass. Power-user escape hatch; normal usage should leave this off.")
    parser.add_argument("--verbose", action="store_true", help="Print the resolved data root to stderr.")
    return parser.parse_args()
Confidence
80% confidence
Finding
Tool parameters are crafted to achieve unintended or unsafe behavior. Parameter abuse can bypass intended safety checks (e.g. shell=True, --force, dangerous glob patterns).

Tool Parameter Abuse

High
Category
Tool Misuse
Content
def parse_args() -> argparse.Namespace:
    parser = argparse.ArgumentParser(description="Build the portable Kitchen Compass dinner + side query catalog.")
    parser.add_argument("--data-root", help="Household data root. Defaults to ./kitchen-compass-data, except when run from the installed skill root it defaults to ../kitchen-compass-data so household data stays outside the skill.")
    parser.add_argument("--skip-validation", action="store_true", help="Skip the pre-build validation pass. Power-user escape hatch; normal usage should leave this off.")
    parser.add_argument("--verbose", action="store_true", help="Print the resolved data root to stderr.")
    return parser.parse_args()
Confidence
80% confidence
Finding
Tool parameters are crafted to achieve unintended or unsafe behavior. Parameter abuse can bypass intended safety checks (e.g. shell=True, --force, dangerous glob patterns).

Tool Parameter Abuse

High
Category
Tool Misuse
Content
def parse_args() -> argparse.Namespace:
    parser = argparse.ArgumentParser(description="Build the portable Kitchen Compass dinner + side query catalog.")
    parser.add_argument("--data-root", help="Household data root. Defaults to ./kitchen-compass-data, except when run from the installed skill root it defaults to ../kitchen-compass-data so household data stays outside the skill.")
    parser.add_argument("--skip-validation", action="store_true", help="Skip the pre-build validation pass. Power-user escape hatch; normal usage should leave this off.")
    parser.add_argument("--verbose", action="store_true", help="Print the resolved data root to stderr.")
    return parser.parse_args()
Confidence
80% confidence
Finding
Tool parameters are crafted to achieve unintended or unsafe behavior. Parameter abuse can bypass intended safety checks (e.g. shell=True, --force, dangerous glob patterns).

Lp3

Medium
Category
MCP Least Privilege
Confidence
89% confidence
Finding
The skill instructs use of shell commands and file/env interactions but declares no explicit tool scope or allowed-tools boundary. In an agent setting, this broadens the effective authority of the skill and makes it easier for later prompt injection, operator error, or unsafe orchestration to invoke filesystem or shell actions without clear least-privilege constraints.

Unsafe Defaults

Medium
Category
Tool Misuse
Content
2. Fill in `household/profile.json`, `household/preferences.json`, and `household/stores.json`.
3. Add recipe markdown files under `recipes/` using `_recipe-template.md` or `assets/recipe-template.md`.
4. Validate recipes with `python3 scripts/validate_recipes.py --data-root <path>`.
5. Rebuild the catalog with `python3 scripts/build_recipe_query_index.py --data-root <path>`. The builder runs the same validation by default and exits nonzero on any failure; pass `--skip-validation` only as an escape hatch.
6. Optionally add remembered inventory with `python3 scripts/manage_inventory.py --data-root <path> ...`.
7. Query recipes or build plans.
8. Optionally opt into manual weekly deal briefs with `python3 scripts/manage_deal_sources.py --data-root <path> ...`, then curate `deals/weekly-deal-brief-input.json` and render it with `python3 scripts/render_weekly_deal_brief.py --data-root <path>`.
Confidence
80% confidence
Finding
Tool defaults are unsafe or overly permissive (e.g. disabled TLS verification, no authentication, world-writable permissions). Unsafe defaults widen the attack surface.

Unsafe Defaults

Medium
Category
Tool Misuse
Content
2. Fill in `household/profile.json`, `household/preferences.json`, and `household/stores.json`.
3. Add recipe markdown files under `recipes/` using `_recipe-template.md` or `assets/recipe-template.md`.
4. Validate recipes with `python3 scripts/validate_recipes.py --data-root <path>`.
5. Rebuild the catalog with `python3 scripts/build_recipe_query_index.py --data-root <path>`. The builder runs the same validation by default and exits nonzero on any failure; pass `--skip-validation` only as an escape hatch.
6. Optionally add remembered inventory with `python3 scripts/manage_inventory.py --data-root <path> ...`.
7. Query recipes or build plans.
8. Optionally opt into manual weekly deal briefs with `python3 scripts/manage_deal_sources.py --data-root <path> ...`, then curate `deals/weekly-deal-brief-input.json` and render it with `python3 scripts/render_weekly_deal_brief.py --data-root <path>`.
Confidence
80% confidence
Finding
Tool defaults are unsafe or overly permissive (e.g. disabled TLS verification, no authentication, world-writable permissions). Unsafe defaults widen the attack surface.

Unsafe Defaults

Medium
Category
Tool Misuse
Content
2. Fill in `household/profile.json`, `household/preferences.json`, and `household/stores.json`.
3. Add recipe markdown files under `recipes/` using `_recipe-template.md` or `assets/recipe-template.md`.
4. Validate recipes with `python3 scripts/validate_recipes.py --data-root <path>`.
5. Rebuild the catalog with `python3 scripts/build_recipe_query_index.py --data-root <path>`. The builder runs the same validation by default and exits nonzero on any failure; pass `--skip-validation` only as an escape hatch.
6. Optionally add remembered inventory with `python3 scripts/manage_inventory.py --data-root <path> ...`.
7. Query recipes or build plans.
8. Optionally opt into manual weekly deal briefs with `python3 scripts/manage_deal_sources.py --data-root <path> ...`, then curate `deals/weekly-deal-brief-input.json` and render it with `python3 scripts/render_weekly_deal_brief.py --data-root <path>`.
Confidence
80% confidence
Finding
Tool defaults are unsafe or overly permissive (e.g. disabled TLS verification, no authentication, world-writable permissions). Unsafe defaults widen the attack surface.

Unsafe Defaults

Medium
Category
Tool Misuse
Content
2. Fill in `household/profile.json`, `household/preferences.json`, and `household/stores.json`.
3. Add recipe markdown files under `recipes/` using `_recipe-template.md` or `assets/recipe-template.md`.
4. Validate recipes with `python3 scripts/validate_recipes.py --data-root <path>`.
5. Rebuild the catalog with `python3 scripts/build_recipe_query_index.py --data-root <path>`. The builder runs the same validation by default and exits nonzero on any failure; pass `--skip-validation` only as an escape hatch.
6. Optionally add remembered inventory with `python3 scripts/manage_inventory.py --data-root <path> ...`.
7. Query recipes or build plans.
8. Optionally opt into manual weekly deal briefs with `python3 scripts/manage_deal_sources.py --data-root <path> ...`, then curate `deals/weekly-deal-brief-input.json` and render it with `python3 scripts/render_weekly_deal_brief.py --data-root <path>`.
Confidence
80% confidence
Finding
Tool defaults are unsafe or overly permissive (e.g. disabled TLS verification, no authentication, world-writable permissions). Unsafe defaults widen the attack surface.

Missing User Warnings

Medium
Confidence
94% confidence
Finding
The script loads household-specific configuration files and embeds them directly into the generated `recipe-catalog.json` payload. That can expose private household profile, preference, or store data to other tools, users, or sync/export flows consuming generated artifacts, especially because this code provides no minimization, consent, or warning at write time.

Unsafe Defaults

Medium
Category
Tool Misuse
Content
raise SystemExit(f"Missing recipes directory: {paths.recipes_dir}")

    recipe_paths = sorted(path for path in paths.recipes_dir.glob("*.md") if not path.name.startswith("_"))
    if not args.skip_validation:
        failures = validate_recipe_paths(recipe_paths)
        if failures:
            for recipe_path, errors in failures:
Confidence
80% confidence
Finding
Tool defaults are unsafe or overly permissive (e.g. disabled TLS verification, no authentication, world-writable permissions). Unsafe defaults widen the attack surface.

Dynamic import via __import__()

Medium
Category
Dangerous Code Execution
Content
print(
            f"[kitchen-compass] duplicate history event ({event['date']}, {event['recipe_slug']}, "
            f"{event['meal_slot']}, {event['event_type']}); skipping. Pass --allow-duplicate or --replace to override.",
            file=__import__('sys').stderr,
        )
        return
Confidence
75% confidence
Finding
Dynamic __import__() can load arbitrary modules at runtime, bypassing static analysis and potentially importing malicious code.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
def _run(cmd, env=None):
    return subprocess.run(cmd, cwd=REPO_ROOT, env=env, capture_output=True, text=True, check=True)


@pytest.fixture
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
def run_cmd():
    def _invoke(script, *args, env=None, check=True):
        cmd = [sys.executable, str(SCRIPTS_DIR / script), *args]
        return subprocess.run(cmd, cwd=REPO_ROOT, env=env, capture_output=True, text=True, check=check)
    return _invoke
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

Missing User Warnings

Low
Confidence
82% confidence
Finding
The README explicitly encourages users to provide external recipe links and describes persistent storage of recipes, history, and inventory on the local filesystem, but it does not warn that linked pages may contain tracking content or that extracted data and household history will be retained. In an agent setting, that omission can lead users to expose household preferences, meal history, or other sensitive lifestyle data without understanding the privacy implications.

Unverifiable Dependency: setuptools has 10 known advisory(ies) (CVE-2013-1633 (Setuptools vulnerable to Man-in-the-middle attacks); CVE-2025-47273 (setuptools has a path traversal vulnerability in PackageIndex.download that lead); CVE-2024-6345 (setuptools vulnerable to Command Injection via package URL) +7 more), but the manifest does not pin a version, so it is unknown whether the installed release is affected

Low
Category
Supply Chain
Confidence
40% confidence
Finding
Dependency has known vulnerabilities (CVEs). Using packages with unpatched security flaws exposes the environment to known exploits.

Unverifiable Dependency: pytest has 2 known advisory(ies) (CVE-2025-71176 (pytest has vulnerable tmpdir handling); CVE-2025-71176 (pytest has vulnerable tmpdir handling)), but the manifest does not pin a version, so it is unknown whether the installed release is affected

Low
Category
Supply Chain
Confidence
40% confidence
Finding
Dependency has known vulnerabilities (CVEs). Using packages with unpatched security flaws exposes the environment to known exploits.

Missing User Warnings

Low
Confidence
79% confidence
Finding
This code performs file writes to stores.json and weekly deal input files via write_atomic, which can modify persisted user data. In this file there is no confirmation prompt, print/log disclosure, or comment/docstring warning users that these operations will overwrite saved configuration or deal data.

Missing User Warnings

Low
Confidence
75% confidence
Finding
This script creates or overwrites per-store brief stub files and generated scan packet files, but the normal execution path does not explicitly tell the user that local files will be written. Although the CLI flags and function names imply preparation/output behavior, there is no direct runtime disclosure around these writes except in quiet mode's summary message.

Static analysis

No suspicious patterns detected.