Last active
August 23, 2024 20:01
-
-
Save mgaitan/ba1e4e252b90a7fd4a4eb9e1742e94fb to your computer and use it in GitHub Desktop.
List or checkout recently used branches in git
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env python3 | |
# -*- coding: utf-8 -*- | |
""" | |
List the most recent branches you have been working on, and checkout any of them. | |
# Install | |
Put this file somewhere in your PATH, and set execution permissions. | |
Git will recognize it as the "recent-branches" subcommand. | |
# Usage | |
Without positional argument, it shows the last 10 most recently used branches. | |
You can pass -n <number> to see more. | |
$ git recent-branches | |
1 - feature/EN-634 | |
2 - feature/en-583_3 | |
3 * master | |
4 - HOTFIX/spotify | |
5 - tests_factories | |
6 - feature/en-583_2 | |
7 - _prod/workers/orders_py3 | |
8 - prueba | |
9 - _prod/workers/products_py3 | |
10 - staging | |
Passing a number will checkout the branch listed in that position. | |
$ git recent-branches 5 | |
Switched to branch 'tests_factories' | |
Your branch is up to date with 'origin/tests_factories'. | |
In the list, the row with "*" (instead "-") is the current branch. | |
""" | |
import argparse | |
import re | |
import subprocess | |
from collections import OrderedDict | |
pattern = re.compile(r"checkout: moving from ([A-Za-z0-9_\/\-\.]+) to") | |
parser = argparse.ArgumentParser(description="Recent branches") | |
parser.add_argument("index", type=int, nargs="?", help="Move to the i-th branch in the list") | |
parser.add_argument("--limit", "-n", type=int, default=10, help="Show until the n-th branch") | |
parser.add_argument("--force", "-f", action="store_true", help="Force checkout") | |
args = parser.parse_args() | |
output = subprocess.check_output(["git", "reflog"], text=True) | |
# OrderedList.fromkeys(list).keys() works as a filter of repeated items in list | |
# keeping the first occurrence of them. A poor-man sorted set. | |
branches = list(OrderedDict.fromkeys(re.findall(pattern, output)).keys()) | |
if args.index: | |
# use sw instead switch if available | |
# install sw from https://gist.github.com/mgaitan/d9a3523d79cd5f9fbfd626f646f0560b | |
use_sw = subprocess.call(["git", "sw"], stderr=subprocess.DEVNULL) == 2 and not args.force | |
cmd = ["git", "sw" if use_sw else "switch"] | |
if args.force: | |
cmd.append("-f") | |
cmd.append(branches[args.index - 1]) | |
subprocess.call(cmd) | |
else: | |
current = subprocess.check_output(["git", "branch", "--show-current"], text=True).strip() | |
for i, branch in enumerate(branches[: args.limit], 1): | |
print(f"{i} {'*' if current == branch else '-'} {branch}") |
@pzelnip, thanks for the idea. I've just implemented it, with a default to top 10 most recently used branches
Nice!
I forked and added it to ask to switch branch
https://gist.github.com/alvarmaciel/884660733fdb7c6ad9603ceb23d239ca
why not simply use fzf
git switch `git branch | fzf| tr -d '[:space:]'`
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Love this idea, would be nice to have a way to say only show the top n branches. Ie something like:
to show the 5 most recent, rather than always show all. I have a few repos I interact with where there's a large number of branches, but only interact with a small handful.