Infer remote URL when syncing token store

This commit is contained in:
mpabi
2026-04-27 20:54:43 +02:00
parent 147468c48d
commit 2e1b477dc0
3 changed files with 35 additions and 15 deletions
+27 -10
View File
@@ -1891,6 +1891,17 @@ def credentialed_remote_url(remote_url: str, user_name: str, token_value: str) -
return urlunsplit((split_url.scheme, netloc, split_url.path, split_url.query, split_url.fragment))
def remote_url_from_token_record(token_record: dict) -> str:
endpoint = token_server_endpoint(token_record).rstrip("/")
owner = str(token_record.get("org", "")).strip("/")
repo_name = str(token_record.get("repo", "")).strip("/")
if not endpoint or not owner or not repo_name:
return ""
if not repo_name.endswith(".git"):
repo_name = f"{repo_name}.git"
return f"{endpoint}/{quote(owner, safe='')}/{quote(repo_name, safe='')}"
def resolve_repo_argument(repo_arg: str | None) -> Path:
return Path(repo_arg).expanduser().resolve() if repo_arg else Path.cwd().resolve()
@@ -2179,16 +2190,16 @@ def run_tokens_write(config: WorkspaceConfig, args: argparse.Namespace) -> None:
token_data = load_token_store(config)
existing_remote_url = git_capture(repo_root, ["remote", "get-url", args.remote])
target_url = args.url or existing_remote_url
if not target_url:
raise SystemExit("Missing target remote URL. Provide --url or create the remote first.")
target_server_info = server_info_from_url(config, target_url)
if target_server_info is None:
raise SystemExit(f"Only http/https remote URLs are supported: {target_url}")
target_endpoint = None
if target_url:
target_server_info = server_info_from_url(config, target_url)
if target_server_info is None:
raise SystemExit(f"Only http/https remote URLs are supported: {target_url}")
target_endpoint = target_server_info["endpoint"]
token_record = resolve_token_from_store(
token_data,
args.server or target_server_info["endpoint"],
args.server or target_endpoint,
args.token_name or args.remote,
args.user,
)
@@ -2200,6 +2211,12 @@ def run_tokens_write(config: WorkspaceConfig, args: argparse.Namespace) -> None:
raise SystemExit(f"Token value is empty in tokens.json: {server_endpoint}:{remote_id}")
if not user_name:
raise SystemExit(f"Token user is empty in tokens.json: {server_endpoint}:{remote_id}")
if not target_url:
target_url = remote_url_from_token_record(token_record)
if not target_url:
raise SystemExit(
f"Missing target remote URL and tokens.json has no org/repo for: {server_endpoint}:{remote_id}"
)
final_url = credentialed_remote_url(target_url, user_name, token_value)
status = "added" if existing_remote_url is None else "updated"
@@ -2755,7 +2772,7 @@ def build_parser() -> argparse.ArgumentParser:
"--repo",
help="Path inside a target git repo. Default: repo containing rvctl.",
)
tokens_sync_parser.add_argument("--url", help="Target remote URL used when direction is 'store' and the remote does not exist yet.")
tokens_sync_parser.add_argument("--url", help="Override target remote URL when writing store -> remote.")
add_store_selection_options(tokens_sync_parser)
tokens_sync_parser.add_argument("--replace", action="store_true", help="Replace different credentials when writing store -> remote.")
tokens_sync_parser.add_argument("--dry-run", action="store_true", help="Print the planned sync without writing it.")
@@ -2779,7 +2796,7 @@ def build_parser() -> argparse.ArgumentParser:
)
add_repo_option(tokens_write_parser)
tokens_write_parser.add_argument("--remote", help="Remote name to update or create.")
tokens_write_parser.add_argument("--url", help="Target remote URL if the remote does not exist yet.")
tokens_write_parser.add_argument("--url", help="Override target remote URL when creating or updating the remote.")
add_store_selection_options(tokens_write_parser)
tokens_write_parser.add_argument("--replace", action="store_true", help="Replace different credentials in the remote URL.")
tokens_write_parser.add_argument("--dry-run", action="store_true", help="Print the planned update without writing it.")
@@ -2797,7 +2814,7 @@ def build_parser() -> argparse.ArgumentParser:
)
add_repo_option(tokens_update_parser)
tokens_update_parser.add_argument("--remote", help="Remote name used when --from store.")
tokens_update_parser.add_argument("--url", help="Target remote URL used when --from store.")
tokens_update_parser.add_argument("--url", help="Override target remote URL when --from store.")
add_store_selection_options(tokens_update_parser)
tokens_update_parser.add_argument("--replace", action="store_true", help="Replace different credentials when writing to remotes.")
tokens_update_parser.add_argument("--dry-run", action="store_true", help="Print the planned update without writing it.")