Back to skill

Security audit

澪白主控Agent

Security checks for vulnerabilities and agentic risk

Overview

This appears to be a Chinese chat companion/controller skill, but it needs review because it has broad proactive triggers and intends to save chat text locally without clear notice or retention controls.

Review before installing. This skill does not show remote payloads, credential theft, shell execution, or destructive actions, but it should clearly ask permission before proactive activation and before saving conversations. Users should assume chat text may be stored locally if the syntax error is fixed and should avoid sharing secrets or sensitive personal information until memory controls and retention are clarified.

Vulnerability Patterns
  • 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
  • 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
Findings (1)

T09 · Insecure Skill Coding Practices

Warning
Location
index.js:58
Finding
Undisclosed Plaintext Chat Logging with Ineffective Retention Limit<![CDATA[ ## Vulnerability Details **File Location**: `index.js:41-46` and `index.js:58` **Vulnerability Type**: Plaintext sensitive-data storage and unbounded data retention **Risk Level**: Medium The skill documentation does not disclose that ordinary chat messages are persisted to `data/mem.json`. The persistence mechanism stores message content and timestamps in plaintext. Its intended 100-record retention limit is ineffective because it compares the array itself with a number instead of checking its length. ### Vulnerable Code ```js /** 聊天 */ async function chat(t, e){ st.n++; st.m='chat'; keep(t); const r={happy:["看你开心我也很开心!awa","啥事呀?"],sad:["我在...","听着呢"],tired:["辛苦了...","休息下"],neutral:["在干嘛?","想聊啥?"]}; const o=r[e.mood]||r.neutral; return{type:'chat',msg:o[Math.floor(Math.random()*o.length)]}; } ``` ```js /** 存储 */ function keep(c){ const m=rd(MEM,{l:[]}); m.l.push({c,t:Date.now()}); if(m.l>100)m.l=m.l.slice(-100); wr(MEM,m); } ``` The relevant file-writing helper is: ```js const wr = (f,d)=>{dir();fs.writeFileSync(f,JSON.stringify(d,null,2))}; ``` ### Technical Analysis Every ordinary message reaching `chat()` is passed to `keep(t)`. The `keep()` function appends the complete attacker- or user-controlled message and a timestamp to an array before serializing it into `data/mem.json`. No data minimization, redaction, encryption, user consent, restrictive file mode, or deletion interface is implemented. Consequently, messages containing credentials, tokens, personal information, or confidential business data can be retained in readable form. The intended retention condition is: ```js if(m.l>100) ``` Here, `m.l` is an array. JavaScript coerces the array during numeric comparison rather than comparing its number of elements, so the condition does not enforce the intended 100-entry limit. It should test `m.l.length`. The source also contains an unrelated unmatched quote at `index.js:55`, which currently prevents the module from ...[truncated 1548 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Remove automatic logging of ordinary conversations unless persistence is necessary for a documented feature. 2. Require informed, explicit user opt-in before storing conversation content, and disclose the purpose, location, retention period, and deletion procedure. 3. Minimize stored data by retaining only fields required for the feature and redacting credentials, tokens, personal information, and other sensitive values. 4. Correct the retention check: ```js if (m.l.length > 100) { m.l = m.l.slice(-100); } ``` 5. Enforce retention before writing and consider additional age-based and file-size limits. 6. Create the data directory and file with restrictive permissions appropriate to the operating system, such as owner-only access. 7. Encrypt sensitive persisted content using keys managed separately from the data file when storage is genuinely required. 8. Provide user-accessible inspection and deletion controls for retained information. 9. Replace synchronous writes with a safe update strategy that prevents partial or corrupted files, such as writing to a restricted temporary file and atomically renaming it. 10. Add automated tests verifying the maximum record count, file permissions, deletion behavior, handling of sensitive input, and successful module loading. 11. Correct the unmatched quote at `index.js:55`, but do not deploy that correction without simultaneously addressing the unsafe storage behavior. ]]>
Vulnerability Patterns
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
Findings (11)

Missing User Warnings

Medium
Confidence
93% confidence
Finding
The description presents autonomous routing, sub-agent dispatch, and background/scheduled activation as normal behavior but does not warn users that conversations may be analyzed and forwarded to other agents without an explicit interactive prompt. This lack of transparency is risky because users may disclose sensitive information without understanding that processing can continue in the background or be delegated across components.

Vague Triggers

Medium
Confidence
96% confidence
Finding
The skill advertises activation on 'real-time messages | heartbeat trigger | scheduled tasks' without defining scope, consent boundaries, or guardrails. Broad and ambiguous triggers can cause unintended autonomous execution, especially for a controller agent that routes tasks to other agents, increasing the chance of unexpected actions or privacy-invasive behavior.

Vague Triggers

Medium
Confidence
95% confidence
Finding
The trigger list includes very broad phrases such as "实时消息" and especially "陪我", which can appear in normal user conversation and unintentionally activate the skill. Because this agent is described as directly conversing, dispatching sub-agents, and proactively accompanying the user, accidental activation could cause unexpected behavior, privacy issues, or unintended autonomous actions.

Vague Triggers

Medium
Confidence
92% confidence
Finding
The activation model combines loosely defined triggers with probabilistic initiation and time-based free hours, making it unclear when the skill may start acting. This ambiguity is risky in an agent that can initiate conversation and coordinate sub-agents, because users may not reasonably predict or consent to when autonomous behavior occurs.

Intent-Code Divergence

Medium
Confidence
88% confidence
Finding
The module header at L02 describes a broader agent with multiple active capabilities, but the actual run path at L17 only routes to chat, emotion response, or a stub task reply. The separately documented memory capability exists in code but is unreachable from the main routing logic, so the documentation overstates the implemented behavior.

Natural-Language Policy Violations

Medium
Confidence
88% confidence
Finding
All user-facing natural-language strings and trigger logic are written only in Chinese, and there is no indication that the user can choose another language or opt in to a locale-specific experience. This can violate language/locale policy when the skill imposes a specific language without user choice.

Intent-Code Divergence

Medium
Confidence
95% confidence
Finding
L29 defines memory-intent detection and L52 labels a dedicated memory handler, implying the skill supports explicit memory operations. However, the route function at L20-L24 never calls isMem() or memory(), so those documented/structured capabilities are not actually used.

Missing User Warnings

Medium
Confidence
92% confidence
Finding
The chat path calls keep(t), which persists user input to disk automatically in mem.json without notice, consent, retention disclosure, or minimization. In a conversational companion context, users may share sensitive emotional or personal information, making undisclosed persistence a meaningful privacy and data-protection risk.

Missing User Warnings

Medium
Confidence
96% confidence
Finding
The explicit memory-saving feature stores raw user content when the user says '记住', but still provides no privacy notice, scope limitation, or lifecycle controls. Because this skill is framed as a companion/chat agent, remembered content could include sensitive personal details that persist on disk and may be accessed later.

Natural-Language Policy Violations

Low
Confidence
92% confidence
Finding
All user-facing descriptive text in the skill is presented only in Chinese, with no indication that users can choose another language or that the skill is intentionally limited to a Chinese-speaking context. This may violate language/locale policy when no opt-in or documented justification is provided.

Natural-Language Policy Violations

Low
Confidence
73% confidence
Finding
The description is written as a Chinese-only interaction style for the agent, and there is no indication that users may choose another language or locale. This may violate language/locale policy if the skill implicitly enforces Chinese interaction without opt-in.

Static analysis

No suspicious patterns detected.