T09 · Insecure Skill Coding Practices
- Location
references/generated-config-store.md:25- Finding
Midea Cloud Credentials Are Persisted in Plaintext with Unrestricted Default File Permissions
- Content
View full analysis
Vulnerability Details
File Location:
references/generated-config-store.md:25-28andreferences/generated-midea-skill-cli.md:62-67
Vulnerability Type: Plaintext sensitive-data storage
Risk Level: HighVulnerable Code
references/generated-config-store.md:25-28:python def save_config(data: dict[str, Any]) -> Path: ensure_dir() CONFIG_PATH.write_text(json.dumps(data, ensure_ascii=False, indent=2), encoding="utf-8") return CONFIG_PATHreferences/generated-midea-skill-cli.md:62-67:python path = save_config({ "account": account, "password": password, "cloud_name": cloud_name, "devices": devices, })Technical Analysis
The generated CLI passes the user's Midea account and password directly to
save_config(). The configuration store serializes the complete dictionary into unencrypted JSON at~/.openclaw/midea-cloud-control/config.json.The file is written using
Path.write_text()without explicitly enforcing owner-only permissions. Its effective permissions therefore depend on the host's umask and any permissions already present on the file. In a shared, misconfigured, backed-up, or compromised environment, another local principal or process may be able to read the password.Encryption at rest alone would not prevent access by a process running as the same user. An operating-system credential manager or dedicated secret service is the preferred storage mechanism.
Attack Path
- A user invokes the account connection workflow and supplies valid Midea credentials.
connect()creates a configuration dictionary containing the plaintext account and password.save_config()serializes that dictionary to~/.openclaw/midea-cloud-control/config.json.- A local process, another user permitted by the resulting filesystem permissions, a backup reader, or malware running in the user's context reads the ...[truncated 672 chars]
- Remediation
View remediation
Remediation Suggestions
- Store the password in the operating system's credential manager, keyring, or another dedicated secret-management service. Persist only a credential reference in
config.json. - If file-based storage is unavoidable, create
~/.openclaw/midea-cloud-controlwith mode0700and atomically create the configuration file with mode0600. - Validate and correct permissions on an existing directory and file before reading or updating credentials.
- Avoid following symbolic links when creating or replacing the configuration file, and use an atomic temporary-file-and-rename operation in the same protected directory.
- Document how users can delete the cached secret and revoke or rotate credentials after suspected exposure.
- Minimize retained data and avoid storing the password when a renewable token or similarly scoped credential is supported.
- Store the password in the operating system's credential manager, keyring, or another dedicated secret-management service. Persist only a credential reference in
