| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879 |
- #!/usr/bin/env python3
- from __future__ import annotations
- import re
- import subprocess
- import sys
- import typing
- import urllib.parse
- if typing.TYPE_CHECKING:
- from _typeshed import StrOrBytesPath
- def oneliner(*args) -> str:
- return subprocess.run(args, check=True, capture_output=True, text=True).stdout.strip()
- commit = oneliner('git', 'rev-parse', 'HEAD')
- local_branch = oneliner('git', 'branch', '--show-current')
- tag = tracking_branch = None
- if local_branch.startswith('tags/'):
- tag = local_branch[5:]
- if tag.endswith('^0'):
- tag = tag[:-2]
- remote_url = oneliner('git', 'config', 'remote.origin.url')
- else:
- try:
- tracking_branch = oneliner('git', 'config', 'branch.%s.merge' % local_branch)
- if tracking_branch.startswith('refs/heads/'):
- tracking_branch = tracking_branch[len('refs/heads/'):]
- else:
- raise Exception("can't handle " + tracking_branch)
- tracking_remote = oneliner('git', 'config', 'branch.%s.remote' % local_branch)
- remote_url = oneliner('git', 'config', 'remote.%s.url' % tracking_remote)
- except subprocess.CalledProcessError:
- remote_url = oneliner('git', 'config', 'remote.origin.url')
- relpath = oneliner('git', 'rev-parse', '--show-prefix')[:-1]
- remote_url = re.sub(r'^(.+@.+):(.+)$', r'ssh://\1/\2', remote_url)
- if remote_url.endswith('.git'):
- remote_url = remote_url[:-len('.git')]
- parsed = urllib.parse.urlparse(remote_url)
- hostname = parsed.hostname
- if hostname.startswith('github.com-'):
- hostname = 'github.com'
- obj_type = 'tree'
- if len(sys.argv) == 2:
- obj_type = 'blob'
- repo_url = urllib.parse.urlunparse(('https', hostname, parsed.path, '', '', ''))
- def url_for(treeish: str) -> str:
- dir_url = '%s/%s/%s' % (repo_url, obj_type, treeish)
- if relpath:
- dir_url = '%s/%s' % (dir_url, relpath)
- if len(sys.argv) == 2:
- return '%s/%s' % (dir_url, sys.argv[1])
- else:
- return dir_url
- if tag is not None:
- print(url_for(tag))
- elif tracking_branch is not None:
- print(url_for(tracking_branch))
- print(url_for(commit))
- for remote in oneliner('git', 'remote').splitlines():
- try:
- default_branch = oneliner('git', 'rev-parse', '--abbrev-ref', remote + '/HEAD').removeprefix(remote + '/')
- except subprocess.CalledProcessError as e:
- if e.returncode == 128: # not a cloned repo
- continue
- else:
- raise
- if default_branch != tracking_branch:
- print(url_for(default_branch))
|