Back to skill

Security audit

alibabacloud-help-doc-search

Security checks for vulnerabilities and agentic risk

Overview

The skill is mostly a disclosed Alibaba Cloud documentation lookup tool, but its document-read command is under-scoped and can fetch non-Alibaba URLs or local files.

Review before installing. The normal search and metadata workflows are read-only and disclosed, but until the read command enforces an allowlist, avoid giving it untrusted URLs and prefer explicit official Alibaba Cloud HTTPS document URLs only. The publisher should reject non-Help Center hosts, non-HTTPS schemes, private or loopback destinations, file URLs, and unvalidated redirects.

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

Error
Location
scripts/help_read.py:48
Finding

Arbitrary URL Fetch Enables Server-Side Request Forgery

Content
View full analysis

Vulnerability Details

File Location: scripts/help_read.py:48-63
Vulnerability Type: Arbitrary outbound request / SSRF
Risk Level: High

Vulnerable Code

python
url = args.url
host = _url_host(url)

# Ensure .md suffix
if not url.endswith(".md"):
    # Only the two Help Center hosts serve raw Markdown at '<url>.md'
    if host in _DOC_HOSTS:
        url = url.rstrip("/") + ".md"

site = (getattr(args, "site", None) or "").strip().lower()
if site in SITES and host and host != SITES[site]["result_host"]:
    print(f"WARN[site-cross]: --site {site} points at {SITES[site]['result_host']} but the given URL is "
          f"on '{host}'; the URL is read as-is and no cross-site rewriting is performed",
          file=sys.stderr)

text = fetch(url, max_bytes=DOC_MAX_BYTES)

The request is ultimately executed by the shared transport layer:

python
req = urllib.request.Request(url, headers={"User-Agent": UA})
opener = urllib.request.urlopen if allow_redirects else _NO_REDIRECT_OPENER.open
try:
    with opener(req, timeout=effective_timeout(timeout or TIMEOUT)) as resp:
        data = resp.read()

Technical Analysis

The read command accepts a user-controlled URL and derives its host with _url_host(). However, membership in _DOC_HOSTS is used only to determine whether the .md suffix should be appended. An unapproved host is never rejected.

A site mismatch also produces only a warning and explicitly continues to read the URL as supplied. Consequently, arbitrary URL schemes and destinations accepted by urllib.request can reach the network transport.

Redirects are enabled by default in fetch(). Therefore, even if direct input were later restricted to an approved Alibaba Cloud host, a redirect could still send the request to an unapproved destination unless every redirect target is validated.

This behavior contradicts the module statement that only Help Center hosts are accepted and exceeds the minimum network access r ...[truncated 1478 chars]

Remediation
View remediation

Remediation Suggestions

  1. Enforce an exact destination allowlist before every request:

    • Require the https scheme.
    • Permit only help.aliyun.com and www.alibabacloud.com.
    • Reject missing hosts, user-information components, nonstandard schemes, and unexpected ports.
  2. Do not merely warn on a host mismatch. Return an input error before making a request.

  3. Disable automatic redirects for document reads. If redirects are required, process them manually and validate every destination against the same scheme, host, and port policy.

  4. Resolve the destination and reject loopback, private, link-local, multicast, reserved, and unspecified IP addresses. Repeat validation after each redirect and account for multiple DNS answers.

  5. Consider constraining paths to the documented Help Center layouts rather than allowing every path on an approved domain.

  6. Add regression tests covering:

    • Direct requests to localhost and private IP addresses.
    • Link-local metadata addresses.
    • Unsupported schemes such as file:.
    • Approved hosts redirecting to unapproved hosts.
    • Hostname parsing edge cases, embedded credentials, and unexpected ports.
    • Valid China and international Help Center document URLs.

A suitable validation flow is:

python
parsed = urllib.parse.urlsplit(url)

if parsed.scheme != "https":
    raise _UsageError("Only HTTPS Help Center URLs are supported.")

if parsed.hostname not in _DOC_HOSTS:
    raise _UsageError("Only official Alibaba Cloud Help Center hosts are supported.")

if parsed.username or parsed.password or parsed.port not in (None, 443):
    raise _UsageError("URL credentials and nonstandard ports are not supported.")

text = fetch(url, max_bytes=DOC_MAX_BYTES, allow_redirects=False)

If legitimate canonical redirects must be supported, follow them through a bounded loop and apply the full validation policy to each Location value before issuing the next request.

Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Rogue AgentSelf-Modification, Session Persistence
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
Findings (27)

YARA rule 'agent_skill_prompt_injection_hidden_instructions': Prompt injection or hidden instructions embedded in AI agent skill text [agent_skills]

High
Category
YARA Match
Confidence
80% confidence
Finding

YARA rule matched a hack tool or exploit indicator (offensive tools, reconnaissance, privilege escalation, or exploit frameworks).

Content

Scanner excerpt · references/ecs-knowledge-faq.md (reported line 31)May include surrounding context.

md
rage profile to a candidate family, and finally validate with real-world testing before committing. The official selection guide walks through this decision process step by step and is the recommended starting point for capacity planning.

Source: https://help.aliyun.com/document_detail/58291.html

## How do subscription, pay-as-you-go, and preemptible instances differ?

Subscription is a prepaid model best for steady 7x24 services such as persistent web servers: you pay upfront for a fixed term at a lower effective price. Pay-as-you-go bills by the second/hour with no commitment, ideal for elastic, bursty, or short-lived workloads. Preemptible instances offer steep discounts over pay-as-you-go but can be reclaimed automatically when market price exceeds your cap or supply runs short, so they only fit interruption-tolerant jobs such as batch computation, CI, and stateless scaling.

Source: https://help.aliyun.com/document_detail/25370.html

## What are savings plans and how do they red

Instruction Override

High
Category
Prompt Injection
Confidence
90% confidence
Finding

This pattern attempts to override system instructions or ignore safety constraints. Without LLM analysis, manual review is recommended.

Content

Scanner excerpt · references/ecs-knowledge-faq.md (reported line 61)May include surrounding context.

md
## Why can I not ping my ECS instance, and how do security groups factor in?

The security group must contain a rule allowing ICMP (ping) inbound; if that rule was removed, ping fails and you should restore it in the ECS console. Also check the VPC network ACL bound to the instance's vSwitch, because ACL rules restrict both inbound and outbound traffic and can override security-group allowances. Ping failures should be diagnosed layer by layer: security group rules, network ACLs, then OS-level firewall settings.

Source: https://help.aliyun.com/document_detail/40572.html

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
88% confidence
Finding

The skill describes capabilities that include environment-variable use, local cache reads/writes under the user's home directory, and outbound network access, but it does not declare an explicit tool/permission scope. That creates a governance gap: an orchestrator or reviewer cannot reliably constrain the skill to the minimum required privileges, increasing the chance of unintended file or network access if the implementation diverges from the documentation.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The trigger list includes phrases like "help center", "best practice", "API reference", and especially "what does this error mean" / "how to fix this error", which are common across many domains and not uniquely tied to Alibaba Cloud. Although the description is Alibaba-specific overall, these broad phrases are presented as triggers without requiring explicit Alibaba Cloud context or negative examples, increasing the risk of unintended invocation.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
82% confidence
Finding

Lines L139-L140 state that error codes, parameter names, and quota numbers are 'never recalled from the index leg' and that this is 'the metadata leg's job'. But earlier guidance distinguishes search-based narrative troubleshooting from explicit api-info metadata lookups for per-API contract data, so this wording overstates what ordinary search does and blurs tool behavior. That is an intent/documentation contradiction rather than a mere omission.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The related documentation search is hard-coded to use site="cn" and lang="zh", and the rendered output also labels the results as 'China site, zh'. This enforces a locale/language choice in the skill behavior with no user selection or opt-in, which matches the policy's language/locale violation criteria.

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 · scripts/help_cache.py (reported line 98)May include surrounding context.

python
def _save_category_cache(cache: dict) -> None:
    """Write the cache file back (create the directory if missing).

    Bare-int seed entries are not written to the file (avoid cache-file shape drift; seeds only take effect in memory).
    Write to a temp file (same directory, pid suffix) then os.replace atomically; on write failure only WARN,

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · references/api-metadata.md (reported line 9)May include surrounding context.

md
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · references/api-metadata.md (reported line 16)May include surrounding context.

md
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · references/api-metadata.md (reported line 25)May include surrounding context.

md
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · references/api-metadata.md (reported line 37)May include surrounding context.

md
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · references/api-metadata.md (reported line 60)May include surrounding context.

md
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · references/ram-policies.md (reported line 11)May include surrounding context.

md
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · scripts/help_api_meta.py (reported line 223)May include surrounding context.

python
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · scripts/help_core.py (reported line 114)May include surrounding context.

python
# Site-independent OpenAPI metadata endpoint (both sites reference the same contracts).
META_BASE = "https://api.aliyun.com/meta/v1"


# Backwards-compatible aliases for the pre-i18n defaults (cn + zh). They must resolve to the

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 · scripts/help_core.py (reported line 148)May include surrounding context.

python
DOC_MAX_BYTES = 4 * 1024 * 1024


# categoryId mapping cache: must live in the user directory; never write into the skill directory (platform static checks only allow standard files)
CATEGORY_CACHE_PATH = os.path.expanduser("~/.cache/aliyun-help-search/category_map.json")

Unbounded Resource Access

Medium
Category
Excessive Agency
Confidence
75% confidence
Finding

Skill allows unbounded resource consumption (API calls, storage, compute). Without rate limits or quotas, a compromised or misbehaving agent can cause denial-of-service or cost overruns.

Content

Scanner excerpt · scripts/help_core.py (reported line 369)May include surrounding context.

python
# N3: a caller may widen or narrow every request deadline from the command line (0 = keep the
# per-endpoint default). The override is applied only through effective_timeout(), so no call
# site carries its own timeout arithmetic.
_cli_timeout = 0


def set_cli_timeout(seconds) -> None:

Unbounded Resource Access

Medium
Category
Excessive Agency
Confidence
75% confidence
Finding

Skill allows unbounded resource consumption (API calls, storage, compute). Without rate limits or quotas, a compromised or misbehaving agent can cause denial-of-service or cost overruns.

Content

Scanner excerpt · scripts/help_core.py (reported line 378)May include surrounding context.

python
# N3: a caller may widen or narrow every request deadline from the command line (0 = keep the
# per-endpoint default). The override is applied only through effective_timeout(), so no call
# site carries its own timeout arithmetic.
_cli_timeout = 0


def set_cli_timeout(seconds) -> None:

Unbounded Resource Access

Medium
Category
Excessive Agency
Confidence
75% confidence
Finding

Skill allows unbounded resource consumption (API calls, storage, compute). Without rate limits or quotas, a compromised or misbehaving agent can cause denial-of-service or cost overruns.

Content

Scanner excerpt · scripts/help_core.py (reported line 380)May include surrounding context.

python
# N3: a caller may widen or narrow every request deadline from the command line (0 = keep the
# per-endpoint default). The override is applied only through effective_timeout(), so no call
# site carries its own timeout arithmetic.
_cli_timeout = 0


def set_cli_timeout(seconds) -> None:

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
90% confidence
Finding

The file embeds bilingual Chinese-English aliasing and later rewrites Chinese queries into English documentation vocabulary, which imposes a specific language/locale behavior in the skill itself. There is no visible user opt-in, configuration, or alternative locale handling in this file, so the skill appears to enforce a language policy rather than offering a choice.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The translate_query_for_english function rewrites Chinese input terms into English terms for search, and its docstring indicates the caller should refuse the Chinese full-text path and use the rewritten English form instead. This is a natural-language locale transformation with no user opt-in or visible choice mechanism in the file.

Content

No source excerpt is available for this finding.

Unbounded Resource Access

Medium
Category
Excessive Agency
Confidence
75% confidence
Finding

Skill allows unbounded resource consumption (API calls, storage, compute). Without rate limits or quotas, a compromised or misbehaving agent can cause denial-of-service or cost overruns.

Content

Scanner excerpt · references/search-backend.md (reported line 155)May include surrounding context.

md
An out-of-range pageNum is not an error on search.json: it answers HTTP 200 with a full
    page whose entries lost categoryId, categoryName and content (measured: pageNum=50 with 40
    valid pages returned 10 items carrying only 7 fields), so a length-based pagination test
    would loop forever and collect shells. require_content=False is used for doSearch, whose
    entries always carry both fields (measured 197/197) and whose historical behaviour must not
    change; there only an entry without a URL is structurally useless.
    """

Unbounded Resource Access

Medium
Category
Excessive Agency
Confidence
75% confidence
Finding

Skill allows unbounded resource consumption (API calls, storage, compute). Without rate limits or quotas, a compromised or misbehaving agent can cause denial-of-service or cost overruns.

Content

Scanner excerpt · scripts/help_search.py (reported line 96)May include surrounding context.

python
An out-of-range pageNum is not an error on search.json: it answers HTTP 200 with a full
    page whose entries lost categoryId, categoryName and content (measured: pageNum=50 with 40
    valid pages returned 10 items carrying only 7 fields), so a length-based pagination test
    would loop forever and collect shells. require_content=False is used for doSearch, whose
    entries always carry both fields (measured 197/197) and whose historical behaviour must not
    change; there only an entry without a URL is structurally useless.
    """

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The module docstring states the endpoint 'only ever serves the cn+zh corpus,' and the implementation defaults to site='cn' and lang='zh'. This natural-language behavior indicates a fixed language/locale constraint without any user opt-in or documented choice, which matches the language/locale policy violation category.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
88% confidence
Finding

The docstring says the unscoped request preserves 'the historical behaviour a default cn+zh invocation relies on,' which natural-language-wise encodes a locale-specific default rather than offering a choice. Because the file presents this as default behavior rather than a documented user-selected regional mode, it falls under the locale policy concern.

Content

No source excerpt is available for this finding.