Security checks for vulnerabilities and agentic risk
Overview
This skill is a disclosed Grandet price lookup and connector with sensitive optional install/configuration features that are scoped, user-directed, and reversible.
Install this only if you want Grandet to look up API pricing and, when asked, help connect a selected provider to your agent app. Review the exact config diff before applying, keep the backups, avoid sharing API keys in chat, and use --no-telemetry or GRANDET_INSTALL_TELEMETRY=0 if you do not want installation receipts sent.
The skill is presented primarily as a price-comparison assistant, but it also contains installer, uninstaller, config-editing, persistence, recovery, and telemetry behaviors. This mismatch can mislead users or orchestrators into granting broader trust than warranted, making sensitive local changes or outbound reporting more likely to occur under the guise of a benign lookup skill.
Content
No source excerpt is available for this finding.
Ae1
High
Category
analysis-evasion
Confidence
100% confidence
Finding
Referenced artifact was not completely inspected
Content
Scanner excerpt · SKILL.md (reported line 59)May include surrounding context.
md
nCode: `~/.agents/skills/`. The bundled installer does the same move with `node scripts/install-price-finder.mjs --app <app> --uninstall`. Other apps and exact
Ae1
High
Category
analysis-evasion
Confidence
100% confidence
Finding
Referenced artifact was not completely inspected
Content
Scanner excerpt · SKILL.md (reported line 70)May include surrounding context.
md
nCode: `~/.agents/skills/`. The bundled installer does the same move with `node scripts/install-price-finder.mjs --app <app> --uninstall`. Other apps and exact
Ae1
High
Category
analysis-evasion
Confidence
100% confidence
Finding
Referenced artifact was not completely inspected
Content
Scanner excerpt · SKILL.md (reported line 69)May include surrounding context.
md
- **Connecting an offer changes which model API an app uses.** `scripts/connect.mjs` edits that app's model-provider settings and can change its default model,
Ae1
High
Category
analysis-evasion
Confidence
100% confidence
Finding
Referenced artifact was not completely inspected
Content
Scanner excerpt · SKILL.md (reported line 117)May include surrounding context.
md
- **Connecting an offer changes which model API an app uses.** `scripts/connect.mjs` edits that app's model-provider settings and can change its default model,
Agent Config Directory Access
High
Category
Agent Snooping
Confidence
90% confidence
Finding
The skill includes editing ~/.continue/config.yaml, another persistent agent/application configuration target. Such access can establish long-lived changes to provider endpoints and credentials handling, which raises the impact of any mistake, abuse, or supply-chain compromise in the skill.
Content
Scanner excerpt · SKILL.md (reported line 69)May include surrounding context.
md
Price, free-credit and quality lookups only read from grandet.ai and change nothing on the computer; when this Skill loads on its own, that is all it does. Two optional parts write to the computer. Run them only when the user asked for them in this conversation, and write only after the user confirms the change you showed:
- **Connecting an offer changes which model API an app uses.** `scripts/connect.mjs` edits that app's model-provider settings and can change its default model, so the app's later sessions send their requests, and spend credit, at the chosen site: Codex `~/.codex/config.toml`, Claude Code `~/.claude/settings.json`, OpenCode `~/.config/opencode/opencode.json(c)`, Kilo Code `~/.config/kilo/kilo.json(c)`, Continue `~/.continue/config.yaml`, Gemini CLI `~/.env`, Hermes `~/.hermes/config.yaml` (Windows: `%LOCALAPPDATA%\hermes\config.yaml`), OpenClaw `~/.openclaw/openclaw.json`. It keeps a backup next to each file and records the change in `~/.grandet/connect/state.json`. The key the user types goes to `~/.grandet/keys/<site>`, readable by the user only. Continue and Gemini CLI also hold it in their config file, which then becomes readable by the user only. Codex gets a shell-profile line that reads the key file; on Windows, Codex, Claude Code and Hermes get a user environment variable. `connect.mjs restore` (the user says "恢复" or "undo") puts every file back as it was.
- **Installing makes this Skill load in later conversations.** `scripts/install-price-finder.mjs` and `scripts/verify-installation.py` copy the Skill into an app's user-level skill folder (for example `~/.agents/skills` or `~/.claude/skills`) and send an installation receipt to grandet.ai with random IDs, the version and the content hash, never paths, accounts, chats or keys. `--no-telemetry` or `GRANDET_INSTALL_TELEMETRY=0` turns the receipt off. Uninstalling moves the folder out again, as in "Uninstall or install this Skill".
## Always
Agent Config Directory Access
High
Category
Agent Snooping
Confidence
90% confidence
Finding
The skill includes editing ~/.continue/config.yaml, another persistent agent/application configuration target. Such access can establish long-lived changes to provider endpoints and credentials handling, which raises the impact of any mistake, abuse, or supply-chain compromise in the skill.
Content
Scanner excerpt · SKILL.md (reported line 69)May include surrounding context.
md
Price, free-credit and quality lookups only read from grandet.ai and change nothing on the computer; when this Skill loads on its own, that is all it does. Two optional parts write to the computer. Run them only when the user asked for them in this conversation, and write only after the user confirms the change you showed:
- **Connecting an offer changes which model API an app uses.** `scripts/connect.mjs` edits that app's model-provider settings and can change its default model, so the app's later sessions send their requests, and spend credit, at the chosen site: Codex `~/.codex/config.toml`, Claude Code `~/.claude/settings.json`, OpenCode `~/.config/opencode/opencode.json(c)`, Kilo Code `~/.config/kilo/kilo.json(c)`, Continue `~/.continue/config.yaml`, Gemini CLI `~/.env`, Hermes `~/.hermes/config.yaml` (Windows: `%LOCALAPPDATA%\hermes\config.yaml`), OpenClaw `~/.openclaw/openclaw.json`. It keeps a backup next to each file and records the change in `~/.grandet/connect/state.json`. The key the user types goes to `~/.grandet/keys/<site>`, readable by the user only. Continue and Gemini CLI also hold it in their config file, which then becomes readable by the user only. Codex gets a shell-profile line that reads the key file; on Windows, Codex, Claude Code and Hermes get a user environment variable. `connect.mjs restore` (the user says "恢复" or "undo") puts every file back as it was.
- **Installing makes this Skill load in later conversations.** `scripts/install-price-finder.mjs` and `scripts/verify-installation.py` copy the Skill into an app's user-level skill folder (for example `~/.agents/skills` or `~/.claude/skills`) and send an installation receipt to grandet.ai with random IDs, the version and the content hash, never paths, accounts, chats or keys. `--no-telemetry` or `GRANDET_INSTALL_TELEMETRY=0` turns the receipt off. Uninstalling moves the folder out again, as in "Uninstall or install this Skill".
## Always
Agent Config Directory Access
High
Category
Agent Snooping
Confidence
90% confidence
Finding
The skill includes editing ~/.continue/config.yaml, another persistent agent/application configuration target. Such access can establish long-lived changes to provider endpoints and credentials handling, which raises the impact of any mistake, abuse, or supply-chain compromise in the skill.
Content
Scanner excerpt · SKILL.md (reported line 69)May include surrounding context.
md
Price, free-credit and quality lookups only read from grandet.ai and change nothing on the computer; when this Skill loads on its own, that is all it does. Two optional parts write to the computer. Run them only when the user asked for them in this conversation, and write only after the user confirms the change you showed:
- **Connecting an offer changes which model API an app uses.** `scripts/connect.mjs` edits that app's model-provider settings and can change its default model, so the app's later sessions send their requests, and spend credit, at the chosen site: Codex `~/.codex/config.toml`, Claude Code `~/.claude/settings.json`, OpenCode `~/.config/opencode/opencode.json(c)`, Kilo Code `~/.config/kilo/kilo.json(c)`, Continue `~/.continue/config.yaml`, Gemini CLI `~/.env`, Hermes `~/.hermes/config.yaml` (Windows: `%LOCALAPPDATA%\hermes\config.yaml`), OpenClaw `~/.openclaw/openclaw.json`. It keeps a backup next to each file and records the change in `~/.grandet/connect/state.json`. The key the user types goes to `~/.grandet/keys/<site>`, readable by the user only. Continue and Gemini CLI also hold it in their config file, which then becomes readable by the user only. Codex gets a shell-profile line that reads the key file; on Windows, Codex, Claude Code and Hermes get a user environment variable. `connect.mjs restore` (the user says "恢复" or "undo") puts every file back as it was.
- **Installing makes this Skill load in later conversations.** `scripts/install-price-finder.mjs` and `scripts/verify-installation.py` copy the Skill into an app's user-level skill folder (for example `~/.agents/skills` or `~/.claude/skills`) and send an installation receipt to grandet.ai with random IDs, the version and the content hash, never paths, accounts, chats or keys. `--no-telemetry` or `GRANDET_INSTALL_TELEMETRY=0` turns the receipt off. Uninstalling moves the folder out again, as in "Uninstall or install this Skill".
## Always
Agent Config Directory Access
High
Category
Agent Snooping
Confidence
94% confidence
Finding
The skill explicitly targets sensitive agent configuration under ~/.codex/config.toml and instructs changes that control provider, base URL, and model defaults. Accessing and rewriting agent config is security-relevant because it can redirect future requests and persist altered behavior across sessions.
Content
Scanner excerpt · references/host-setup.md (reported line 93)May include surrounding context.
For every file: read the current content, show the user the exact lines you will add or change, copy the file to <file>.grandet-backup-<YYYYMMDD-HHMMSS>, and write only after the user confirms. Keep every other setting. Use a provider ID made from the site (for example apijing). On Windows, ~ is %USERPROFILE%.
The instructions modify ~/.claude/settings.json, including base URL and model environment overrides plus a helper that reads a local key file. That affects how a security-sensitive coding agent authenticates and where it sends prompts, making misdirection or accidental data routing plausible.
Content
Scanner excerpt · references/host-setup.md (reported line 106)May include surrounding context.
env_key = ""
text
**Claude Code** (`anthropic`) — `~/.claude/settings.json`, merged into the existing JSON:
```json
{
Agent Config Directory Access
High
Category
Agent Snooping
Confidence
90% confidence
Finding
The Continue instructions direct edits to ~/.continue/config.yaml and explicitly normalize putting an API key placeholder into a persistent config file. Even though the user is asked to fill it manually, this encourages risky secret placement and modifies agent behavior outside the skill's stated role.
Content
Scanner excerpt · references/host-setup.md (reported line 136)May include surrounding context.
Use "npm": "@ai-sdk/openai" instead when connecting through openai-response.
Continue — add one entry to models in ~/.continue/config.yaml; Continue keeps the key in this file, so write the placeholder and ask the user to replace it themselves:
yaml
- name: <site> <modelName>
Tool Parameter Abuse
High
Category
Tool Misuse
Confidence
60% 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).
Content
Scanner excerpt · references/host-setup.md (reported line 194)May include surrounding context.
macOS / Linux:
sh
f=$(mktemp) && printf 'header = "Authorization: Bearer %s"\n' "$(cat ~/.grandet/keys/<site>)" | curl -sS -K - -o "$f" -w '%{http_code}\n' '<origin>/v1/models'; python3 -c 'import json,sys; print(sys.argv[2] in [m.get("id") for m in json.load(open(sys.argv[1])).get("data", [])])' "$f" '<modelName>'; rm -f "$f"
The key goes to curl through standard input, so it never appears in the command line or the process list. Never write a key into a curl argument, a URL or a command you show in chat.
Chaining Abuse
High
Category
Tool Misuse
Confidence
75% confidence
Finding
Tool calls are chained to bypass individual safety checks or escalate capabilities beyond what any single tool call would allow.
Content
Scanner excerpt · references/host-setup.md (reported line 194)May include surrounding context.
macOS / Linux:
sh
f=$(mktemp) && printf 'header = "Authorization: Bearer %s"\n' "$(cat ~/.grandet/keys/<site>)" | curl -sS -K - -o "$f" -w '%{http_code}\n' '<origin>/v1/models'; python3 -c 'import json,sys; print(sys.argv[2] in [m.get("id") for m in json.load(open(sys.argv[1])).get("data", [])])' "$f" '<modelName>'; rm -f "$f"
The key goes to curl through standard input, so it never appears in the command line or the process list. Never write a key into a curl argument, a URL or a command you show in chat.
Context-Inappropriate Capability
High
Category
Not specified by scanner
Confidence
98% confidence
Finding
The guide tells users to download, extract, and execute a remote archive from GitHub or a mirror, then run local Node scripts that can modify files and manage keys. Supplying copy-pasteable remote-code execution steps inside a skill is highly dangerous because it shifts trust to an external artifact that can change, be replaced, or be mirrored with weaker guarantees.
Content
No source excerpt is available for this finding.
External Script Fetching
High
Category
Supply Chain
Confidence
90% confidence
Finding
Remote code is downloaded and executed. This bypasses code review and could introduce malicious code.
Content
Scanner excerpt · references/http-fallback.md (reported line 38)May include surrounding context.
Add an explicit user protocol/profile and optional currency when known. A multi-protocol target needs no profile question. A profile/endpoint conflict returns 400; targets with inference profiles also reject a protocol outside that set. Known platforms must match the profile's declaration. An explicit target with inference profiles unsupported on the selected OS cannot be bypassed with endpointType: it returns TARGET_APP_PLATFORM_MISMATCH. Correct only from the user's actual requirements, never by dropping a target or platform. Apps without inference profiles, including current Cursor/Windsurf definitions and unlisted safe app IDs, proceed without a protocol question as PRICE_ONLY_UNVERIFIED_APP_ROUTE; return the price choice with unverified app compatibility. A user-specified endpointType instead yields EXPLICIT_PROTOCOL_UNVERIFIED_APP_ROUTE with a generic protocol card and null profileId. The same flag marks a legacy client protocol override outside its declared app routes; neither proves app integration.
External Script Fetching
High
Category
Supply Chain
Confidence
90% confidence
Finding
Remote code is downloaded and executed. This bypasses code review and could introduce malicious code.
Content
Scanner excerpt · references/http-fallback.md (reported line 81)May include surrounding context.
GET https://grandet.ai/api/v1/free-credits with q, kind (official, relay or all), userCanMeet (any, no_card, student), lang, page, limit (at most 20), host, targetApp, skillVersion, skillBuild. Same as MCP grandet_find_free_credits. Read it as in free credits; follow pagination for more pages.
Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.
Content
Scanner excerpt · scripts/connect.mjs (reported line 370)May include surrounding context.
js
if (o.group) steps.push(`On ${o.site}, create the token in group 「${o.group}」.`);
const keyCommand = `node "${SELF}" key --app ${o.app} --site ${o.site}${o.home === resolve(homedir()) ? '' : ` --home "${o.home}"`}`;
steps.push(`The user stores the key in their own terminal: ${keyCommand}`);
if (o.app === 'gemini-cli') notes.push('Gemini CLI reads ~/.env only when the working folder and its parents have no .env of their own');
if (o.app === 'codex' && o.platform !== 'win32') notes.push('Codex reads the key from an environment variable; open a new terminal after storing the key');
if (o.app === 'hermes') notes.push(o.platform === 'win32' ? 'Hermes reads the key from a user environment variable; restart Hermes after storing the key' : 'Hermes reads the key file through key_cmd; restart Hermes after storing the key');
if (o.app === 'openclaw') notes.push(`OpenClaw reads the key from ${o.keyPath} (a file SecretRef); restart the OpenClaw gateway after storing the key`);
Tool Parameter Abuse
High
Category
Tool Misuse
Confidence
80% 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).
Content
Scanner excerpt · scripts/connect.mjs (reported line 397)May include surrounding context.
js
async function loadState(home) { const t = await readText(statePath(home)); return t ? JSON.parse(t) : { schema: 'grandet.connect-state/v1', changes: [] }; }
async function saveState(home, state) { await atomicWrite(statePath(home), `${JSON.stringify(state, null, 2)}\n`); }
// The replacement keeps the permissions of the file it replaces unless a mode is given, so a config the user
// locked down (chmod 600) stays locked. writeFile's mode is filtered by the umask, so it is set explicitly.
async function atomicWrite(path, text, mode) {
await mkdir(dirname(path), { recursive: true });
const keep = mode ?? await stat(path).then((s) => s.mode & 0o777, () => undefined);
Description-Behavior Mismatch
High
Category
Not specified by scanner
Confidence
97% confidence
Finding
The module hard-codes a remote telemetry endpoint and explicitly describes installation-event transmission, which is unrelated to the skill’s stated price-finder purpose. Even though the payload is limited and there is an opt-out, this creates undisclosed outbound data flow and remote event reporting capability in a context where users would not expect networked installation tracking.
Content
No source excerpt is available for this finding.
Context-Inappropriate Capability
High
Category
Not specified by scanner
Confidence
97% confidence
Finding
This code implements a full telemetry state machine: local state persistence, event journaling, retry logic, and external uploads. In a skill whose declared function is answering API price questions, that hidden installation tracking capability is dangerous because it expands the trust boundary, enables ongoing outbound communication, and could be repurposed for broader data collection or covert signaling in future changes.
Content
No source excerpt is available for this finding.
Description-Behavior Mismatch
High
Category
Not specified by scanner
Confidence
98% confidence
Finding
This script performs installation, persistence, and telemetry delivery to a remote Grandet endpoint even though the skill is described as an API-price lookup utility. The telemetry includes persistent installation and event identifiers, content hashes, host/scope/source metadata, and timestamps, which are unrelated to the skill’s user-facing purpose and create undisclosed network-capable behavior in a context where users would not reasonably expect it.
Content
No source excerpt is available for this finding.
Context-Inappropriate Capability
High
Category
Not specified by scanner
Confidence
99% confidence
Finding
The code POSTs installation metadata to a remote service, including stable installation identifiers, event identifiers, version, content SHA-256, host classification, scope, operation, and timestamps. Even if the data is not secret in isolation, it enables tracking of installations and environments across time and is unrelated to the advertised API pricing functionality, making it an unjustified exfiltration channel.
Content
No source excerpt is available for this finding.
Ssd 4
Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding
The instructions explicitly tell the agent to perform the whole setup itself, avoid handing commands or paths to the user, and only stop for narrowly defined approval moments. That pushes the agent toward autonomous installation, filesystem changes, downloads, and enabling persistent capabilities with reduced user visibility, which is dangerous because it normalizes privileged actions without granular consent.
Content
No source excerpt is available for this finding.
Skill Enumeration
Medium
Category
Agent Snooping
Confidence
80% confidence
Finding
Skill enumerates or reads other installed skills. Access to other skills' SKILL.md files or the skills directory reveals prompt instructions, capabilities, and secrets that should be invisible to peer skills.
Content
Scanner excerpt · INSTALL.md (reported line 33)May include surrounding context.
md
You need the complete `grandet-api-price-finder` folder: `SKILL.md`, `references/` and `agents/`. `SKILL.md` alone is not enough.
- If a package, checkout or cached copy is already present and the `Installation build` line at the end of its `SKILL.md` names `grandet-skill-0.3.0-build.20261017`, reuse it without re-downloading. A copy that names an older build is out of date: download this build instead. In this repository or the extracted ZIP, the folder is at [`skills/grandet-api-price-finder/`](https://github.com/hanzohanzhe/Grandet/blob/main/skills/grandet-api-price-finder/SKILL.md).
- Otherwise download and extract the [installation ZIP](https://github.com/hanzohanzhe/Grandet/releases/download/skill-v0.3.0-build.20261017/grandet-api-price-finder-0.3.0.zip) from this repository.
- **Mainland China, or when the GitHub download is slow or fails:** download the same kit from Tencent SkillHub instead, no account needed: [SkillHub download](https://api.skillhub.cn/api/v1/download?slug=grandet-api-price-finder&version=0.3.0-build.20261017.0). It holds the `.skill` contents with the files at the archive root (plus SkillHub's own `_meta.json`). Extract it into a new folder named `grandet-api-price-finder` and use that folder as an extracted `.skill` root below, with `--receipt-source release_skill`. A 404 means SkillHub is still reviewing this build; then use GitHub.