{"record":{"id":"808b5e482f37dfce","repo":"CoplayDev/unity-mcp","slug":"remote-url-must-be-a-non-empty-url","errorCode":null,"errorMessage":"--remote-url must be a non-empty URL","messagePattern":"--remote-url must be a non-empty URL","errorType":"exception","errorClass":"RuntimeError","httpStatus":null,"severity":"error","filePath":"tools/prepare_unity_asset_store_release.py","lineNumber":106,"sourceCode":"    )\n    parser.add_argument(\n        \"--backup\",\n        action=\"store_true\",\n        help=\"Backup existing Assets/MCPForUnity before replacing.\",\n    )\n    parser.add_argument(\n        \"--dry-run\",\n        action=\"store_true\",\n        help=\"Only validate that operations would succeed; do not write/copy/delete.\",\n    )\n    args = parser.parse_args()\n\n    repo_root = Path(args.repo_root).expanduser().resolve()\n    asset_project = Path(args.asset_project).expanduser().resolve(\n    ) if args.asset_project else (repo_root / \"TestProjects\" / \"AssetStoreUploads\")\n    remote_url = args.remote_url.strip()\n    if not remote_url:\n        raise RuntimeError(\"--remote-url must be a non-empty URL\")\n\n    source_mcp = repo_root / \"MCPForUnity\"\n    if not source_mcp.is_dir():\n        raise RuntimeError(\n            f\"Source MCPForUnity folder not found: {source_mcp}\")\n\n    assets_dir = asset_project / \"Assets\"\n    if not assets_dir.is_dir():\n        raise RuntimeError(f\"Assets folder not found: {assets_dir}\")\n\n    dest_mcp = assets_dir / \"MCPForUnity\"\n\n    if args.dry_run:\n        print(\"[dry-run] Validated paths. No changes applied.\")\n        print(\"[dry-run] Would stage a temporary copy of MCPForUnity and apply Asset Store edits there.\")\n        print(\n            f\"[dry-run] Would replace:\\n- {dest_mcp}\\n  with\\n- {source_mcp}\")\n        return 0","sourceCodeStart":88,"sourceCodeEnd":124,"githubUrl":"https://github.com/CoplayDev/unity-mcp/blob/c21bf496bca87d54e75bad048563c3adb1782081/tools/prepare_unity_asset_store_release.py#L88-L124","documentation":"Raised by main() in prepare_unity_asset_store_release.py when --remote-url, after stripping whitespace, is empty. argparse declares the flag as required=True, which rejects a missing flag entirely — but argparse still accepts an empty or whitespace-only string as a valid value. This secondary check catches that gap and aborts before the URL is injected into C# source.","triggerScenarios":"Invoked with --remote-url \"\", --remote-url \"   \", or an env-var expansion that resolves to blank (e.g. --remote-url \"$REMOTE_URL\" when the variable is unset). The .strip() result is falsy, triggering the RuntimeError.","commonSituations":"CI pipeline where the remote URL is supplied via an environment variable that wasn't set; copy-paste of the example command without filling in the actual URL; shell quoting that passes an empty expansion.","solutions":["Provide a real non-empty URL: --remote-url https://your.remote.endpoint/","If sourcing from an environment variable, ensure it is exported and non-empty before invoking the script, e.g. test -n \"$REMOTE_URL\" && python tools/prepare_unity_asset_store_release.py --remote-url \"$REMOTE_URL\".","Add a URL-format validation (e.g. urllib.parse) if you want to catch malformed values earlier."],"exampleFix":"# before\npython tools/prepare_unity_asset_store_release.py --remote-url \"\"\n\n# after\npython tools/prepare_unity_asset_store_release.py --remote-url https://your.remote.endpoint/","handlingStrategy":"validation","validationCode":"from urllib.parse import urlparse\n\ndef is_valid_remote_url(url: str) -> bool:\n    stripped = url.strip()\n    if not stripped:\n        return False\n    parsed = urlparse(stripped)\n    return parsed.scheme in (\"http\", \"https\") and bool(parsed.netloc)\n\n# Before invoking the script:\nif not is_valid_remote_url(my_url):\n    raise SystemExit(\"REMOTE_URL must be a non-empty http(s) URL\")","typeGuard":null,"tryCatchPattern":null,"preventionTips":["In CI, gate the call with: test -n \"$REMOTE_URL\" || exit 1.","Use argparse type= with a validation function to reject empty/whitespace URLs at parse time instead of after.","Store the URL in a committed config file or CI secret rather than passing it inline."],"tags":["build-script","release-tooling","argument-validation","cli"],"backgroundTag":null,"analyzedSha":"c21bf496bca87d54e75bad048563c3adb1782081","analyzedAt":"2026-08-13T17:36:56.095Z","schemaVersion":2},"datasetVersion":"2026-08-13T19:17:28.613Z"}