Performance Fix: Minimize number of advertisedHaves
While we set up hooks in ReceiveCommits to minimize the number of advertised refs (for instance filtering out refs/changes and refs/cache-automerge refs), their objectIds will still be added to BaseReceivePack.advertisedHaves (JGit), leading to an unnecessarily complex commit graph for JGit to traverse when checking for commit connectivity in BaseReceivePack.checkConnectivity(). By filtering the refs before the objectIds are added to advertisedHaves, lots of time can be saved when pushing to complex Gits. Push times for one of our Gits (warm caches): Before fix: real 0m42.926s After fix: real 0m6.325s This Git has around 90k change/ps refs. Change-Id: I2f0a0830bd733f908f0aeaf1eaf0412dae428a16
This commit is contained in:
committed by
David Pursehouse
parent
b9e9b23d8b
commit
a4a5366444
@@ -18,7 +18,6 @@ import static com.google.gerrit.reviewdb.client.Change.INITIAL_PATCH_SET_ID;
|
||||
import static com.google.gerrit.server.git.MultiProgressMonitor.UNKNOWN;
|
||||
import static com.google.gerrit.server.mail.MailUtil.getRecipientsFromApprovals;
|
||||
import static com.google.gerrit.server.mail.MailUtil.getRecipientsFromFooters;
|
||||
|
||||
import static org.eclipse.jgit.lib.Constants.R_HEADS;
|
||||
import static org.eclipse.jgit.transport.ReceiveCommand.Result.NOT_ATTEMPTED;
|
||||
import static org.eclipse.jgit.transport.ReceiveCommand.Result.OK;
|
||||
@@ -114,6 +113,7 @@ import org.eclipse.jgit.transport.AdvertiseRefsHook;
|
||||
import org.eclipse.jgit.transport.AdvertiseRefsHookChain;
|
||||
import org.eclipse.jgit.transport.BaseReceivePack;
|
||||
import org.eclipse.jgit.transport.ReceiveCommand;
|
||||
import org.eclipse.jgit.transport.RefFilter;
|
||||
import org.eclipse.jgit.transport.ReceiveCommand.Result;
|
||||
import org.eclipse.jgit.transport.ReceivePack;
|
||||
import org.eclipse.jgit.transport.UploadPack;
|
||||
@@ -363,6 +363,20 @@ public class ReceiveCommits {
|
||||
rp.setAllowDeletes(true);
|
||||
rp.setAllowNonFastForwards(true);
|
||||
rp.setCheckReceivedObjects(true);
|
||||
rp.setRefFilter(new RefFilter() {
|
||||
@Override
|
||||
public Map<String, Ref> filter(Map<String, Ref> refs) {
|
||||
Map<String, Ref> filteredRefs = Maps.newHashMapWithExpectedSize(refs.size());
|
||||
for (Map.Entry<String, Ref> e : refs.entrySet()) {
|
||||
String name = e.getKey();
|
||||
if (!name.startsWith("refs/changes/")
|
||||
&& !name.startsWith(GitRepositoryManager.REFS_CACHE_AUTOMERGE)) {
|
||||
filteredRefs.put(name, e.getValue());
|
||||
}
|
||||
}
|
||||
return filteredRefs;
|
||||
}
|
||||
});
|
||||
|
||||
if (!projectControl.allRefsAreVisible()) {
|
||||
rp.setCheckReferencedObjectsAreReachable(config.checkReferencedObjectsAreReachable);
|
||||
|
||||
Reference in New Issue
Block a user