T09 · Insecure Skill Coding Practices
Error
- Location
- scripts/paylock.py:27
- Finding
- Authentication Tokens Exposed Through Command-Line Arguments<![CDATA[ ## Vulnerability Details **File Location**: `scripts/paylock.py:27-35`, `scripts/paylock.py:63-74` **Vulnerability Type**: Command-line credential exposure **Risk Level**: High ### Vulnerable Code ```python d = sub.add_parser("deliver", help="Deliver work for contract") d.add_argument("--id", required=True) d.add_argument("--delivery-payload", required=True) d.add_argument("--delivery-hash", required=True) d.add_argument("--payee-token", required=True) v = sub.add_parser("verify", help="Verify delivery") v.add_argument("--id", required=True) v.add_argument("--payer-token", required=True) ``` ```python elif args.command == "deliver": result = client.request( "POST", f"/{args.id}/deliver", payload={ "delivery_payload": args.delivery_payload, "delivery_hash": args.delivery_hash, "payee_token": args.payee_token, }, ) elif args.command == "verify": result = client.request( "POST", f"/{args.id}/verify", payload={"payer_token": args.payer_token}, ) ``` ### Technical Analysis The unified CLI requires payer and payee authentication tokens to be supplied as command-line arguments. Command-line arguments are not an appropriate secret-transport mechanism because they may be retained or exposed through: - Shell history files - Process inspection tools such as `ps` - `/proc/<pid>/cmdline` on Linux - Process-monitoring and orchestration systems - Audit, debugging, and terminal-session logs - Wrapper scripts or automation logs This behavior also contradicts `SKILL.md:21-25`, which states that authentication tokens are passed through environment variables and never through CLI arguments. Although the dedicated `deliver_contract.py` and `verify_contract.py` scripts support environment variables, the documented unified `paylock.py` interface does not. ### Attack Path 1. A user invokes the unified CLI with `--payee-token` or `--payer-token`. 2. The token ...[truncated 1073 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions - Remove `--payer-token` and `--payee-token` from the unified CLI, or make them deprecated emergency options that emit a prominent warning. - Read the credentials from `PAYLOCK_PAYER_TOKEN` and `PAYLOCK_PAYEE_TOKEN`, consistently with the documentation and dedicated scripts. - For interactive use, support protected input through `getpass.getpass()` or a dedicated file descriptor rather than ordinary stdin or command-line arguments. - Prefer short-lived, contract-scoped tokens with explicit action restrictions. - Implement server-side token expiration, revocation, replay prevention, and rate limiting. - Ensure error messages and API responses never echo submitted tokens. - Update tests and documentation to verify that secrets do not appear in process arguments. A safer implementation pattern is: ```python import os d.add_argument("--payee-token", default=None, help=argparse.SUPPRESS) v.add_argument("--payer-token", default=None, help=argparse.SUPPRESS) payee_token = os.getenv("PAYLOCK_PAYEE_TOKEN") payer_token = os.getenv("PAYLOCK_PAYER_TOKEN") ``` For stronger protection, remove the arguments entirely and fail safely when the required environment variable is absent. ]]>
