zsh-users
 help / color / mirror / code / Atom feed
* Script to fetch Git commits modifying exactly the same files
@ 2016-09-23 14:14 Sebastian Gniazdowski
  0 siblings, 0 replies; only message in thread
From: Sebastian Gniazdowski @ 2016-09-23 14:14 UTC (permalink / raw)
  To: Zsh Users

[-- Attachment #1: Type: text/plain, Size: 578 bytes --]

Hello,
attached is a script for listing Git commits that modify EXACTLY the
same FILES as given commit. Also supports AT LEAST mode.

If one want's to do something fancy with git commits, this is rather
on top of the list. It is usable in statistical manner. Good for
intersecting through some unknown repository and obtaining clues.

Without UI script might be hard to use. For Gui, see Zcommodore, it
includes the script and is already quite usable, and with custom Ctags
supporting Zsh:

https://asciinema.org/a/2c45yzfep3qlan6crhw9rm8zb

Best regards,
Sebastian Gniazdowski

[-- Attachment #2: zgit_same_files --]
[-- Type: application/octet-stream, Size: 2926 bytes --]

#!/usr/bin/env zsh

emulate -LR zsh
setopt extendedglob

autoload colors
colors

cmdr_same_files() {
    if [[ "$1" = "-h" || "$#" = "0" ]]; then
        print -- "Searches for commits that alter the same set of files as input commit"
        print -- "${fg_bold[green]}Usage:${reset_color} zgit_same_files [-e] <repo path> <commit sha>"
        print
        print -- "-e Commits modifying EXACTLY the same files, never more than them"
        print
        print -- "${fg_bold[green]}Example run:${reset_color}"
        print -- "cmdr_same_files -e . f393004"
        print -- "or"
        print -- "cmdr_same_files -e ~/github/myproject f393004"
        return 0
    fi

    integer exactly=0
    [[ "$1" = "-e" ]] && exactly=1 && shift

    [[ "$#" -lt 2 ]] && { echo "Two parameters required, repo path and commit sha, aborting."; return 1; }

    (( exactly == 1 )) && print "${fg_bold[red]}Searching for commits modifying EXACTLY (-e) the same files${reset_color}"
    (( exactly == 0 )) && print "${fg_bold[red]}Searching for commits modifying AT LEAST the same files${reset_color}"

    local root_dir="$1"
    local commit="$2"

    [[ ! -d "$root_dir" ]] && { print "Repository dir (first parameter) doesn't exist or isn't directory"; return 1; }

    # Get list of files (3 steps)
    integer nfiles
    local -a files save_files
    files=( ${(f)"$( git -C "$root_dir" show --name-status "$commit" 2>/dev/null )"} )
    files=( "${(@M)files:#((#s)[ADM][ADM]#[[:space:]]##*|(#s)[ ][ADM][[:space:]]##*)}" )
    files=( "${files[@]/(#b)(#s)[[:alpha:]]##[[:space:]]##(*)(#e)/${match[1]}}" )
    nfiles="${#files}"
    save_files=( "${files[@]}" )

    [[ "$nfiles" = "0" ]] && { print "No commits found"; return 1; }

    # First revision list
    local -a revlist
    revlist=( ${(f)"$( git -C "$root_dir" rev-list HEAD -- ${files[1]} )"} )
    shift 1 files

    # Following revision lists - do intersections
    local -a revlist2
    local f
    for f in "${files[@]}"; do
        revlist2=( ${(f)"$( git -C "$root_dir" rev-list HEAD -- $f )"} )
        revlist=( "${revlist[@]:*revlist2}" )
    done

    if (( exactly )); then
        # Now for obtained revision list: count files,
        # reject revisions that change more files than
        # the required number
        local rev
        revlist2=()
        for rev in "${revlist[@]}"; do
            files=( ${(f)"$( git -C "$root_dir" show --name-status "$rev" 2>/dev/null )"} )
            files=( "${(@M)files:#(#s)[ADM][[:space:]]##*}" )
            [[ "${#files}" -eq "$nfiles" ]] && revlist2+=( "$rev" )
        done
    else
        revlist2=( "${revlist[@]}" )
    fi

    if [[ "${#revlist2}" = "0" ]]; then
        echo "${fg_bold[green]}No commits modifying the same set of files:${reset_color}"
        print -rl -- "${save_files[@]}"
    else
        git -C "$root_dir" show --stat "${revlist2[@]}"
    fi
}

cmdr_same_files "$@"
# vim:ft=zsh

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2016-09-23 14:20 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-09-23 14:14 Script to fetch Git commits modifying exactly the same files Sebastian Gniazdowski

Code repositories for project(s) associated with this public inbox

	https://git.vuxu.org/mirror/zsh/

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).