我创建了一个工具,它遍历存储库的所有提交。
然后它对所有父项进行提交的差异,然后读取内容以进行某些检查。
现在它发现这种速度很快就会减慢。它总是在相同的特定提交之后减慢,因为它是一个合并提交。
这里是代码如何通过提交进行迭代。为了更好地关注,以下代码稍微简化了一些。
var repo = new Repository(path);
foreach (LibGit2Sharp.Commit commit in repo.Commits)
{
IEnumerable<FileChanges> changed = repo.GetChangedToAllParents(commit);
var files = ResolveChangeFileInfos(changed);
var entry = new Commit(commit.Id.ToString(), commit.Author.Email, commit.Committer.When, commit.Message, files);
yield return entry;
}
在GetChagedToAllParents
我基本上像这样做一个差异的foreach父母
foreach(var parent in commit.parent)
{
var options = new CompareOptions
{
Algorithm = DiffAlgorithm.Minimal,
IncludeUnmodified = false
};
var patches = repo.Diff.Compare<Patch>(parent.Tree, commit.Tree, options); // Difference
}
后来我用这种方式阅读了文件的内容:
var blob = repo.Lookup<Blob>(patchEntry.Oid.Sha); // Find blob
Stream contentStream = blob.GetContentStream();
string result = null;
using (var tr = new StreamReader(contentStream, Encoding.UTF8))
{
result = tr.ReadToEnd();
}
有任何已知问题吗?我错过任何泄漏吗?
更新
我发现大部分时间(约90%)是差异所采取的。它变得越来越慢
var options = new CompareOptions
{
Algorithm = DiffAlgorithm.Minimal,
IncludeUnmodified = false
};
var patches = repo.Diff.Compare<Patch>(parent.Tree, commit.Tree, options); // Difference
我可以使用以下代码重现它:
var repo = new Repository(path);
foreach (var commit in repo.Commits)
{
pos++;
if (pos%100 == 0)
{
Console.WriteLine(pos);
}
var options = new CompareOptions
{
Algorithm = DiffAlgorithm.Minimal,
IncludeUnmodified = false,
Similarity = new SimilarityOptions
{
RenameDetectionMode = RenameDetectionMode.None,
WhitespaceMode = WhitespaceMode.IgnoreAllWhitespace
}
};
foreach (var parent in commit.Parents)
{
var changedFiles=
repo.Diff.Compare<TreeChanges>(parent.Tree, commit.Tree, options).ToList();
}
}
它为每1000次提交保留了大约500MB,并且在某些时候它只是崩溃了。所以我也在这里发布了它:
https://github.com/libgit2/libgit2sharp/issues/1359
是否有更快的方法来获取在特定提交中更改的所有文件?