Back to skill

Security audit

Meili Memory Skill

Security checks for vulnerabilities and agentic risk

Overview

This skill has a coherent memory-search purpose, but its installer and configuration create high-impact local security risks that need review before use.

Review this skill before installing. It may be useful for local memory search, but the current installer asks for broad system authority, creates persistent background jobs, exposes the search master key, and can send private memory to any configured MEILI_HOST. Prefer a version that uses a verified MeiliSearch package, a user-level service, explicit opt-in for cron, strict localhost validation, and non-executing .env parsing.

Vulnerability Patterns
  • 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
  • Unauthorized Access and Privilege EscalationObtains permissions beyond the task's legitimate needs
  • 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
Findings (6)

T03 · Remote Payload Retrieval and Execution

Error
Location
install.sh:7
Finding

Unverified Remote Script Retrieval and Execution

Content
View full analysis
/dev/null; then echo "Installing MeiliSearch..." curl -L https://install.meilisearch.com | sh sudo mv ./meilisearch /usr/local/bin/ else echo "MeiliSearch already installed: $(meilisearch --version)" fi ``` ### Technical Analysis The installer pipes a network response directly into `sh`. The retrieved content is not pinned to a release, inspected, signature-verified, or validated against a cryptographic checksum. Consequently, the code executed during installation can change after the Skill package has been reviewed. The `-L` option also follows redirects without restricting the final destination. The remote script controls the resulting `./meilisearch` file, which is subsequently moved into `/usr/local/bin` with elevated privileges. ### Attack Path 1. An attacker compromises the installation endpoint, its delivery infrastructure, or a redirected destination. 2. The user runs `install.sh`. 3. `curl` retrieves attacker-controlled shell commands. 4. The response is immediately executed by `sh` under the installing user's account. 5. The payload creates or replaces `./meilisearch`. 6. The attacker-controlled binary is moved to `/usr/local/bin` using `sudo`. 7. The installer later starts that binary through a persistent system service. ### Impact Assessment An attacker can execute arbitrary commands with the installing user's privileges and can influence the binary installed into a privileged system path. In conjunction with the systemd configuration created later by the installer, the attacker-controlled binary may run persistently as root at startup. ]]>
Remediation
View remediation

T05 · Unauthorized Access and Privilege Escalation

Error
Location
install.sh:24
Finding

Root-Level System Service and Automatic Scheduled Persistence

Content
View full analysis
/tmp/meilisearch.service << EOF [Unit] Description=MeiliSearch After=network.target [Service] Type=simple ExecStart=/usr/local/bin/meilisearch --http-addr 127.0.0.1:7700 --master-key ${MASTER_KEY} --db-path /var/lib/meilisearch/data.ms Restart=always RestartSec=5 [Install] WantedBy=multi-user.target EOF sudo cp /tmp/meilisearch.service /etc/systemd/system/meilisearch.service sudo systemctl daemon-reload sudo systemctl enable meilisearch sudo systemctl start meilisearch ``` ```bash # 7. Set up cron for hourly indexing (crontab -l 2>/dev/null | grep -v "meili-memory"; echo "0 * * * * cd ${SKILL_DIR} && bash scripts/indexer.sh >> /tmp/meili-indexer.log 2>&1") | crontab - ``` ### Technical Analysis The installer establishes two cross-session persistence mechanisms: 1. A systemd service enabled at system startup. 2. An hourly cron task that executes the installed indexer. The service does not specify a `User=` or `Group=` directive. A service installed under `/etc/systemd/system` therefore runs as root by default. Root privileges are not required for a localhost-only search database whose files could be stored under a dedicated unprivileged account or the user's workspace. `Restart=always` causes the process to be restarted indefinitely. Because the service executes the binary retrieved through the unverified remote installation path, the persistence and privilege issues amplify the remote execution risk. The cron task also executes mutable scripts from the user's workspace every hour. Any party able to modify those scripts or their sourced configuration can obtain repeated code execution under the cron owner's account. ### Attack Path 1. The user runs the installer and grants `sudo` access. 2. The installer c ...[truncated 798 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
install.sh:15
Finding

MeiliSearch Master Key Exposed in Output, Service Configuration, and Process Arguments

Content
View full analysis
/tmp/meilisearch.service << EOF [Unit] Description=MeiliSearch After=network.target [Service] Type=simple ExecStart=/usr/local/bin/meilisearch --http-addr 127.0.0.1:7700 --master-key ${MASTER_KEY} --db-path /var/lib/meilisearch/data.ms Restart=always RestartSec=5 [Install] WantedBy=multi-user.target EOF ``` ```bash echo "" echo "=== Installation complete ===" echo "MeiliSearch: http://127.0.0.1:7700" echo "Skill dir: ${SKILL_DIR}" echo "Master key: ${MASTER_KEY}" ``` ### Technical Analysis The generated master key is exposed through multiple channels: - Printed immediately after generation. - Printed again at installation completion. - Embedded directly in the systemd unit's `ExecStart` command. - Exposed as a command-line argument while the service is running. - Initially written through a predictable shared temporary path, `/tmp/meilisearch.service`. This behavior conflicts with the documentation's security claim that the key is loaded from the workspace `.env` file and is never hardcoded in scripts. Although the generated value is not committed in the package, the installed system configuration contains the plaintext secret. ### Attack Path 1. The installer generates the master key. 2. Terminal capture, CI logs, shell-session recording, or installation logs retain the printed value. 3. Alternatively, a local user reads the installed unit or process command line where permissions permit. 4. The recovered master key is used to authenticate to MeiliSearch. 5. The attacker searches, changes, deletes, or adds indexed memory documents. ### Impact Assessment Exposure of the master key grants administrative a ...[truncated 283 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
lib/config.sh:11
Finding

Workspace Environment File Is Executed as Arbitrary Shell Code

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
lib/config.sh:19
Finding

Unvalidated MeiliSearch Host Can Redirect Credentials and Private Memory

Content
View full analysis
&2 exit 1 fi export MEILI_HOST MEILI_KEY ``` ```python subprocess.run([ "curl", "-s", "-X", "POST", f"{ms_host}/indexes/{tier}/documents", "-H", f"Authorization: Bearer {ms_key}", "-H", "Content-Type: application/json", "-d", f"@{batch_file}" ], capture_output=True, text=True) ``` ```python result = subprocess.run([ "curl", "-s", f"{ms_host}/indexes/{tier}/search", "-H", f"Authorization: Bearer {ms_key}", "-H", "Content-Type: application/json", "-d", f"@{query_file}" ], capture_output=True, text=True) ``` ### Technical Analysis The Skill is documented as a local, self-hosted search facility, but `MEILI_HOST` is accepted without validating its scheme, hostname, address, or port. The indexer sends batches containing sections from `MEMORY.md` and daily memory notes to this endpoint. The search script sends private search queries to the same destination. Both requests include the master key in an `Authorization` header. This does not prove that the package intentionally exfiltrates data because the default is localhost. However, compromise of the environment or `.env` file creates a direct outbound disclosure channel. ### Attack Path 1. An attacker modifies the process environment or `${WORKSPACE}/.env`. 2. `MEILI_HOST` is set to an attacker-controlled HTTP or HTTPS server. 3. The hourly indexer executes and processes `MEMORY.md` and `memory/*.md`. 4. Document batches and the bearer key are sent to the attacker-control ...[truncated 458 chars]
Remediation
View remediation
`, `http://localhost:`, or a protected Unix socket. - Resolve and validate hostnames to prevent alternate-address bypasses if hostnames are permitted. - Reject embedded credentials, unexpected schemes, redirects, and non-approved ports. - Configure curl with `--fail-with-body`, timeout limits, and redirect restrictions. - If remote operation is intentionally supported, require HTTPS with certificate verification and explicit endpoint allowlisting. - Use separate least-privileged keys for searching and indexing rather than transmitting a master key. - Warn and require explicit confirmation before sending memory to any non-local endpoint. ]]>

T02 · Agent Memory Poisoning

Error
Location
scripts/distill.sh:145
Finding

Heuristic Distillation Can Persist Attacker-Controlled Instructions into Long-Term Memory

Content
View full analysis
Remediation
View remediation
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
Findings (36)

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding

The skill also performs distillation by scanning notes, extracting facts, modifying MEMORY.md, and triggering re-indexing, which goes well beyond the declared search-only purpose. In a memory-recall context this is particularly sensitive because it transforms and rewrites personal knowledge stores, creating integrity and privacy risks if the behavior is not clearly declared and tightly scoped.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding

The skill also performs distillation by scanning notes, extracting facts, modifying MEMORY.md, and triggering re-indexing, which goes well beyond the declared search-only purpose. In a memory-recall context this is particularly sensitive because it transforms and rewrites personal knowledge stores, creating integrity and privacy risks if the behavior is not clearly declared and tightly scoped.

Content

No source excerpt is available for this finding.

Context-Inappropriate Capability

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The script fetches code from the network and executes it directly with a shell pipeline. This is dangerous because any compromise of the remote endpoint, TLS trust chain, or downloaded script immediately becomes arbitrary code execution on the host during installation.

Content

No source excerpt is available for this finding.

External Script Fetching

High
Category
Supply Chain
Confidence
99% confidence
Finding

Fetching and executing an external script in one step is a classic supply-chain and remote-code-execution risk. The installer fully trusts code outside the repository and outside the user's control, so compromise of that external resource compromises the host.

Content

Scanner excerpt · install.sh (reported line 9)May include surrounding context.

sh
# 1. Install MeiliSearch binary
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"

Missing User Warnings

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

Executing a curl-piped shell command without any confirmation or integrity verification gives remote content direct execution privileges immediately. This removes any opportunity for user review and makes compromise of the download source equivalent to host compromise.

Content

No source excerpt is available for this finding.

Chaining Abuse

High
Category
Tool Misuse
Confidence
98% confidence
Finding

The pipe into sh creates an immediate execution chain from network content to the local shell. This pattern is dangerous because it bypasses inspection and compounds the risk of malicious or tampered remote content into instant arbitrary command execution.

Content

Scanner excerpt · install.sh (reported line 9)May include surrounding context.

sh
# 1. Install MeiliSearch binary
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"

Context-Inappropriate Capability

High
Category
Not specified by scanner
Confidence
92% confidence
Finding

The installer modifies privileged system configuration by writing into /etc/systemd/system, creating directories under /var/lib, and enabling a boot-persistent service. These actions materially increase the blast radius of any installer bug or supply-chain issue and exceed a minimal local-skill trust boundary.

Content

No source excerpt is available for this finding.

Missing User Warnings

High
Category
Not specified by scanner
Confidence
91% confidence
Finding

The installer performs privileged writes and enables a persistent service without warning the user about the scope of changes. Silent privilege use and persistence are dangerous because they reduce informed consent and can leave long-running components active beyond the user's expectations.

Content

No source excerpt is available for this finding.

YARA rule 'backdoor_persistence': Backdoor persistence with malicious payloads (shell commands, SSH key injection, hidden root users) [malware]

High
Category
YARA Match
Confidence
75% confidence
Finding

YARA rule matched a known malware signature (reverse shell, backdoor, ransomware, C2 framework, or info stealer).

Content

Scanner excerpt · install.sh (reported line 66)May include surrounding context.

sh
"${SKILL_DIR}/scripts/"*.sh
echo "Skill files installed to ${SKILL_DIR} ✅"

# 6. Update scripts with the generated key
sed -i "s/ms-323a144af37bf9ab26ddc8bc4edd1b3c/${MASTER_KEY}/g" "${SKILL_DIR}/scripts/search.sh"
sed -i "s/ms-323a144af37bf9ab26ddc8bc4edd1b3c/${MASTER_KEY}/g" "${SKILL_DIR}/scripts/indexer.sh"
echo "Scripts configured with master key ✅"

# 7. Set up cron for hourly indexing
(crontab -l 2>/dev/null | grep -v "meili-memory"; echo "0 * * * * cd ${SKILL_DIR} && bash scripts/indexer.sh >> /tmp/meili-indexer.log 2>&1") | crontab -
echo "Hourly auto-indexing cron job installed ✅"

# 8. Run initial index
echo "Running initial index..."
bash "${SKILL_DIR}/scripts/indexer.sh" 2>&1

echo ""
echo "=== Installation complete ==="
echo "MeiliSearch: http://127.0.0.1:7700"
echo "Skill dir:   ${SKILL_DIR}"
echo "Master key:  ${MASTER_KEY}"
echo ""
echo "To search manually: bash ${SKILL_DIR}/scripts/search.sh 'your query'"
echo "To reindex:         bash ${SKILL_DIR}/scripts/index

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · lib/config.sh (reported line 11)May include surrounding context.

sh
WORKSPACE="/root/.openclaw/workspace"
fi

# Load .env if it exists
ENV_FILE="${WORKSPACE}/.env"
if [ -f "$ENV_FILE" ]; then
  set -a

Credential Access

High
Category
Privilege Escalation
Confidence
95% confidence
Finding

The script executes source "$ENV_FILE", which runs the contents of the workspace .env file as shell code. If an attacker can modify that file, they can achieve arbitrary command execution whenever this config loader is sourced, making this more dangerous in an agent skill context where workspace files may be influenced by other components or untrusted inputs.

Content

Scanner excerpt · lib/config.sh (reported line 12)May include surrounding context.

sh
fi

# Load .env if it exists
ENV_FILE="${WORKSPACE}/.env"
if [ -f "$ENV_FILE" ]; then
  set -a
  source "$ENV_FILE"

External Script Fetching

High
Category
Supply Chain
Confidence
90% confidence
Finding

Remote code is downloaded and executed. This bypasses code review and could introduce malicious code.

Content

Scanner excerpt · scripts/indexer.sh (reported line 356)May include surrounding context.

sh
echo ""
echo "=== Index Stats ==="
for TIER in core working archive; do
  STATS=$(curl -s "${MEILI_HOST}/indexes/${TIER}/stats" -H "Authorization: Bearer ${MEILI_KEY}" 2>/dev/null)
  COUNT=$(echo "$STATS" | python3 -c "import json,sys; print(json.load(sys.stdin).get('numberOfDocuments','?'))" 2>/dev/null || echo "?")
  echo "  ${TIER}: ${COUNT} documents"
done

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
80% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · README.md (reported line 12)May include surrounding context.

md
- **Credentials**: MeiliSearch master key is loaded from `~/.openclaw/workspace/.env` — never hardcoded in scripts
- **Sensitive data filtering**: Indexer and distillation skip content containing tokens, passwords, API keys, private keys, and credentials
- **Safe defaults**: Distillation defaults to `--dry-run`; destructive operations require `--force`
- **Secure temp files**: All temporary files use `mktemp` with `chmod 600` and are cleaned up on exit

## Capabilities

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
80% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

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

md
- **Credentials**: MeiliSearch master key is loaded from `~/.openclaw/workspace/.env` — never hardcoded in scripts
- **Sensitive data filtering**: Indexer and distillation skip content containing tokens, passwords, API keys, private keys, and credentials
- **Safe defaults**: Distillation defaults to `--dry-run`; destructive operations require `--force`
- **Secure temp files**: All temporary files use `mktemp` with `chmod 600` and are cleaned up on exit

## Capabilities

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
80% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · scripts/indexer.sh (reported line 41)May include surrounding context.

sh
- **Credentials**: MeiliSearch master key is loaded from `~/.openclaw/workspace/.env` — never hardcoded in scripts
- **Sensitive data filtering**: Indexer and distillation skip content containing tokens, passwords, API keys, private keys, and credentials
- **Safe defaults**: Distillation defaults to `--dry-run`; destructive operations require `--force`
- **Secure temp files**: All temporary files use `mktemp` with `chmod 600` and are cleaned up on exit

## Capabilities

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
80% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · scripts/indexer.sh (reported line 301)May include surrounding context.

sh
- **Credentials**: MeiliSearch master key is loaded from `~/.openclaw/workspace/.env` — never hardcoded in scripts
- **Sensitive data filtering**: Indexer and distillation skip content containing tokens, passwords, API keys, private keys, and credentials
- **Safe defaults**: Distillation defaults to `--dry-run`; destructive operations require `--force`
- **Secure temp files**: All temporary files use `mktemp` with `chmod 600` and are cleaned up on exit

## Capabilities

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
80% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · scripts/search.sh (reported line 27)May include surrounding context.

sh
- **Credentials**: MeiliSearch master key is loaded from `~/.openclaw/workspace/.env` — never hardcoded in scripts
- **Sensitive data filtering**: Indexer and distillation skip content containing tokens, passwords, API keys, private keys, and credentials
- **Safe defaults**: Distillation defaults to `--dry-run`; destructive operations require `--force`
- **Secure temp files**: All temporary files use `mktemp` with `chmod 600` and are cleaned up on exit

## Capabilities

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
94% confidence
Finding

The skill declares broad read/write/execute capabilities in prose but does not use a formal tool scope such as permissions or allowed-tools. That makes the effective authority ambiguous and can let an agent invoke filesystem and shell actions beyond what a user would expect from a 'search' skill, increasing the chance of over-privileged execution.

Content

No source excerpt is available for this finding.

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
70% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · install.sh (reported line 10)May include surrounding context.

sh
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"
fi

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
70% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · install.sh (reported line 20)May include surrounding context.

sh
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"
fi

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
70% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · install.sh (reported line 39)May include surrounding context.

sh
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"
fi

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
70% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · install.sh (reported line 40)May include surrounding context.

sh
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"
fi

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
70% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · install.sh (reported line 42)May include surrounding context.

sh
if ! command -v meilisearch &> /dev/null; then
  echo "Installing MeiliSearch..."
  curl -L https://install.meilisearch.com | sh
  sudo mv ./meilisearch /usr/local/bin/
else
  echo "MeiliSearch already installed: $(meilisearch --version)"
fi

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The installer prints the generated MeiliSearch master key to stdout, which can leak into terminal logs, shell history captures, CI logs, remote session recordings, or support transcripts. Exposure of this credential would allow full administrative access to the MeiliSearch instance.

Content

No source excerpt is available for this finding.

Description-Behavior Mismatch

Medium
Category
Not specified by scanner
Confidence
88% confidence
Finding

The installer goes beyond a simple local skill setup by installing a system-wide service and a recurring cron job. Even if intended to support MeiliSearch, this expands the operational footprint and persistence of the skill, increasing risk and making unintended data processing or resource use more likely.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.