other
- Location
core/analyzer/task_analyzer.py:14- Finding
Undisclosed Transmission of Private DingTalk Communications to a Third-Party AI Service
- Content
View full analysis
- Remediation
View remediation
Security audit
Security checks for vulnerabilities and agentic risk
The skill matches its work-assistant purpose, but it needs Review because it collects sensitive workplace chats and task data, sends raw DingTalk content to an undeclared third-party AI endpoint, includes live-looking credentials, and installs scheduled automation.
Install only after removing and rotating the shipped credentials, replacing config.yaml with placeholders, approving the LLM provider and endpoint, adding explicit consent/redaction for DingTalk group and DM content, disabling or scoping direct-message collection by default, and documenting how to remove the cron job and purge the SQLite ledger.
core/analyzer/task_analyzer.py:14Undisclosed Transmission of Private DingTalk Communications to a Third-Party AI Service
core/analyzer/task_analyzer.py:14Hard-Coded Third-Party AI API Key
config.yaml:37Plaintext Teambition Bearer Token Distributed in Configuration
core/storage/task_ledger.py:7Indefinite Plaintext Retention of Sensitive Work Data in SQLite
scripts/run_daily_assistant.sh:17Predictable Shared Temporary Lock File Permits Local Interference
The documented purpose does not match the detected behavior: the finding indicates outbound transmission of DingTalk message content and user identifiers to an undeclared third-party LLM service, while core advertised functions are not clearly represented. Undisclosed exfiltration of private work communications and identifiers is dangerous because users may consent to a task assistant but not to external sharing of sensitive chats, creating privacy, compliance, and data leakage risk.
This configuration enables broad monitoring of group chats, @all notices, direct messages, and Teambition tasks, then aggregates and forwards them into a daily report. That creates a real data-minimization and confidentiality risk because private and potentially sensitive workplace communications are centrally collected, persisted in a task ledger, and retransmitted to another channel, increasing exposure and the blast radius of any compromise or misdelivery.
The code transmits raw DingTalk group chats, @mentions, and private messages to an external LLM endpoint, which exposes potentially sensitive workplace communications to a third party. In this skill context, the data includes persistent task tracking, direct messages, and internal project discussions, so the external transfer materially increases confidentiality and compliance risk.
The network call sends user chat content off-box without any visible notice, consent flow, or disclosure to the user. Because the skill aggregates workplace conversations including private chats and @all announcements, silent export to an external service can violate user expectations, internal policy, and privacy obligations.
The skill advertises capabilities that require file, network, and shell access but does not declare any explicit tool scope or permissions boundary. This creates an avoidable trust gap: operators cannot tell what the skill is allowed to do, and broad undeclared capabilities increase the risk of over-privileged execution or misuse during installation and runtime.
The skill description promotes broad monitoring of group chats, direct messages, @mentions, @all notices, task data, and token-based integrations without a clear warning about the sensitivity of the collected information. In this context, omission is security-relevant because users may enable surveillance-like collection of private and workplace communications without understanding the scope, retention, and downstream processing risks.
The setup instructions tell users to install a cron job but do not warn that this creates ongoing scheduled collection, analysis, storage, and outbound delivery of workplace communications and reports. Hidden persistence and automation materially increase risk because monitoring continues after initial setup and may keep transmitting sensitive information without the user appreciating the continuous nature of the behavior.
The natural-language content in this config is written exclusively in Chinese, including operational comments that define behavior, without any indication that language choice is configurable or intentionally limited to a specific audience. This can violate language/locale policy when a skill implicitly forces one language without user opt-in or documented regional justification.
The manifest ignores groups based only on generic keywords such as "通知", "监控", and "打卡", which are common terms that can appear in many ordinary group names. Because no scope constraints or negative examples are provided, these broad triggers may unintentionally exclude relevant groups.
The default system prompt is hard-coded in Chinese and instructs the model to behave as a Chinese-language assistant. This imposes a specific language/locale choice without offering the user a language preference or documenting that the skill is intentionally region-specific.
A live API key is hardcoded directly in source code, creating a credential exposure risk if the repository, logs, or deployment artifacts are accessed by unauthorized parties. An exposed key can be reused to access the external LLM service, incur cost, and potentially retrieve or submit sensitive data under the organization's account.
The outbound requests.post call is the concrete mechanism used to exfiltrate collected DingTalk message data to an external host. In this assistant, that transmission is especially sensitive because the payload includes direct messages, mentions, and internal work coordination, amplifying privacy and data-governance risk.
}
try:
resp = requests.post(api_url, headers=headers, json=payload, timeout=45)
if resp.status_code == 200:
res_data = resp.json()
content = res_data['choices'][0]['message']['content']
subprocess module calls execute external commands. Without careful input validation, this enables command injection.
self.direct_messages_cfg = self.rules.get('direct_messages', {})
def _run_dws_cmd(self, cmd_args):
p = subprocess.Popen(cmd_args, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
out, err = p.communicate()
try:
return json.loads(out.decode('utf-8', errors='ignore'))
This collector intentionally aggregates private messages, @mentions, and group chat content across potentially multiple profiles, but the code contains no access control, consent check, minimization, or user-facing disclosure at the collection point. In the context of a personal work assistant that persistently tracks unfinished items and pushes summaries to DingTalk, this materially increases privacy and data leakage risk because sensitive chat content may be harvested and reprocessed beyond the original conversation scope.
This code constructs an authenticated HTTP request using a bearer token and organization identifier, transmitting credential-backed data to an external service. While the network call is core to the collector's purpose, there is no docstring, comment, or user-facing notice disclosing that stored credentials and task metadata are sent to Teambition.
The docstring states the report should be generated as a Chinese personal morning report, and the rest of the function emits fixed Chinese headings and labels. This is a natural-language locale policy issue because the skill enforces a specific language without offering user opt-in or documenting that it is intentionally region-specific.
The code serializes and stores raw task metadata verbatim in the raw_data column, which can include sensitive chat content, identifiers, or other source-system metadata beyond what is needed for reporting. In this skill's context—aggregating DingTalk messages, @all notices, DMs, and Teambition tasks—persistent raw storage increases privacy exposure and the blast radius of local compromise or accidental disclosure.
The script interactively collects a Teambition user token and writes it directly into config.yaml, but it does not warn the user that the credential will be stored in plaintext on disk. In the context of a personal work assistant that aggregates enterprise chat and task data, compromise of this file could expose organizational data and enable unauthorized API access.
The script’s natural-language comments describe behavior specifically around Chinese legal holidays and use only Chinese-language user-facing descriptions. This indicates a locale-specific assumption without any visible opt-in, user choice, or documented justification that the skill is intended only for a China-specific context.
This pipeline automatically transmits a generated report containing aggregated Teambition tasks, group chat content, @mentions, and direct messages to an external DingTalk recipient without an approval gate or content-sensitivity check in this file. In this skill's context, the report likely contains internal business data and private communications, so misconfiguration of target_user_id or unintended execution can cause significant confidentiality leakage.
subprocess module calls execute external commands. Without careful input validation, this enables command injection.
'--target', target_user,
'--message', report_md
]
subprocess.run(cmd)
print(f"✅ 日报已推送至钉钉目标: {target_user}")
# 标记公告为已播报
This script establishes persistence by installing a weekday cron job that will automatically execute another script. In an agent skill context, unattended scheduled execution increases risk because it creates ongoing behavior after setup and can repeatedly process work messages and push reports without additional user approval; if the referenced script is modified or abused later, the persistence mechanism will keep invoking it.
CRON_JOB="0 10 * * 1-5 $SCRIPT_PATH > /dev/null 2>&1"
# 检查是否已存在
if crontab -l 2>/dev/null | grep -Fq "$SCRIPT_PATH"; then
echo "⚠️ 定时任务已存在,无需重复添加。"
else
(crontab -l 2>/dev/null; echo "$CRON_JOB") | crontab -
The command appends a new cron entry to the user's crontab, creating durable scheduled execution. While this appears intended for legitimate automation, persistence is security-relevant because it survives the initial run and can be leveraged to continuously run code, making any compromise of run_daily_assistant.sh or its dependencies recurring and harder for users to notice.
if crontab -l 2>/dev/null | grep -Fq "$SCRIPT_PATH"; then
echo "⚠️ 定时任务已存在,无需重复添加。"
else
(crontab -l 2>/dev/null; echo "$CRON_JOB") | crontab -
echo "✅ 已成功添加工作日 10:00 定时晨报任务 (Crontab)!"
fi
The comments and descriptive labels in the template are Chinese-only, which can impose a language expectation without any visible opt-in or stated regional limitation. Under the language/locale policy, forcing a specific language without documenting user choice or a justified locale constraint can be a policy concern.
This code creates a local database directory and initializes persistent storage for task details, announcements, and raw metadata. The file contains no confirmation prompt, logging, or user-facing notice that user/project data will be stored on disk, which can matter for privacy and data-retention expectations.
Detected: suspicious.exposed_secret_literal