libgit2: как разместить определенные строки в блоке

Я пишу приложение для Mac, которое позволит мне отображать только те строки, которые содержат определенный текст в качестве подстроки. По сути, я пытаюсь создать ту функцию, которую исходное дерево предлагает своим пользователям. Постановка выбранных строк в куски. Моя логика выбора заключалась бы в том, чтобы выбрать строки, содержащие определенный текст, в качестве подстроки. Но я не мог понять, как этого добиться с помощью libgit2.

Я инициализировал репо следующим образом

int error = git_repository_open(&repo, gitRepoString.UTF8String);

Затем я создаю diff-индекс для рабочего каталога, как показано ниже.

error = git_diff_index_to_workdir(&diff, repo, NULL, NULL);

После этого я могу перебирать куски и строки в каждом куске, используя функции обратного вызова, как показано ниже.

error = git_diff_foreach(diff, each_file_cb,
                                    each_binary_cb,
                                     each_hunk_cb,
                                     each_line_cb,
                                     &d);

и обратные вызовы вызываются для каждой строки в фрагменте.

int each_line_cb(const git_diff_delta *delta,
                 const git_diff_hunk *hunk,
                 const git_diff_line *line,
                 void *payload)
{
    return 0;
}

Теперь я понимаю, что мне нужно как-то создать патч и добавить в патч только нужные строки в diff.

Может ли кто-нибудь направить в правильном направлении? Если libgit2 еще не позволяет это сделать, есть ли какая-либо другая библиотека, которая может позволить мне это сделать. Также исходное дерево atlassian, похоже, использует libgit2 под капотом. Как они могли это реализовать?

Кстати, git CLI позволяет сделать это с помощью исправлений, как указано в этом ответе. https://stackoverflow.com/a/32311872/569497


person Selvin    schedule 27.03.2017    source источник
comment
Простого способа сделать это пока нет. У нас есть набор патчей в нашем форке (github.com/stinb/libgit2/tree/gitahead), которые добавляют поддержку приложения с частичным исправлением. Я хотел бы попытаться получить их вверх по течению в ближайшее время. Я отправлю ссылку на PR после того, как я представлю его.   -  person Jason Haslam    schedule 28.03.2017
comment
Кстати, я не знаю, как это делает SourceTree, но я подозреваю, что он не полагается на функциональность libgit2.   -  person Jason Haslam    schedule 28.03.2017
comment
FWIW, я отправил запрос на включение (github.com/libgit2/libgit2/pull/4184), чтобы включить частичное исправление. Если это будет объединено, я могу добавить ответ, который объясняет, как использовать его для реализации постановки отдельных фрагментов и строк.   -  person Jason Haslam    schedule 29.03.2017
comment
Большое спасибо @JasonHaslam с нетерпением жду вашего решения!   -  person Selvin    schedule 03.04.2017


Ответы (1)


В итоге я реализовал это вручную. Это оказалось проще, чем я ожидал.

Мой подход к применению куска:

  • Разделите строки целевого файла на массив
  • Соберите «контекстные» и «старые» строки из фрагмента и убедитесь, что они соответствуют существующему контенту.
  • Соберите «контекст» и «новые» строки и замените раздел контекста/старого в моем массиве строк.
  • Запишите данные обратно, пытаясь сопоставить существующие окончания строк

Это должно быть легко адаптировать только к применению определенных линий.

Мой код здесь (в Swift, с использованием Objective Git): https://github.com/Uncommon/Xit/blob/369dd52d444d4650759c22414121dd2a6be282d2/Xit/XTDiffDelta.swift

person Uncommon    schedule 28.03.2017