Back to skill

Security audit

offline-quiz-builder

Security checks for vulnerabilities and agentic risk

Overview

The skill mostly matches its offline quiz-builder purpose, but it contains security flaws that could run local commands or injected browser scripts when given malicious paths or question-bank data.

Review before installing. Use only trusted question-bank files and safe output paths, and avoid enabling reminders until open_quiz.py is fixed to use shell-free subprocess calls. The quiz renderer should also escape or strictly validate option keys before generated sites are shared or opened with untrusted bank data.

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 (2)

T09 · Insecure Skill Coding Practices

Error
Location
assets/app-template/assets/js/app.js:779
Finding

Stored DOM-Based Cross-Site Scripting Through Unescaped Question Option Keys

Content
View full analysis
' + opts.map(function (o) { var cls = 'opt'; if (locked) { cls += ' locked'; if (right.indexOf(o.key) >= 0) cls += ' ok'; else if (sel.indexOf(o.key) >= 0) cls += ' bad'; } else if (sel.indexOf(o.key) >= 0) cls += ' sel'; return '
' + o.key + '' + '' + esc(o.text) + '
'; }).join('') + ''; } ``` The same unsafe construction exists in the batch-mode renderer: ```javascript function batchOptionsHtml(q, opts, sel, idx) { return '
' + opts.map(function (o) { ...[truncated 2764 chars]
Remediation
View remediation
' + esc(o.key) + '' + esc(o.text) + ''; ``` Apply the same correction to `batchOptionsHtml()`. 3. Prefer DOM construction over string-based HTML generation. Set untrusted values through `textContent` and attributes through `setAttribute()`. 4. Audit every `innerHTML` and `insertAdjacentHTML` call for data originating from question banks or browser storage. 5. Add regression tests using option keys containing quotes, angle brackets, event handlers, and entity-encoded payloads. Validation should reject them, and rendering should never create executable elements. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/open_quiz.py:51
Finding

Shell Command Injection in Browser-Opening Fallback

Content
View full analysis
Remediation
View remediation
Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
Findings (22)

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding

代码核心是一个已经生成好的题库网站前端应用,而不是“资料转题库网站”的转换器。它围绕 BANK/questions.json 渲染题目、答题、判题、复盘、错题收藏、统计、日历和设置,并通过 Store/SRS 做本地学习记录与复习排程,这与描述中的离线复习网站功能大体一致。但声明的关键卖点是把任意学习资料或已有题库自动转换成网站,以及自动创建每日复习提醒任务;在提供的代码中没有看到文件解析、文档提取、题目生成、题库构建、导出站点,或任何系统计划任务/提醒任务创建相关逻辑。因而描述显著高于实际代码能力,属于能力描述不准确的 mismatch。

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding

声明描述的是一个功能完整的离线复习题库生成与学习系统,但所给代码片段只是一个占位 JavaScript 文件,没有解析资料、生成题库、排程复习、创建提醒或提供学习功能。虽然注释说明真实题库可能由其他脚本生成并覆盖此文件,但基于当前提供的代码片段,其实际行为与声明的主要用途严重不符,因此应判定为不匹配。

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding

该代码块是第三方动画库 GSAP 的最小化源码,核心功能是为网页元素提供 tween、timeline、CSS transform、SVG transform、easing 等动画能力。这类代码可作为某个网站的界面支持性依赖,但它本身并不执行声明中所述的核心业务功能。根据评估标准,支持性实现细节本可不视为不匹配;但这里提供的代码块完全体现的是一个通用动画引擎,而不是学习资料转题库或智能复习系统的任何实质行为,因此与声明用途存在明显不一致。

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
89% confidence
Finding

声明描述的是一个完整的离线智能复习题库网站生成器,强调从多种原始学习资料自动转换,并包含复习排程与学习管理功能。实际代码块只是构建流程中的一个子步骤:对现成题库 JSON 做严格校验、补全 subjects 元数据、生成 questions.json 和 data.js 以供离线网页使用。它确实支持“离线题库网站构建”的一部分,但远不足以覆盖声明中的核心能力,尤其是资料解析/题目生成、遗忘曲线排程、提醒任务和学习功能模块。因此描述对该代码块的能力有明显夸大,属于实质性不匹配。

Content

No source excerpt is available for this finding.

Hidden Instructions

High
Category
Prompt Injection
Confidence
70% confidence
Finding

Hidden instructions were detected in comments or invisible text. These could contain malicious directives. Manual review is recommended.

Content

Scanner excerpt · assets/app-template/index.html (reported line 12)May include surrounding context.

html
</head>
<body>

<!-- 顶栏:淡色主题 + 图标导航 -->
<header class="topbar">
  <div class="topbar-inner">
    <div class="brand" id="brandHome" title="返回首页">

Hidden Instructions

High
Category
Prompt Injection
Confidence
70% confidence
Finding

Hidden instructions were detected in comments or invisible text. These could contain malicious directives. Manual review is recommended.

Content

Scanner excerpt · assets/app-template/index.html (reported line 12)May include surrounding context.

html
</head>
<body>

<!-- 顶栏:淡色主题 + 图标导航 -->
<header class="topbar">
  <div class="topbar-inner">
    <div class="brand" id="brandHome" title="返回首页">

os.system() or os exec-family call

High
Category
Dangerous Code Execution
Confidence
95% confidence
Finding

The script interpolates a filesystem path into a shell command via os.system on macOS. Although the path is wrapped in double quotes, shell metacharacters such as embedded double quotes can still break out of quoting and permit command injection if an attacker controls the target path. Because this skill is designed to open user-supplied local quiz directories/files, the input surface is realistic and the fallback path makes exploitation possible when webbrowser.open() fails.

Content

Scanner excerpt · scripts/open_quiz.py (reported line 52)May include surrounding context.

python
if sys.platform.startswith("win"):
            os.startfile(str(index))  # noqa: S606
        elif sys.platform == "darwin":
            os.system(f'open "{index}"')
        else:
            os.system(f'xdg-open "{index}"')

os.system() or os exec-family call

High
Category
Dangerous Code Execution
Confidence
96% confidence
Finding

The Linux fallback builds an xdg-open shell command from a user-influenced path and executes it with os.system. A malicious filename containing shell-breaking characters can trigger arbitrary command execution under the current user when the fallback branch is reached. In this skill's context, opening arbitrary local study materials and generated sites makes attacker-controlled filenames or directories plausible, increasing the risk.

Content

Scanner excerpt · scripts/open_quiz.py (reported line 54)May include surrounding context.

python
elif sys.platform == "darwin":
            os.system(f'open "{index}"')
        else:
            os.system(f'xdg-open "{index}"')

    print(f"已在默认浏览器打开:{url}")
    return 0

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
70% confidence
Finding

Without declared permissions the skill's intent is opaque and cannot be validated.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

该描述将触发条件写成“当用户想把资料变成刷题网站、做复习题库、生成练习题、搭建离线背题工具、或需要按遗忘曲线安排复习时,应使用本技能”。其中“生成练习题”“做复习题库”等表述较宽泛,缺少边界、排除条件或更精确的触发短语,容易与一般学习辅导请求重叠。

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
93% confidence
Finding

This JavaScript file contains extensive natural-language UI strings in Chinese, starting from the header comments and continuing throughout labels, prompts, and button text. Because the skill does not provide any visible user opt-in, language selector, or justification that it is intended only for a Chinese-language audience, it violates the language/locale policy criteria.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

The manifest-style JSON metadata presents the skill title and descriptive note entirely in Chinese, indicating a fixed language/locale experience. Under the policy, locale constraints should either offer user opt-in/choice or be clearly documented as justified for a region-specific tool, which is not present here.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The trigger phrase at line 17 is broad enough to match common user requests that may not specifically intend to invoke this skill. Overly generic activation phrases increase the chance of unintended skill execution, which can grant local filesystem write access and Bash-capable workflows in situations where the user only asked a general educational question.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
86% confidence
Finding

This markdown instruction set forces a specific language/locale for the skill's behavior and user-facing communication, but does not indicate that the user can choose another language or that the restriction is justified by a region-specific requirement. Under the policy, fixed language behavior without user opt-in is a natural-language policy violation.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
89% confidence
Finding

The title and instruction text require adherence to a Chinese question-bank schema and are written as a strict specification, but they do not indicate that language choice is optional or limited to a China-specific/regulatory context. Under the policy, forcing a specific language or locale without opt-in is a natural-language policy violation.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

This code file contains natural-language instructions and behavior descriptions only in Chinese, which effectively forces a specific language for users of the skill. The policy allows locale constraints only when explicitly documented and justified or when users are offered a language choice, neither of which appears here.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

The module docstring is entirely in Chinese and presents the skill's purpose and usage only in that language. This creates a locale/language policy issue because the skill implicitly requires Chinese comprehension without any opt-in, alternative language, or explicit justification that it is intended only for a Chinese-speaking audience.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
84% confidence
Finding

The stylesheet explicitly prioritizes Chinese-specific fonts such as "PingFang SC", "Microsoft YaHei", and other Simplified Chinese families. This can amount to a locale preference being baked into the skill experience without any visible user opt-in or documented regional limitation in this file.

Content

No source excerpt is available for this finding.

Description-Behavior Mismatch

Low
Category
Not specified by scanner
Confidence
84% confidence
Finding

The manifest emphasizes a purely offline review-site experience, and the file header states '纯前端实现,不依赖任何在线服务'. However, the app still issues an XMLHttpRequest to load questions.json at runtime. While this is a local asset fetch rather than a network service call, it is still behavior beyond a fully self-contained in-memory app and creates a small mismatch with the stated all-offline/self-contained framing.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
94% confidence
Finding

This JavaScript file contains natural-language guidance in a comment that forces a specific language context for readers of the skill asset. Under the policy, language-specific instructions without user opt-in or documented justification can be considered a locale/language policy violation.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
91% confidence
Finding

The document sets lang="zh-CN" and all visible interface text is in Chinese, which indicates a fixed locale. Under the policy rule, forcing a specific language without opt-in or justification is a natural-language policy concern.

Content

No source excerpt is available for this finding.

Vague Triggers

Low
Category
Not specified by scanner
Confidence
84% confidence
Finding

This trigger lacks specificity about both the source material and the operation being requested, making it easier for unrelated or ambiguous prompts to invoke the skill. In this skill's context, accidental activation is more concerning because the manifest advertises read-write local filesystem access and Bash usage, even though network access is disabled.

Content

No source excerpt is available for this finding.