T09 · Insecure Skill Coding Practices
Error
- Location
- scripts/capabilities/execute/service.py:8
- Finding
- Product Mutations Can Bypass the Required Pre-Check and User Confirmation Workflow<![CDATA[ ## Vulnerability Details **File Location**: `scripts/capabilities/execute/service.py:8-34`; `scripts/capabilities/execute/cmd.py:17-37` **Vulnerability Type**: Missing enforcement of authorization workflow and operation allowlisting **Risk Level**: High ### Vulnerable Code ```python def execute_action(item_id: str, spi_code: str, spi_params: dict) -> dict: """ Execute the actual modification. Must only be called after before_check succeeds and the user confirms. """ if not item_id: raise ParamError("Product ID (item_id) cannot be empty") if not spi_code: raise ParamError("Operation code (spi_code) cannot be empty") if not spi_params: raise ParamError("Operation parameters (spi_params) cannot be empty") data = api_post( f"/api/{TOOL_CODE_EXECUTE}/1.0.0", { "item_id": item_id, "spi_code": spi_code, "spi_params": spi_params, }, timeout=30, ) if not isinstance(data, dict): raise ServiceError("Invalid response format; try again later") return data ``` The command entry point invokes this function directly: ```python parser.add_argument('--item_id', type=str, required=True, help='Product ID') parser.add_argument('--spi_code', type=str, required=True, help='Operation code') parser.add_argument('--spi_params', type=str, required=True, help='Operation parameters as JSON') args = parser.parse_args() try: spi_params = json.loads(args.spi_params) except json.JSONDecodeError as e: print_error(ValueError(f"spi_params is not valid JSON: {e}")) return try: result = execute_action(args.item_id, args.spi_code, spi_params) ``` ### Technical Analysis The Skill documentation requires every write operation to follow this sequence: 1. Call `before_check`. 2. Verify that the proposed operation is permitted. 3. Display the proposed mutation or agreement to the user. 4. Obtain explicit user confirmation. 5. ...[truncated 2167 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions 1. Make `before_check` return a cryptographically protected, short-lived approval token. 2. Bind the token to: - The authenticated account or AK identifier. - Product ID. - Operation code. - A canonical hash of the complete operation parameters. - Expiration time. 3. Require the approval token as an argument to `execute`. 4. Validate the token server-side and reject missing, expired, reused, or mismatched tokens. 5. Mark tokens as single-use after a successful mutation. 6. Require a distinct confirmation step after the pre-check response. Where possible, record confirmation in trusted orchestration state rather than relying exclusively on Agent instructions. 7. Add an explicit allowlist of supported operation codes. 8. Validate each operation with a dedicated schema, including type, format, length, and value constraints. 9. Reject unexpected fields and ensure that the parameters executed are byte-for-byte or canonically equivalent to those approved. 10. Add tests proving that direct execution, changed parameters, replayed approvals, and unsupported operation codes are rejected. ]]>
