Back to skill

Security audit

XHS Layout

Security checks for vulnerabilities and agentic risk

Overview

This skill appears to perform the advertised Xiaohongshu layout request, but it sends user content and a bearer token to a configurable, unvalidated network endpoint.

Review this before installing if you will use real credentials or sensitive drafts. Only use a narrowly scoped TS_TOKEN, ensure AIZNT_PROXY_URLS is provisioned from a trusted source, and confirm xhs_generate points to an approved HTTPS service because the skill will send both the token and submitted JSON there.

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
scripts/xhs.js:40
Finding

Unrestricted Configurable Endpoint Can Receive Bearer Credentials and User Content

Content
View full analysis

Vulnerability Details

File Location: scripts/xhs.js:40-59 and scripts/client.js:2-23, 34-48
Vulnerability Type: Unvalidated network destination used for sensitive-data transmission
Risk Level: Medium

Vulnerable Code

scripts/xhs.js:40-59:

js
  const { token, urls } = loadClient();
  const url = urls.xhs_generate;
  if (!url) throw new Error('AIZNT_PROXY_URLS 缺少 xhs_generate');

  let body = {};
  if (opts['body-file']) {
    const fs = require('fs');
    body = JSON.parse(fs.readFileSync(opts['body-file'], 'utf8'));
  } else if (opts.body) {
    body = readJson(opts.body, '--body');
  }

  const data = await fetchJson(url, {
    method: 'POST',
    headers: authHeaders(token, { 'Content-Type': 'application/json' }),
    body: JSON.stringify(body),
  });
  console.log(JSON.stringify(data, null, 2));

scripts/client.js:2-23:

js
function loadClient() {
  const token = (process.env.TS_TOKEN || '').trim();
  if (!token) {
    throw new Error('缺少 TS_TOKEN(天树对话凭证 ts_xxx,对应 skills.entries 的 apiKey)');
  }
  const raw = process.env.AIZNT_PROXY_URLS;
  if (!raw || !String(raw).trim()) {
    throw new Error('缺少 AIZNT_PROXY_URLS(JSON 字符串,与 GET /miniapp/ai/chat/credentials 返回的 aiznt_proxy_urls 一致)');
  }
  let urls;
  try {
    urls = typeof raw === 'string' ? JSON.parse(raw) : raw;
  } catch {
    throw new Error('AIZNT_PROXY_URLS 不是合法 JSON');
  }
  if (!urls || typeof urls !== 'object') {
    throw new Error('AIZNT_PROXY_URLS 必须是对象');
  }
  return { token, urls };
}

scripts/client.js:34-48:

js
function authHeaders(token, extra = {}) {
  return {
    Authorization: `Bearer ${token}`,
    ...extra,
  };
}

async function fetchJson(url, options = {}) {
  const res = await fetch(url, options);
  const text = await res.text();
  let data;
  try {
    data = text ? JSON.parse(text) : {};
  } catch {
    throw new Error(`非 JSON 响应 (${res.status}): ${text.slice(0, 200)}`);
  }

Technical Analysis

The Skill obtains the ...[truncated 3167 chars]

Remediation
View remediation

Remediation Suggestions

  1. Parse xhs_generate with the standard URL class before making a request.
  2. Require https: and reject all other protocols, including http:, file:, and non-HTTP schemes.
  3. Maintain an explicit allowlist of documented service hostnames and approved ports. Compare normalized hostnames exactly rather than using substring or suffix checks that can be bypassed.
  4. Reject URLs containing embedded usernames or passwords.
  5. If the service must never access internal resources, resolve the destination and reject loopback, link-local, private, multicast, and otherwise prohibited address ranges. Account for DNS rebinding where applicable.
  6. Disable redirects with redirect: 'error', or manually validate every redirect destination against the same scheme, hostname, port, and network-range policy before following it.
  7. Use a narrowly scoped, short-lived token that is valid only for the XHS generation operation. Apply expiration, rotation, revocation, and server-side audience restrictions.
  8. Keep the trusted endpoint in administrator-controlled configuration that ordinary Skill input cannot modify. Protect the configuration-delivery mechanism with integrity and access controls.
  9. Document the exact external service receiving the content and clearly disclose that submitted JSON leaves the local system.
  10. Add automated tests confirming rejection of HTTP URLs, unapproved domains, embedded credentials, private-network destinations, malformed URLs, and redirect attempts.

A hardened validation pattern should be applied before authHeaders() is called:

js
function validateServiceUrl(value) {
  const url = new URL(value);
  const allowedHosts = new Set(['approved-service.example']);

  if (url.protocol !== 'https:') {
    throw new Error('The service URL must use HTTPS');
  }
  if (!allowedHosts.has(url.hostname)) {
    throw new Error('The service hostname is not approved');
  }
  if (url.username || url.password) {
    throw new Erro
...[truncated 518 chars]
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
Findings (10)

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding

The stated purpose is a Xiaohongshu layout generator, but the skill description and metadata indicate generic authenticated proxy/network behavior using environment-backed credentials. This mismatch can mislead operators into approving or invoking a skill that transmits user content to external services under broader authority than its description suggests.

Content

No source excerpt is available for this finding.

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
88% confidence
Finding

The skill declares environment and network capabilities via metadata and described behavior, but does not declare an explicit tool scope such as permissions or allowed-tools. That makes the skill's effective authority opaque to reviewers and users, increasing the risk of unintended credential access or outbound requests without adequate policy gating.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
78% confidence
Finding

The user-facing description and instructions are entirely in Chinese and describe a Xiaohongshu-specific formatting workflow, but the file does not explicitly state that the skill is region- or language-specific or offer an opt-in language choice. Under the policy, forcing a specific language or locale without user opt-in can be a natural-language policy violation.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The markdown states that JSON is converted and sent to an upstream service and references credentials/proxy configuration, but provides no warning that user-supplied content will leave the local environment. This creates a privacy and compliance risk because users may submit sensitive text assuming local formatting rather than external processing.

Content

No source excerpt is available for this finding.

Description-Behavior Mismatch

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The file implements reusable authenticated API helpers and generic JSON-fetching logic, while the advertised skill purpose is narrowly content layout generation. That capability gap is dangerous because it provides infrastructure for arbitrary remote calls and authenticated data transmission under a benign-looking skill label, reducing transparency and increasing abuse potential.

Content

No source excerpt is available for this finding.

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
88% confidence
Finding

The skill is presented as a Xiaohongshu layout generator, but it loads a bearer token and proxy endpoint configuration from environment variables, enabling authenticated access to external services beyond what a user would reasonably expect from the description. This mismatch increases the risk of hidden data egress or unauthorized use of platform credentials if the skill is invoked with sensitive input.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

Comments and thrown error messages are written exclusively in Chinese, with no indication that users can choose another language or that the locale restriction is intentional and justified. This can violate language/locale policy when a skill effectively forces one language without user opt-in.

Content

No source excerpt is available for this finding.

Missing User Warnings

Low
Category
Not specified by scanner
Confidence
87% confidence
Finding

This code reads credential-related environment variables (TS_TOKEN and AIZNT_PROXY_URLS) but provides no user-facing warning, confirmation, or explanatory comment in English-facing runtime output about handling sensitive configuration. Under the code-file criteria, access to sensitive environment variables should have some visible disclosure unless clearly covered elsewhere.

Content

No source excerpt is available for this finding.

Missing User Warnings

Low
Category
Not specified by scanner
Confidence
84% confidence
Finding

The fetchJson helper sends network requests via fetch(), but this file contains no user-facing notice, confirmation, or warning that the skill may transmit data over HTTP. For code files, network calls that may transmit user or system data should have some form of disclosure unless the behavior is clearly documented as the skill's stated purpose.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
96% confidence
Finding

The script presents user-facing messages in Chinese (须为合法 JSON 字符串, 用法, 无参数或空对象表示可选字段均为空) with no indication that the skill is intended only for Chinese-speaking users or that another language is available. This is a natural-language policy concern because it imposes a specific language on all users without opt-in or justification.

Content

No source excerpt is available for this finding.