T09 · Insecure Skill Coding Practices
- Location
SKILL.md:385- Finding
Unsanitized Username Allows Path Traversal During User Creation
- Content
View full analysis
- Remediation
View remediation
Security audit
Security checks for vulnerabilities and agentic risk
The skill is purpose-aligned for authentication, but it handles credentials and account authority in a shared local filesystem with concrete authorization and path-safety flaws.
Review before installing. This skill is not showing exfiltration or deception, but it would become a security foundation for users, sessions, credentials, and client access. Require username/path validation, consistent OPENCLAW_DATA_DIR path handling, senior approval for government submissions, explicit confirmation for disruptive admin actions, and strong filesystem isolation before relying on it.
SKILL.md:385Unsanitized Username Allows Path Traversal During User Creation
SKILL.md:194Authorization Policy Allows Accountants to Bypass Required Senior Approval for Government Submissions
Tool calls are chained to bypass individual safety checks or escalate capabilities beyond what any single tool call would allow.
export OPENCLAW_DATA_DIR="/data"
which jq openssl || sudo apt install jq openssl
mkdir -p $OPENCLAW_DATA_DIR/auth
chmod 700 $OPENCLAW_DATA_DIR/auth
The skill explicitly documents local storage of credential material in a shared file-system environment where other skills may have access. Even with hashed passwords, exposing credentials.json paths and relying on shared local files increases the risk of offline password cracking, credential tampering, and unauthorized account manipulation if filesystem isolation fails or is misconfigured.
Auth_File_Structure:
user_data:
- /data/auth/users/{username}/profile.json
- /data/auth/users/{username}/credentials.json
- /data/auth/users/{username}/permissions.json
- /data/auth/users/{username}/sessions/
- /data/auth/users/{username}/2fa/
The code writes credential hashes directly to credentials.json under a predictable shared path. In the stated OpenClaw context where all skills share filesystem access, this creates a high-risk secret exposure and tampering surface: another skill could read hashes for offline attacks or overwrite credential files to disrupt or hijack accounts.
create_directory(f"{user_dir}/sessions")
create_directory(f"{user_dir}/2fa")
write_json(f"{user_dir}/profile.json", profile)
write_json(f"{user_dir}/credentials.json", credentials)
write_json(f"{user_dir}/permissions.json", {'role': user_data['role'], 'custom': []})
# Audit log
The need to manually chmod credential files highlights that sensitive credential material is present on disk in a shared environment and depends on post-deployment OS hardening to be safe. If these permission steps are skipped, fail, or run too late, credential hashes become readable to unintended processes or users.
chown -R openclaw:openclaw /data/auth/
# Credential files must be read-only to the service user
chmod 600 /data/auth/users/*/credentials.json
# Session files
chmod 600 /data/auth/users/*/sessions/*.json
The skill declares OPENCLAW_DATA_DIR as the storage root, but the code examples hard-code /data/auth paths throughout authentication, authorization, and user management. In a shared multi-skill environment this can cause credentials, sessions, and access-control files to be read from or written to the wrong location, bypass expected isolation, or expose sensitive auth data unexpectedly.
The skill declares OPENCLAW_DATA_DIR as the storage root, but the code examples hard-code /data/auth paths throughout authentication, authorization, and user management. In a shared multi-skill environment this can cause credentials, sessions, and access-control files to be read from or written to the wrong location, bypass expected isolation, or expose sensitive auth data unexpectedly.
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
export OPENCLAW_DATA_DIR="/data"
which jq openssl || sudo apt install jq openssl
mkdir -p $OPENCLAW_DATA_DIR/auth
chmod 700 $OPENCLAW_DATA_DIR/auth
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
export OPENCLAW_DATA_DIR="/data" which jq openssl || sudo apt install jq openssl mkdir -p $OPENCLAW_DATA_DIR/auth chmod 700 $OPENCLAW_DATA_DIR/auth
No external auth services. User credentials are stored as salted SHA-256 hashes locally. 2FA uses SHA-256 TOTP generated by openssl.
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
export OPENCLAW_DATA_DIR="/data" which jq openssl || sudo apt install jq openssl mkdir -p $OPENCLAW_DATA_DIR/auth chmod 700 $OPENCLAW_DATA_DIR/auth
No external auth services. User credentials are stored as salted SHA-256 hashes locally. 2FA uses SHA-256 TOTP generated by openssl.
The markdown lists user-deactivate, --revoke-sessions, and password-reset --send-reset-link as available commands, but it does not warn that these actions can immediately disrupt user access or trigger account recovery flows. For a skill handling authentication state, readers should be clearly alerted to the operational impact of these commands.
The commands assign-clients --all-clients and access-matrix --all-users --all-clients can expand or expose access across the full client set, but the markdown provides no caution about the sensitivity of these operations. Because this skill manages access to accounting client data, the documentation should explicitly warn about the privacy and authorization implications.
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
chown -R openclaw:openclaw /data/auth/
# Credential files must be read-only to the service user
chmod 600 /data/auth/users/*/credentials.json
# Session files
chmod 600 /data/auth/users/*/sessions/*.json
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
chown -R openclaw:openclaw /data/auth/
# Credential files must be read-only to the service user
chmod 600 /data/auth/users/*/credentials.json
# Session files
chmod 600 /data/auth/users/*/sessions/*.json
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
chmod 600 /data/auth/users/*/sessions/*.json
# Role definitions (read by all skills for auth checks, writable only by admin)
chmod 644 /data/auth/roles/*.json
# Audit logs (append-only in production if OS supports it)
chmod 600 /data/auth/logs/**/*.json
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.
chmod 644 /data/auth/roles/*.json
chmod 600 /data/auth/logs/**/*.json
**Note**: The OpenClaw agent and all skills share the same file system context. Without OS-level permission restrictions, any skill could read credential hashes. These permissions ensure that only the authentication skill's process can access sensitive auth data.
The expectation explicitly requires formatting timestamps in the Europe/Athens timezone. This is a natural-language locale constraint, and the file does not indicate user choice or clearly document that the skill is limited to a Greece-specific or region-specific context.
The documented command session-revoke --all-devices is an immediate, potentially disruptive action that terminates active sessions, yet the markdown does not disclose that impact. Users of the skill should be warned before using commands that can forcibly log users out everywhere.
The docstring and comment emphasize one-time cleartext token exposure and hashed-at-rest storage, but the function mutates the session object after writing it and returns that enriched object containing bearer_token. While the token may indeed not be written to disk here, the documentation's framing understates that the returned session object now carries the secret alongside all persisted session metadata.
No suspicious patterns detected.