Использование git для идентификации всех модифицированных функций в ревизии - PullRequest
4 голосов
/ 19 апреля 2011

Есть ли хороший способ использовать git для идентификации всех модифицированных функций в каждой ревизии в истории?Я пытался использовать ключ -p, но, похоже, он работает не так, как работает параметр show-c-function в svn.

Я предполагаю, что я хочу использовать "gitdiff HEAD ~ i HEAD ~ i-1 -p "для увеличения значений i.Я пропускаю некоторые параметры, которые помогут определить лучшее предположение diff для функций, которые были изменены?

Ответы [ 3 ]

6 голосов
/ 11 сентября 2016

Вот магическое пение для перечисления функций в пределах git diff *

git diff |                  \
grep -E '^(@@)' |           \
grep "(" |                  \
sed 's/@@.*@@//' |          \
sed 's/(.*//' |             \
awk -F " " '{print $NF}' |  \
uniq

... и что этоdo is ...

  1. Выбирает текущий diff,
  2. next выбирает только строки с "заголовками",
  3. next выбирает только строки соткрывающая скобка (как потенциально содержащая имена функций),
  4. next игнорирует заголовки блоков,
  5. next игнорирует текст после открывающей скобки,
  6. next выбирает только слово непосредственно передоткрывающая скобка,
  7. и, наконец, игнорирует несколько вхождений одного и того же слова в списке.

Вуаля! у вас есть список функцийизменено текущим git diff.


* Проверено с помощью git version 2.7.4 в Ubuntu 16.04 под управлением bash.

3 голосов
/ 19 апреля 2011

Вот быстрая и грязная попытка того, что я думаю, что вы собираетесь.Он делает git log, чтобы показать все ревизии, -p, чтобы включить diff в журнал, grep, чтобы включить только строки, содержащие идентификатор фиксации и заголовки блоков, и использует sed для фильтрации строкичисла, оставляя только предположение по имени функции, которое Git пишет после заголовка блока.

git log -p | grep -E '^(commit|@@)' | sed 's/@@.*@@//'
0 голосов
/ 27 февраля 2018

Вы можете перечислить все измененные функции в ревизии, используя фильтры git textconv.Идея состоит в том, чтобы создать специальный фильтр, который перечисляет все функции / методы, а для всех функций - контрольную сумму тела.Это дает такой вид отфильтрованного текстового представления:

m() 12
bar() 42

(здесь m() - сигнатура функции, 12 - контрольная сумма ее тела))

Когда git diff используетэтот фильтр для двух версий до и после ревизии:

  • , если добавлена ​​функция, в diff добавляется строка

Пример: добавляется foo

m() 12
+ foo() 24 
bar() 42
  • если функция изменена, контрольная сумма изменяется, и в diff обновляется строка

Пример: тело foo изменяется

m() 12
- foo() 23 
+ foo() 24 
bar() 42

Как это сделать?

  1. Создать фильтр: java-ls-method.groovy - реализация такого фильтра с использованием Groovy и Spoon
  2. Зарегистрируйте этот фильтр в git: git config diff.java-ls-methods.textconv /home/path/to/java-ls-methods.groovy
  3. Свяжите этот фильтр с файлами Java: echo "*.java diff=java-ls-methods" >> .gitattributes
  4. Создайте diff: git diff (diff против последнегоcommit) или git diff master (diff против другой ветви)
  5. Как только ваш diff закончен, прокомментируйте строку в .gitattributes, чтобы вернуться к обычному diff

Кредиты: решение на основе https://stackoverflow.com/a/16929266

...