Last active
January 30, 2024 06:22
-
-
Save JacobHayes/9c86cc650c17a776f4a592fe0b2e7645 to your computer and use it in GitHub Desktop.
Reformat python files in git history w/ Black (line=100, py3.7/3.8)
This file contains 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 | |
# | |
# Modified from https://github.com/newren/git-filter-repo/blob/master/contrib/filter-repo-demos/lint-history | |
# | |
# pip3 install git-filter-repo black | |
# git pull | |
# git remote prune origin # clean up associated local branches too | |
# python3 black_history.py | |
# git remote add origin <url> | |
# git push -u origin --mirror --no-verify | |
import subprocess | |
import black | |
import git_filter_repo as fr | |
blobs_handled = {} | |
cat_file_process = None | |
def reformat_commit(commit, metadata): | |
for change in commit.file_changes: | |
if change.blob_id in blobs_handled: | |
change.blob_id = blobs_handled[change.blob_id] | |
elif change.filename.endswith(b".py"): | |
# change.blob_id is None for deleted files (ex: change.type=b'D') | |
if change.blob_id is None: | |
assert change.type == b"D" | |
continue | |
# Get the old blob contents | |
cat_file_process.stdin.write(change.blob_id + b"\n") | |
cat_file_process.stdin.flush() | |
objhash, objtype, objsize = cat_file_process.stdout.readline().split() | |
contents_plus_newline = cat_file_process.stdout.read(int(objsize) + 1) | |
# Reformat into a new blob | |
try: | |
blob = fr.Blob( | |
# Set fast=False to verify AST integrity after the reformat | |
black.format_file_contents( | |
contents_plus_newline.decode(), | |
fast=True, | |
mode=black.FileMode( | |
line_length=100, | |
target_versions={ | |
black.TargetVersion.PY37, | |
black.TargetVersion.PY38, | |
}, | |
), | |
).encode() | |
) | |
except black.NothingChanged: | |
continue | |
except black.InvalidInput: | |
print(f"\nUnable to format {change.filename.decode()}") | |
continue | |
# Insert the new file into the filter's stream, and remove the tempfile | |
filter.insert(blob) | |
# Record our handling of the blob and use it for this change | |
blobs_handled[change.blob_id] = blob.id | |
change.blob_id = blob.id | |
args = fr.FilteringOptions.default_options() | |
args.force = True | |
cat_file_process = subprocess.Popen( | |
["git", "cat-file", "--batch"], stdin=subprocess.PIPE, stdout=subprocess.PIPE | |
) | |
filter = fr.RepoFilter(args, commit_callback=reformat_commit) | |
filter.run() | |
cat_file_process.stdin.close() | |
cat_file_process.wait() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Is there a way to convert this to clang format ?