blob: a9a297df495f14fec7317235db61f792ca4ebefc [file]
#!/usr/bin/env vpython3
# Copyright 2026 The Chromium Authors
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""Extracts host, project, change, and patchset from a Gerrit CL URL."""
import argparse
import json
import re
import sys
import urllib.parse
def parse_gerrit_url(url: str) -> dict[str, str | int]:
"""Parses a Gerrit CL URL into host, project, change, and patchset.
Args:
url: Absolute Gerrit CL URL string.
Returns:
Dictionary containing host, project, change (int), and patchset (int).
"""
parsed = urllib.parse.urlparse(url)
host = parsed.netloc
path = parsed.path
if not host or not path:
raise ValueError(f'Invalid Gerrit URL: {url}')
match = re.match(r'^/c/(.+?)/\+/(\d+)(?:/(\d+))?', path)
if not match:
raise ValueError(f'Could not extract CL details from path: {path}')
project = match.group(1)
change = int(match.group(2))
patchset = int(match.group(3)) if match.group(3) else 1
return {
'host': host,
'project': project,
'change': change,
'patchset': patchset,
}
def main() -> None:
"""Parses CLI arguments and prints Gerrit CL details as JSON."""
parser = argparse.ArgumentParser(description=__doc__)
parser.add_argument('url', help='Gerrit CL URL')
args = parser.parse_args()
try:
details = parse_gerrit_url(args.url)
print(json.dumps(details, indent=2))
except ValueError as e:
print(str(e), file=sys.stderr)
sys.exit(1)
if __name__ == '__main__':
main()