Back to skill

Security audit

Jasper Recall

Security checks for vulnerabilities and agentic risk

Overview

This skill is a memory-search tool with a coherent purpose, but it has serious review-worthy risks around private memory exposure, automatic context injection, and unsafe command execution paths.

Install only after reviewing the privacy and command-execution risks. Avoid exposing the HTTP server, do not use unpinned npx setup in privileged environments, assume indexed memories and recall queries may be sent to SkillBoss API Hub, and disable autoRecall or sandbox learning writes unless you have a clear trust and review process.

Vulnerability Patterns
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
Findings (5)

T09 · Insecure Skill Coding Practices

Error
Location
scripts/index-digests.py:31
Finding

Private Agent Memory Is Transmitted to an External Embedding Service

Content
View full analysis
list: """Get text embedding via SkillBoss API Hub.""" r = requests.post( f"{API_BASE}/pilot", headers={"Authorization": f"Bearer {SKILLBOSS_API_KEY}", "Content-Type": "application/json"}, json={"type": "embedding", "inputs": {"text": text}}, timeout=60, ) return r.json()["result"]["data"][0]["embedding"] ``` ```python # Generate embeddings via SkillBoss API Hub embeddings = get_embeddings_batch(chunks) ``` ```python # Daily notes and other memory files (but not subdirs) files_to_index.extend(glob.glob(os.path.join(MEMORY_DIR, "*.md"))) # Repos documentation repos_dir = os.path.join(MEMORY_DIR, "repos") if os.path.exists(repos_dir): files_to_index.extend(glob.glob(os.path.join(repos_dir, "*.md"))) # Founder Logs for logs_dir_name in ["founder-logs", "founderLogs"]: logs_dir = os.path.join(MEMORY_DIR, logs_dir_name) if os.path.exists(logs_dir): files_to_index.extend(glob.glob(os.path.join(logs_dir, "*.md"))) # SOPs sops_dir = os.path.join(MEMORY_DIR, "sops") if os.path.exists(sops_dir): files_to_index.extend(glob.glob(os.path.join(sops_dir, "*.md"))) for filepath in files_to_index: try: with open(filepath, 'r', encoding='utf-8') as f: content = f.read() ``` The same data flow applies to recall queries: ```python SKILLBOSS_API_KEY = os.environ["SKILLBOSS_API_KEY"] API_BASE = "https://api.heybossai.com/v1" def get_embedding(text: str) -> list: r = requests.post( f"{API_BASE}/pilot", headers={"Authoriza ...[truncated 2825 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
cli/server.js:21
Finding

Shell Command Injection Through Recall Queries

Content
View full analysis
`"${a}"`).join(' ')}`, { encoding: 'utf8' }); ``` ### Technical Analysis `child_process.execSync()` executes a command through a shell. The query is attacker-controlled and is interpolated into the command string. Escaping only double-quote characters does not neutralize shell command substitutions such as `$(command)` or backtick expressions, which are evaluated even when they appear inside double quotes. The server exposes the vulnerable path through the unauthenticated `GET /recall` endpoint. Its default loopback bindi ...[truncated 1836 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
scripts/index-digests.py:86
Finding

Public-Only Recall Can Expose Complete Private Memory Files

Content
View full analysis
str: """ Determine which collection a file belongs to based on path and content. Returns: 'private', 'shared', or 'learnings' """ rel_lower = rel_path.lower() content_lower = content.lower() # Agent learnings: moltbook insights, agent collaboration notes if any(x in rel_lower for x in ['moltbook/', 'learnings/', 'agent-insights/']): return 'learnings' if '[learning]' in content_lower or '[insight]' in content_lower: return 'learnings' # Shared: explicit shared folder or [public] tag if 'shared/' in rel_lower: return 'shared' if '[public]' in content_lower: return 'shared' # Default: private return 'private' ``` ```python # Also maintain legacy collection for backwards compatibility legacy_collection = client.get_or_create_collection( name="jasper_memory", metadata={"description": "Legacy collection - use specific collections instead"} ) ``` ```python # Determine target collection coll_key = determine_collection(rel_path, content) collection = collections[coll_key] # Index to the appropriate collection indexed = index_to_collection( collection, filepath, rel_path, content, file_hash, stats[coll_key] ) # Also index to legacy collection for backwards compatibility index_to_collection( legacy_collection, filepath, rel_path, content, file_hash, stats["legacy"] ) ``` The public-only search path can fall back to the unrestricted legacy collection: ```python if args.public_only: if args.collection: if args.collection not in ["shared", "learnings"]: print(f"❌ --public-only restricts to 'sha ...[truncated 2580 chars]
Remediation
View remediation

T02 · Agent Memory Poisoning

Error
Location
scripts/write-learning.py:53
Finding

Sandboxed Agents Can Persist Memory That Is Automatically Injected Into Future Agent Sessions

Content
View full analysis
r.score >= minScore); ... const memoryContext = relevant .map((r: any) => `- [${r.source || 'memory'}] ${r.content.slice(0, 500)}${r.content.length > 500 ? '...' : ''}`) .join('\n'); return { prependContext: `\nThe following memories may be relevant to this conversation:\n${memoryContext}\n`, }; ``` Setup enables automatic recall without setting public-only mode: ```javascript config.plugins.entries['jasper-recall'] = { enabled: true, config: { autoRecall: true, minScore: 0.3, defaultLimit: 5 } }; ``` ### Technical Analysis The `write-learning.py` uti ...[truncated 2458 chars]
Remediation
View remediation

T08 · Insecure Dependencies

Warning
Location
cli/jasper-recall.js:142
Finding

Setup Installs Unpinned Python Dependencies From a Mutable Package Source

Content
View full analysis
Remediation
View remediation
Vulnerability Patterns
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
  • Rogue AgentSelf-Modification, Session Persistence
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Taint TrackingDirect Taint Flow, Variable-Mediated Taint Flow, Credential Exfiltration Chain
Findings (91)

Tainted flow: 'SKILLBOSS_API_KEY' from os.environ (line 31, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/index-digests.py (reported line 37)May include surrounding context.

python
def get_embedding(text: str) -> list:
    """Get text embedding via SkillBoss API Hub."""
    r = requests.post(
        f"{API_BASE}/pilot",
        headers={"Authorization": f"Bearer {SKILLBOSS_API_KEY}", "Content-Type": "application/json"},
        json={"type": "embedding", "inputs": {"text": text}},

Tainted flow: 'SKILLBOSS_API_KEY' from os.environ (line 23, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/recall.py (reported line 29)May include surrounding context.

python
def get_embedding(text: str) -> list:
    """Get text embedding via SkillBoss API Hub."""
    r = requests.post(
        f"{API_BASE}/pilot",
        headers={"Authorization": f"Bearer {SKILLBOSS_API_KEY}", "Content-Type": "application/json"},
        json={"type": "embedding", "inputs": {"text": text}},

Tool Parameter Abuse

High
Category
Tool Misuse
Confidence
90% 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).

Content

Scanner excerpt · SKILL.md (reported line 425)May include surrounding context.

"Collection not found"

bash
rm -rf ~/.openclaw/chroma-db  # Clear and rebuild
index-digests

Tool Parameter Abuse

High
Category
Tool Misuse
Confidence
90% 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).

Content

Scanner excerpt · SKILL.md (reported line 425)May include surrounding context.

"Collection not found"

bash
rm -rf ~/.openclaw/chroma-db  # Clear and rebuild
index-digests

Rp1

Medium
Category
MCP Rug Pull
Confidence
95% confidence
Finding

The changelog instructs users to run npx jasper-recall serve --port 3458 without pinning an exact package version. npx will resolve and execute the latest published package by default, which can lead to unintended code execution if a malicious or compromised update is published or if behavior changes unexpectedly.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
94% confidence
Finding

The changelog references npx jasper-recall setup without a pinned version, causing execution of whatever version is current in the registry at runtime. In an agent or automation context, this increases supply-chain risk because a compromised package update could be executed immediately by users following the docs.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
94% confidence
Finding

The documented npx jasper-recall update command is unpinned, so the command itself may fetch and run an unreviewed package version before performing any update logic. This is especially risky because an 'update' workflow conditions users to trust remote code changes, amplifying the impact of a malicious publication or account compromise.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
93% confidence
Finding

The changelog suggests npx jasper-recall config without version pinning, which means users may execute an unexpected future release rather than the version documented in the changelog. Even though this is a configuration command, it still launches package code and therefore carries the same supply-chain execution risk.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
95% confidence
Finding

The documentation instructs users to execute npx jasper-recall setup without pinning a specific package version. That allows the fetched package to change over time or be replaced through supply-chain compromise, causing arbitrary code execution during installation in the user's environment.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The 'Why Python?' section states there are Node.js equivalents that work 'fully offline' and that the one-time download 'runs entirely locally,' which implies no external service dependency. However, the manifest description and embedding section explicitly state embeddings are obtained via SkillBoss API Hub and require SKILLBOSS_API_KEY, so the documentation contradicts the actual described behavior.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
90% confidence
Finding

The skill explicitly persists session content by converting session logs into searchable digests and indexing them into a memory system. In an agent environment, this increases the risk of retaining secrets, credentials, sensitive prompts, and personal data beyond their original context, especially when later searchable or shareable across agents.

Content

Scanner excerpt · SKILL.md (reported line 77)May include surrounding context.

index-digests # Index memory files into ChromaDB

text

**Create session digests:**
```bash
digest-sessions          # Process new sessions
digest-sessions --dry-run  # Preview what would be processed

Rp1

Medium
Category
MCP Rug Pull
Confidence
95% confidence
Finding

The npx jasper-recall moltbook-setup example downloads and runs the latest published package rather than a fixed version. In a skill intended to configure agent memory access, this creates meaningful supply-chain risk because a malicious or altered package could install wrappers, change access controls, or execute arbitrary setup logic.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
95% confidence
Finding

The verification step npx jasper-recall moltbook-verify is also unpinned, so even a command framed as validation may execute changed remote code. While the operation sounds lower risk than setup, it still grants arbitrary package code execution at runtime.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
94% confidence
Finding

The server startup example npx jasper-recall serve runs code obtained at execution time from npm without version pinning. Because this starts a network-facing service for memory retrieval, a compromised or changed package could expose data, weaken defaults, or embed backdoors.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
60% confidence
Finding

Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Content

Scanner excerpt · SKILL.md (reported line 420)May include surrounding context.

"No index found"

bash
index-digests  # Create the index first

"Collection not found"

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

In --fix mode, the script automatically runs package installation commands (for example pip install chromadb and sentence-transformers), which can trigger network access and modify the local Python environment without a sufficiently explicit warning at the point of action. This is dangerous because a user may treat a 'doctor' command as diagnostic-only, while it actually performs system changes and downloads third-party code, increasing supply-chain and unexpected-change risk.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
82% confidence
Finding

The --fix path automatically invokes indexing via node index-digests.js when collections are missing, but the warning text does not clearly explain that indexing may read and process user memory/workspace data. This can surprise users by causing unintended processing of potentially sensitive local content under the guise of automated repair.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
60% confidence
Finding

Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Content

Scanner excerpt · cli/jasper-recall.js (reported line 7)May include surrounding context.

js
* Local RAG system for AI agent memory
 * 
 * Usage:
 *   npx jasper-recall setup     # Install dependencies and create scripts
 *   npx jasper-recall recall    # Run a query (alias)
 *   npx jasper-recall index     # Index files (alias)
 *   npx jasper-recall digest    # Digest sessions (alias)

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Rp1

Medium
Category
MCP Rug Pull
Confidence
70% confidence
Finding

npx commands without a version suffix (e.g. @1.0.0) create a rug-pull risk if the upstream server is compromised and publishes a malicious update.

Content

No source excerpt is available for this finding.

Static analysis

Detected: suspicious.dangerous_exec, suspicious.destructive_delete_command

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
cli/doctor.js:15

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
cli/jasper-recall.js:43

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
cli/server.js:33

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
extensions/jasper-recall/index.ts:58

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
extensions/openclaw-plugin/index.ts:58

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
src/index.js:28

Documentation contains a destructive delete command without an explicit confirmation gate.

Warn
Code
suspicious.destructive_delete_command
Location
SKILL.md:425