Added the ability to limit results by date range (Fixes issue 1).

This can now be done by supplying one (or both) of the "--since" and
"--until" parameters to the gitinspector executable. These parameters
work in the same manner as they do in git and accept the same values.
Statistics will only be generated from data between the given interval.
This commit is contained in:
Adam Waldenberg 2013-05-01 23:09:10 +02:00
parent cd3de23da2
commit f4c3285cb8
6 changed files with 74 additions and 7 deletions

View file

@ -23,6 +23,7 @@ from changes import FileDiff
import comment import comment
import filtering import filtering
import format import format
import interval
import missing import missing
import multiprocessing import multiprocessing
import re import re
@ -84,15 +85,18 @@ class BlameThread(threading.Thread):
class Blame: class Blame:
def __init__(self, hard): def __init__(self, hard):
self.blames = {} self.blames = {}
ls_tree_r = subprocess.Popen("git ls-tree --name-only -r HEAD", shell=True, bufsize=1, stdout=subprocess.PIPE).stdout ls_tree_r = subprocess.Popen("git ls-tree --name-only -r " + interval.get_ref(), shell=True, bufsize=1,
stdout=subprocess.PIPE).stdout
lines = ls_tree_r.readlines() lines = ls_tree_r.readlines()
for i, row in enumerate(lines): for i, row in enumerate(lines):
row = row.decode("utf-8", "replace").strip().strip("\"").strip("'") row = row.decode("utf-8", "replace").strip().strip("\"").strip("'")
row = row.decode("string_escape").strip() row = row.decode("string_escape").strip()
if FileDiff.is_valid_extension(row) and not filtering.set_filtered(FileDiff.get_filename(row)): if FileDiff.is_valid_extension(row) and not filtering.set_filtered(FileDiff.get_filename(row)):
if not missing.add(row.strip()): if not missing.add(row.strip()):
blame_string = "git blame -w {0} \"".format("-C -C -M" if hard else "") + row.strip() + "\"" blame_string = "git blame -w {0} ".format("-C -C -M" if hard else "") + \
interval.get_ref() + " -- \"" + row.strip() + "\""
thread = BlameThread(blame_string, FileDiff.get_extension(row), self.blames, row.strip()) thread = BlameThread(blame_string, FileDiff.get_extension(row), self.blames, row.strip())
thread.daemon = True thread.daemon = True
thread.start() thread.start()

View file

@ -21,12 +21,12 @@ from __future__ import print_function
from outputable import Outputable from outputable import Outputable
import extensions import extensions
import filtering import filtering
import interval
import re import re
import os import os
import subprocess import subprocess
import terminal import terminal
import textwrap import textwrap
import sys
class FileDiff: class FileDiff:
def __init__(self, string): def __init__(self, string):
@ -91,7 +91,8 @@ class AuthorInfo:
class Changes: class Changes:
def __init__(self, hard): def __init__(self, hard):
self.commits = [] self.commits = []
git_log_r = subprocess.Popen("git log --pretty=\"%ad|%t|%aN|%s\" --stat=100000,8192 --no-merges -w " + git_log_r = subprocess.Popen("git log --pretty=\"%ad|%H|%aN|%s\" --stat=100000,8192 --no-merges -w " +
interval.get_since() + interval.get_until() +
"{0} --date=short".format("-C -C -M" if hard else ""), "{0} --date=short".format("-C -C -M" if hard else ""),
shell=True, bufsize=1, stdout=subprocess.PIPE).stdout shell=True, bufsize=1, stdout=subprocess.PIPE).stdout
commit = None commit = None
@ -115,6 +116,9 @@ class Changes:
filediff = FileDiff(i) filediff = FileDiff(i)
commit.add_filediff(filediff) commit.add_filediff(filediff)
if interval.has_interval():
interval.set_ref(self.commits[0].sha)
def get_commits(self): def get_commits(self):
return self.commits return self.commits

View file

@ -26,6 +26,7 @@ import filtering
import format import format
import getopt import getopt
import help import help
import interval
import metrics import metrics
import missing import missing
import os import os
@ -81,8 +82,8 @@ if __name__ == "__main__":
try: try:
__opts__, __args__ = getopt.gnu_getopt(sys.argv[1:], "cf:F:hHlmrTwx:", ["checkout-missing", "exclude=", __opts__, __args__ = getopt.gnu_getopt(sys.argv[1:], "cf:F:hHlmrTwx:", ["checkout-missing", "exclude=",
"file-types=", "format=", "hard", "help", "list-file-types", "file-types=", "format=", "hard", "help", "list-file-types",
"metrics", "responsibilities", "grading", "timeline", "metrics", "responsibilities", "since=", "grading",
"version"]) "timeline", "until=", "version"])
for o, a in __opts__: for o, a in __opts__:
if o in("-c", "--checkout-missing"): if o in("-c", "--checkout-missing"):
missing.set_checkout_missing(True) missing.set_checkout_missing(True)
@ -102,6 +103,8 @@ if __name__ == "__main__":
__run__.include_metrics = True __run__.include_metrics = True
elif o in("-r", "--responsibilities"): elif o in("-r", "--responsibilities"):
__run__.responsibilities = True __run__.responsibilities = True
elif o in("--since"):
interval.set_since(a)
elif o in("--version"): elif o in("--version"):
version.output() version.output()
sys.exit(0) sys.exit(0)
@ -115,6 +118,8 @@ if __name__ == "__main__":
__run__.useweeks = True __run__.useweeks = True
elif o in("-T", "--timeline"): elif o in("-T", "--timeline"):
__run__.timeline = True __run__.timeline = True
elif o in("--until"):
interval.set_until(a)
elif o in("-w"): elif o in("-w"):
__run__.useweeks = True __run__.useweeks = True
elif o in("-x", "--exclude"): elif o in("-x", "--exclude"):

View file

@ -42,7 +42,11 @@ Mandatory arguments to long options are mandatory for short options too.
analysis of commits analysis of commits
-r --responsibilities show which files the different authors seem -r --responsibilities show which files the different authors seem
most responsible for most responsible for
--since=DATE show statistics for commits more recent than a
specific date
-T, --timeline show commit timeline, including author names -T, --timeline show commit timeline, including author names
--until=DATE show statistics for commits older than a
specific date
-w show all statistical information in weeks -w show all statistical information in weeks
instead of in months instead of in months
-x, --exclude=PATTERN an exclusion pattern describing file names that -x, --exclude=PATTERN an exclusion pattern describing file names that

49
interval.py Normal file
View file

@ -0,0 +1,49 @@
#!/usr/bin/python
# coding: utf-8
#
# Copyright © 2012-2013 Ejwa Software. All rights reserved.
#
# This file is part of gitinspector.
#
# gitinspector is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# gitinspector is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with gitinspector. If not, see <http://www.gnu.org/licenses/>.
__since__ = ""
__until__ = ""
__ref__ = "HEAD"
def has_interval():
return __since__ + __until__ != ""
def get_since():
return __since__
def set_since(since):
global __since__
__since__ = "--since=\"" + since + "\" "
def get_until():
return __until__
def set_until(until):
global __until__
__until__ = "--until=\"" + until + "\" "
def get_ref():
return __ref__
def set_ref(ref):
global __ref__
__ref__ = ref

View file

@ -19,6 +19,7 @@
from __future__ import print_function from __future__ import print_function
from outputable import Outputable from outputable import Outputable
import interval
import os import os
import subprocess import subprocess
import terminal import terminal
@ -28,7 +29,7 @@ __checkout_missing__ = False
__missing_files__ = set() __missing_files__ = set()
def add(file_name): def add(file_name):
if not os.path.exists(file_name): if not interval.has_interval() and not os.path.exists(file_name):
if __checkout_missing__: if __checkout_missing__:
subprocess.call("git checkout \"" + file_name.strip() + "\"", shell=True) subprocess.call("git checkout \"" + file_name.strip() + "\"", shell=True)
else: else: