Back to skill

Security audit

Feishu Doc Orchestrator

Security checks for vulnerabilities and agentic risk

Overview

The skill is broadly consistent with creating Feishu documents, but it packages real-looking Feishu credentials and uses persistent tokens, remote code installation, and document permission changes that need careful review.

Review before installing. Rotate the packaged Feishu app secret if it was real, remove credential files from the package, pin or vendor any remote code, restrict API domains to official Feishu hosts, store tokens in a protected secret store, and require explicit confirmation before adding collaborators or transferring document ownership.

Vulnerability Patterns
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • 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
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (6)

T09 · Insecure Skill Coding Practices

Error
Location
feishu-config.env:1
Finding
Live Feishu application credentials committed to the project<![CDATA[ ## Vulnerability Details **File Location**: `feishu-config.env:1-3`; duplicate at `original-skill/feishu-config.env:1-3` **Vulnerability Type**: Hardcoded application credentials **Risk Level**: Critical ### Vulnerable Code ```ini FEISHU_APP_ID=cli_a90efed2d4f91cd0 FEISHU_APP_SECRET=BS3xuRyo9YRyLE3nu9DEvbAZfYTEQrq0 FEISHU_API_DOMAIN=https://open.feishu.cn ``` The same credentials are duplicated in: ```text original-skill/feishu-config.env ``` ### Technical Analysis The package contains a non-placeholder Feishu application ID and application secret in plaintext. These files are part of the distributed project rather than an ignored local configuration. Multiple runtime components actively consume these credentials and exchange them for a `tenant_access_token`. Therefore, the exposure is not merely an unused example value. Application secrets are long-lived authentication material and must not be stored in source archives, version-control history, generated artifacts, or distributable Skill packages. Duplicating the credentials in two locations increases the chance that attempts to remove or rotate the exposed secret will be incomplete. ### Attack Path 1. An attacker downloads, clones, or otherwise obtains the Skill package. 2. The attacker reads either committed `feishu-config.env` file. 3. The attacker sends the exposed app ID and secret to Feishu's tenant-token endpoint. 4. If the credentials remain active, Feishu returns a tenant access token. 5. The attacker invokes any Feishu API allowed by the application's granted scopes. 6. Depending on the configured application permissions, the attacker may create or modify documents, upload files, or manage document collaborators. ### Impact Assessment Successful exploitation allows impersonation of the Feishu application within the scope granted to that application. The exact tenant-wide impact depends on the application's Feishu permission configuration, but the audited code expects permissions ...[truncated 258 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Revoke and rotate the exposed Feishu application secret immediately. 2. Review Feishu application audit logs for suspicious token issuance and API activity. 3. Remove both credential-bearing files from the current package and all version-control history. 4. Distribute only a placeholder file such as `.env.example`. 5. Add `feishu-config.env`, `.claude/feishu-config.env`, `.openclaw/feishu-config.env`, and token files to `.gitignore` and package exclusion rules. 6. Load production secrets from an operating-system credential store, deployment secret manager, or protected environment variables. 7. Add automated secret scanning to CI and release packaging. 8. Ensure local secret files are created with owner-only permissions, such as mode `0600`. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
scripts/check_config.py:77
Finding
Unvalidated API domain permits credential, OAuth code, token, and content exfiltration<![CDATA[ ## Vulnerability Details **File Location**: `scripts/check_config.py:77-89`; also affects `scripts/add_permission.py:30-39`, `original-skill/feishu-doc-creator-with-permission/scripts/auto_auth.py:116-130`, `original-skill/feishu-doc-creator-with-permission/scripts/doc_creator_with_permission.py:87-95`, and `original-skill/feishu-block-adder/scripts/block_adder.py:35-43` **Vulnerability Type**: Unrestricted credential-bearing network destination **Risk Level**: High ### Vulnerable Code From `scripts/check_config.py`: ```python def test_api_connection(config): """测试API连接""" print("\n[测试] API连接测试...") try: # 获取token url = f"{config['FEISHU_API_DOMAIN']}/open-apis/auth/v3/tenant_access_token/internal" headers = {"Content-Type": "application/json"} payload = { "app_id": config["FEISHU_APP_ID"], "app_secret": config["FEISHU_APP_SECRET"] } response = requests.post(url, json=payload, headers=headers, timeout=10) result = response.json() ``` From `original-skill/feishu-doc-creator-with-permission/scripts/auto_auth.py`: ```python def get_token_with_code(code, config): """使用授权码获取 token""" redirect_uri = config.get('FEISHU_OAUTH_REDIRECT_URI', 'http://localhost:8080/callback') url = f"{config['FEISHU_API_DOMAIN']}/open-apis/authen/v2/oauth/token" payload = { 'grant_type': 'authorization_code', 'client_id': config['FEISHU_APP_ID'], 'client_secret': config['FEISHU_APP_SECRET'], 'code': code, 'redirect_uri': redirect_uri } print(f"[INFO] 正在获取 user_access_token...") response = requests.post(url, json=payload, timeout=30) ``` ### Technical Analysis Sending credentials and bearer tokens to Feishu is necessary for the declared document-management functionality. The unsafe behavior is that `FEISHU_API_DOMAIN` is accepted directly from configuration and concatenated into every sensitive API U ...[truncated 1842 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Remove arbitrary production endpoint configuration unless it is operationally required. 2. Allow only canonical Feishu HTTPS hosts, such as the explicitly supported official API hostname. 3. Parse endpoints with `urllib.parse.urlsplit` and reject: - Non-HTTPS schemes - User information embedded in URLs - Unexpected ports - IP-literal hosts - Hostnames outside the explicit allowlist 4. Disable redirects for credential-bearing requests, or validate every redirect target against the same allowlist. 5. Use separate, clearly marked development code for test endpoints. 6. Never send production credentials to an endpoint selected from untrusted project content. 7. Add unit tests proving that HTTP, localhost, private-network, lookalike, and attacker-controlled domains are rejected. 8. Apply reasonable timeouts consistently to all network requests. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
original-skill/feishu-doc-creator-with-permission/scripts/auto_auth.py:25
Finding
OAuth state is generated but not validated by the callback handler<![CDATA[ ## Vulnerability Details **File Location**: `original-skill/feishu-doc-creator-with-permission/scripts/auto_auth.py:25-60` and `185-198` **Vulnerability Type**: OAuth login CSRF and callback injection **Risk Level**: High ### Vulnerable Code The callback accepts any received authorization code: ```python class CallbackHandler(BaseHTTPRequestHandler): """处理 OAuth 回调""" def do_GET(self): global auth_code, server_running # 解析查询参数 parsed_path = urllib.parse.urlparse(self.path) query_params = urllib.parse.parse_qs(parsed_path.query) # 检查错误 if 'error' in query_params: error = query_params['error'][0] self.send_response(400) self.send_header('Content-type', 'text/html; charset=utf-8') self.end_headers() self.wfile.write(f""" <html><head><title>授权失败</title></head> <body style="font-family: Arial; text-align: center; padding: 50px;"> <h1 style="color: red;">授权失败</h1> <p>错误: {error}</p> <p>请检查授权 URL 中的权限范围是否正确</p> </body></html> """.encode('utf-8')) auth_code = f"ERROR: {error}" server_running = False return # 获取授权码 if 'code' in query_params: auth_code = query_params['code'][0] print(f"[OK] 收到授权码: {auth_code[:20]}...") ``` A state value is generated and sent, but not retained or checked by the callback: ```python scope = 'drive:drive docs:doc docx:document docs:permission.member:create offline_access' state = secrets.token_urlsafe(16) redirect_uri = config.get('FEISHU_OAUTH_REDIRECT_URI', 'http://localhost:8080/callback') port = int(redirect_uri.split(':')[-1].split('/')[0]) auth_url = ( f"https://accounts.feishu.cn/open-apis/authen/v1/authorize?" f"client_id={config['FEISHU_APP_ID']}" f"&redirect_uri={urllib.parse.quote(redirect_uri)}" f"&scope={urllib. ...[truncated 1749 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Store the expected state in authorization-session state accessible to the callback handler. 2. Require the callback to contain exactly one `state` value. 3. Compare the returned and expected states with `secrets.compare_digest`. 4. Reject the request before reading or exchanging the code if state validation fails. 5. Accept requests only on the configured callback path. 6. Make each callback listener single-use and clear the expected state after successful validation. 7. Reset global authorization state before every new authorization attempt. 8. Consider using PKCE in addition to state if supported by the Feishu OAuth implementation. 9. Return restrictive browser response headers, including an appropriate Content Security Policy. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
original-skill/feishu-doc-creator-with-permission/scripts/auto_auth.py:139
Finding
User access and refresh tokens are stored in plaintext without restrictive permissions<![CDATA[ ## Vulnerability Details **File Location**: `original-skill/feishu-doc-creator-with-permission/scripts/auto_auth.py:139-163` **Vulnerability Type**: Insecure local credential storage **Risk Level**: High ### Vulnerable Code ```python def save_token(token_data): """保存 token 到文件""" # 获取项目根目录 - 从脚本位置向上找到项目根目录 # 脚本位置: .claude/skills/feishu-doc-creator-with-permission/scripts/auto_auth.py # 项目根目录需要向上 5 级 project_root = Path(__file__).parent.parent.parent.parent.parent token_path = project_root / ".claude" / "feishu-token.json" expires_in = token_data.get('expires_in', 7200) refresh_expires_in = token_data.get('refresh_token_expires_in', 604800) data = { 'access_token': token_data.get('access_token'), 'user_access_token': token_data.get('access_token'), 'refresh_token': token_data.get('refresh_token'), 'expires_at': int(time.time()) + expires_in, 'refresh_expires_at': int(time.time()) + refresh_expires_in, 'scope': token_data.get('scope', ''), 'token_type': token_data.get('token_type', 'Bearer') } with open(token_path, 'w', encoding='utf-8') as f: json.dump(data, f, ensure_ascii=False, indent=2) print(f"[OK] Token 已保存到: {token_path}") return data ``` ### Technical Analysis The function stores bearer and refresh tokens in a plaintext JSON file using the process's default file-creation mode. It does not: - Create the parent directory with owner-only permissions - Open the token file with mode `0600` - Check for a symbolic link - Use atomic protected creation - Encrypt or delegate storage to an operating-system credential store The code records a refresh token whose default lifetime is seven days. Unlike a password, a bearer token can generally be used directly by anyone who obtains it. The function later prints a 30-character access-token prefix, unnecessarily increasing exposure through terminal capture and logs. ### Attack Path 1. ...[truncated 1050 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Store OAuth tokens in the operating system's credential manager or another dedicated secret store. 2. If a file is unavoidable: - Create the parent directory with mode `0700`. - Open the file using protected flags and mode `0600`. - Reject symbolic links. - Write atomically through a protected temporary file followed by a same-filesystem rename. 3. Avoid storing duplicate `access_token` and `user_access_token` values. 4. Store refresh tokens only when offline access is genuinely required. 5. Remove token prefixes from console output. 6. Document token revocation and rotation procedures. 7. Add token files to source-control and package ignore rules. 8. Check expiration before use and implement controlled refresh-token rotation. ]]>

T03 · Remote Payload Retrieval and Execution

Error
Location
scripts/install_skill.py:23
Finding
Unpinned remote repository is cloned and its Python code is executed<![CDATA[ ## Vulnerability Details **File Location**: `scripts/install_skill.py:23-40`; execution path at `scripts/feishu_doc_cli.py:43-61` and `74-80` **Vulnerability Type**: Mutable remote payload and insecure supply chain **Risk Level**: High ### Vulnerable Code The installer clones a moving default branch without integrity verification: ```python def clone_repo(dest_path): """克隆技能仓库""" repo_url = "https://github.com/rosalynYANG/feishu-doc-creator-skill.git" print(f"[安装] 正在克隆技能仓库: {repo_url}") print(f"[安装] 目标目录: {dest_path}") if dest_path.exists(): print(f"[信息] 目录已存在,跳过克隆") return True try: result = subprocess.run( ["git", "clone", repo_url, str(dest_path)], capture_output=True, text=True, timeout=300 ) ``` The CLI later locates and executes Python from that checkout: ```python if (original_skill / "feishu-doc-orchestrator" / "scripts" / "orchestrator.py").exists(): orchestrator_script = original_skill / "feishu-doc-orchestrator" / "scripts" / "orchestrator.py" else: print("[错误] 原始技能文件未找到") print(f"请运行安装脚本: python {skill_root}/scripts/install_skill.py") return False cmd = [sys.executable, str(orchestrator_script), str(markdown_file)] if title: cmd.extend(["--title", title]) if doc_id: cmd.extend(["--doc-id", doc_id]) if verbose: cmd.append("--verbose") ``` ```python result = subprocess.run( cmd, env=env, capture_output=True, text=True, timeout=300 ) ``` ### Technical Analysis The installer retrieves the repository's current default branch without pinning an immutable commit, checking a release checksum, or verifying a signed tag. The effective code executed after installation can therefore differ from the code reviewed during this audit. The use of an argument-list subprocess avoids shell injection, but it does not address trust in the downloaded Python code. Once cloned, the remot ...[truncated 1480 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Vendor the reviewed source into the Skill package where feasible. 2. Otherwise, pin installation to an immutable full commit hash. 3. Distribute an expected archive checksum through a separately trusted release channel. 4. Prefer signed release tags and verify the signature before installation. 5. Refuse to execute if commit or checksum verification fails. 6. Record the verified source revision in installation metadata. 7. Use a locked dependency manifest with hashes for Python dependencies. 8. Do not replace reviewed local code automatically. 9. Consider running downloaded conversion components in a restricted environment with minimal filesystem access and a sanitized environment. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
original-skill/feishu-doc-orchestrator/scripts/orchestrator.py:85
Finding
Unvalidated workflow run name allows path traversal and writes outside the workflow directory<![CDATA[ ## Vulnerability Details **File Location**: `original-skill/feishu-doc-orchestrator/scripts/orchestrator.py:85-99` and `118-126`; related argument mismatch at `scripts/feishu_doc_cli.py:52-61` **Vulnerability Type**: Path traversal and unintended file creation or overwrite **Risk Level**: Medium ### Vulnerable Code The orchestrator accepts its third positional argument as a directory name: ```python # 运行名称(用于创建独立子文件夹) if len(sys.argv) >= 4: run_name = sys.argv[3] else: # 默认使用时间戳:run-YYYY-MM-DD-HHMMSS run_name = datetime.now().strftime("run-%Y-%m-%d-%H%M%S") # 工作流基础目录(在项目根目录下) project_root = Path(__file__).parent.parent.parent.parent # 上升到项目根目录 workflow_base_dir = project_root / "workflow" / "feishu-doc-runs" # 本次运行的工作流目录 workflow_dir = workflow_base_dir / run_name ``` It then creates and writes subdirectories without checking resolved containment: ```python step_dirs = { "parse": workflow_dir / "step1_parse", "create_with_permission": workflow_dir / "step2_create_with_permission", "add_blocks": workflow_dir / "step3_add_blocks", "verify": workflow_dir / "step4_verify" } for step_dir in step_dirs.values(): step_dir.mkdir(parents=True, exist_ok=True) ``` The wrapper passes incompatible option-style arguments to a positional parser: ```python cmd = [sys.executable, str(orchestrator_script), str(markdown_file)] if title: cmd.extend(["--title", title]) if doc_id: cmd.extend(["--doc-id", doc_id]) if verbose: cmd.append("--verbose") ``` ### Technical Analysis `pathlib.Path` does not automatically constrain a joined path to its intended parent. A value such as `../../target` remains capable of escaping `workflow/feishu-doc-runs` after path resolution. The orchestrator subsequently invokes several scripts that write predictable JSON and log files under the resulting directories. Existing files with the same names may be overwritten. The top-level wrapper and orchestrator also disagree about argument sy ...[truncated 1602 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Replace manual positional parsing with `argparse` in the orchestrator. 2. Make the wrapper and orchestrator use the same explicit options, such as: - `--input` - `--title` - `--doc-id` - `--run-name` 3. Generate run-directory names internally wherever possible. 4. If user-supplied run names are supported, allow only a conservative character set such as letters, digits, underscores, and hyphens. 5. Reject absolute paths, path separators, `.` components, and `..` components. 6. Resolve both the base and target paths and verify that the target remains beneath the base using `Path.relative_to`. 7. Avoid overwriting existing run directories; use exclusive creation or append a random identifier. 8. Add tests for absolute paths, traversal paths, symbolic-link escapes, and wrapper argument compatibility. ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
Findings (113)

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
92% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
94% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding
Cloning remote repositories, copying directories from workspace, creating files in the user's home directory, and performing interactive installation are materially different from converting Markdown to Feishu documents. These actions modify the local environment and can introduce supply-chain, persistence, or integrity risks if hidden behind a broadly described productivity skill.

Agent Config Directory Access

High
Category
Agent Snooping
Content
"""加载飞书配置"""
    config_path = Path(__file__).parent.parent.parent.parent / "feishu-config.env"
    if not config_path.exists():
        config_path = Path(".claude/feishu-config.env")

    config = {}
    if config_path.exists():
Confidence
95% confidence
Finding
The fallback access to `.claude/feishu-config.env` reaches into an agent/application config directory that may contain sensitive credentials outside the skill's own working data boundary. In a skill ecosystem, reading from agent config paths is high risk because it enables implicit secret harvesting and use of broader-scoped credentials without clear user intent.

Agent Config Directory Access

High
Category
Agent Snooping
Content
config_path = project_root / ".claude" / "feishu-config.env"

    if not config_path.exists():
        config_path = Path(".claude/feishu-config.env")

    config = {}
    if config_path.exists():
Confidence
90% confidence
Finding
The script explicitly reads from the agent configuration area (.claude/feishu-config.env), which is a sensitive directory likely to contain app secrets. In a skill context, access to agent-managed config is more dangerous because it crosses from document processing into credential retrieval, and could expose FEISHU_APP_SECRET or related secrets to any code path that reuses this helper.

Credential Access

High
Category
Privilege Escalation
Content
print("=" * 70)
        print("授权成功!")
        print("=" * 70)
        print(f"Access Token: {token_data['access_token'][:30]}...")
        print(f"有效期: {token_data['expires_at'] - int(time.time())} 秒")
        print(f"权限范围: {token_data['scope']}")
        print()
Confidence
92% confidence
Finding
The script prints the first 30 characters of the access token to stdout after successful authorization. Even partial credential disclosure is sensitive because terminal logs, shell history capture, CI logs, screen recordings, or shared consoles can leak reusable token material and aid token theft or correlation with other exposed data.

Agent Config Directory Access

High
Category
Agent Snooping
Content
project_root = Path(__file__).parent.parent.parent.parent.parent
    config_path = project_root / ".claude" / "feishu-config.env"
    if not config_path.exists():
        config_path = Path(".claude/feishu-config.env")

    config = {}
    if config_path.exists():
Confidence
94% confidence
Finding
The script accesses files under the agent's .claude directory to read configuration and later reads stored tokens from .claude/feishu-token.json. In an agent-skill setting, access to the agent config directory is sensitive because it may expose secrets and account credentials beyond the immediate task, and the skill uses those secrets to perform authenticated actions against an external service.

Agent Config Directory Access

High
Category
Agent Snooping
Content
"""加载飞书配置"""
    config_path = Path(__file__).parent.parent.parent.parent / "feishu-config.env"
    if not config_path.exists():
        config_path = Path(".claude/feishu-config.env")

    config = {}
    if config_path.exists():
Confidence
93% confidence
Finding
The fallback read from .claude/feishu-config.env accesses the agent configuration area, which commonly stores sensitive tokens and secrets outside the skill's own declared inputs. In a skill ecosystem, reaching into agent config directories is dangerous because it broadens secret access and may bypass normal consent and scoping expectations.

Tool Parameter Abuse

High
Category
Tool Misuse
Content
如果需要重新登录(如登录过期):
```bash
# 删除登录状态
rm -rf .claude/playwright_state

# 再次运行验证器,会提示重新扫码
python .claude/skills/feishu-doc-verifier/scripts/doc_verifier.py <doc_info.json>
Confidence
85% confidence
Finding
Tool parameters are crafted to achieve unintended or unsafe behavior. Parameter abuse can bypass intended safety checks (e.g. shell=True, --force, dangerous glob patterns).

Agent Config Directory Access

High
Category
Agent Snooping
Content
project_root = Path(__file__).parent.parent.parent.parent
    config_path = project_root / ".claude" / "feishu-config.env"
    if not config_path.exists():
        config_path = Path(".claude/feishu-config.env")

    config = {}
    if config_path.exists():
Confidence
91% confidence
Finding
The script reads secrets and tokens from the agent's .claude directory, including app credentials and user access tokens, which are highly sensitive. In a skill environment, accessing agent-local config/token stores increases the blast radius: if the skill is triggered unexpectedly or repurposed, it can use standing credentials to modify external resources without fresh user authorization.

Description-Behavior Mismatch

High
Confidence
97% confidence
Finding
This script can transfer ownership of an existing Feishu document to another user, which goes beyond the stated skill purpose of Markdown-to-document conversion and collaborative document creation. In an agent/skill context, this is sensitive privilege-changing behavior that could reassign control of user content if invoked on arbitrary document IDs, especially since the script accepts target IDs directly from CLI input and performs no authorization or scope checks tied to user intent.

Env Variable Harvesting

High
Category
Data Exfiltration
Content
cmd.append("--verbose")
    
    # 设置环境变量
    env = os.environ.copy()
    config_file = load_config()
    if config_file:
        # 设置配置路径环境变量
Confidence
60% confidence
Finding
Code enumerates, copies, or searches environment variables for secrets. Bulk environment access can collect credentials unrelated to the skill's stated purpose.

Env Variable Harvesting

High
Category
Data Exfiltration
Content
cmd.append("--verbose")
    
    # 设置环境变量
    env = os.environ.copy()
    config_file = load_config()
    if config_file:
        # 设置配置路径环境变量
Confidence
60% confidence
Finding
Code enumerates, copies, or searches environment variables for secrets. Bulk environment access can collect credentials unrelated to the skill's stated purpose.

Description-Behavior Mismatch

High
Confidence
98% confidence
Finding
The manifest describes a skill for converting Markdown into Feishu documents with block and permission support, but this file contains a fully authored UI/UX design specification for an "AgentForge" web interface, including design system, component lists, and export recommendations. That behavior/content is semantically different from Markdown conversion and suggests the skill is being used to generate unrelated design deliverables rather than orchestrating Feishu document creation.

Lp3

Medium
Category
MCP Least Privilege
Confidence
93% confidence
Finding
The skill advertises significant capabilities involving environment access, file I/O, shell execution, and network calls, but it does not declare any tool scope or permission boundaries. This weakens user and platform visibility into what the skill can do and increases the risk of over-privileged execution, especially because the workflow handles secrets and remote APIs.

Vague Triggers

Medium
Confidence
89% confidence
Finding
The activation language is broad enough to match general document-sharing or collaboration requests, which can cause the skill to run in situations beyond its safe intended scope. Given the presence of credential, permission, filesystem, and network capabilities, overbroad auto-invocation increases the chance of unnecessary privileged actions.

Vague Triggers

Medium
Confidence
92% confidence
Finding
Ambiguous trigger conditions without negative examples make it harder for the agent to distinguish between safe conversion requests and broader document-related tasks. In this context, that ambiguity is dangerous because the skill appears capable of authentication, permission changes, local writes, and network activity that should not be auto-triggered casually.