diff options
author | David Ostrovsky <david@ostrovsky.org> | 2022-06-28 17:11:52 +0200 |
---|---|---|
committer | David Ostrovsky <david@ostrovsky.org> | 2022-06-28 17:11:52 +0200 |
commit | 4604bdb864d986bc5c005b34917a788ed8abdd16 (patch) | |
tree | 00598d8cf04543b04897fbd014eeec51692deee1 | |
parent | 973413c69e34e63394109163c71bf86c73a9e691 (diff) | |
parent | 5f156a8febabca89b220547641f9c7a93ee89bfa (diff) |
Merge branch 'stable-3.0' into stable-3.1
* stable-3.0:
Allow async receive-commits to have a thread-local cache
Fix RepoRefCache stale checks during NoteDb rebuild
Lazy load change notes when submit by push
Change-Id: Ie82487167fc84ec543083b018c3fde1b0a041e1d
Release-Notes: skip
3 files changed, 19 insertions, 12 deletions
diff --git a/java/com/google/gerrit/server/git/RepoRefCache.java b/java/com/google/gerrit/server/git/RepoRefCache.java index c813b8375b..4fa33118f5 100644 --- a/java/com/google/gerrit/server/git/RepoRefCache.java +++ b/java/com/google/gerrit/server/git/RepoRefCache.java @@ -136,8 +136,9 @@ public class RepoRefCache implements RefCache { } try { - ObjectId diskId = refdb.exactRef(refName).getObjectId(); - boolean isStale = !Optional.ofNullable(diskId).equals(id); + Optional<ObjectId> diskId = + Optional.ofNullable(refdb.exactRef(refName)).map(Ref::getObjectId); + boolean isStale = !diskId.equals(id); if (isStale) { log.atSevere().log( "Repository " diff --git a/java/com/google/gerrit/server/git/receive/AsyncReceiveCommits.java b/java/com/google/gerrit/server/git/receive/AsyncReceiveCommits.java index f5c3aa9d43..c68ed30871 100644 --- a/java/com/google/gerrit/server/git/receive/AsyncReceiveCommits.java +++ b/java/com/google/gerrit/server/git/receive/AsyncReceiveCommits.java @@ -33,6 +33,7 @@ import com.google.gerrit.metrics.Histogram1; import com.google.gerrit.metrics.MetricMaker; import com.google.gerrit.metrics.Timer1; import com.google.gerrit.server.IdentifiedUser; +import com.google.gerrit.server.cache.PerThreadCache; import com.google.gerrit.server.config.AllUsersName; import com.google.gerrit.server.config.ConfigUtil; import com.google.gerrit.server.config.GerritServerConfig; @@ -133,7 +134,7 @@ public class AsyncReceiveCommits implements PreReceiveHook { public void run() { String oldName = Thread.currentThread().getName(); Thread.currentThread().setName(oldName + "-for-" + name); - try { + try (PerThreadCache threadLocalCache = PerThreadCache.create(null)) { receiveCommits.processCommands(commands, progress); } finally { Thread.currentThread().setName(oldName); diff --git a/java/com/google/gerrit/server/git/receive/ReceiveCommits.java b/java/com/google/gerrit/server/git/receive/ReceiveCommits.java index 3b5b080009..012ba437fb 100644 --- a/java/com/google/gerrit/server/git/receive/ReceiveCommits.java +++ b/java/com/google/gerrit/server/git/receive/ReceiveCommits.java @@ -3278,7 +3278,7 @@ class ReceiveCommits { } ListMultimap<ObjectId, Ref> byCommit = changeRefsById(); - Map<Change.Key, ChangeNotes> byKey = null; + Map<Change.Key, ChangeData> changeDataByKey = null; List<ReplaceRequest> replaceAndClose = new ArrayList<>(); int existingPatchSets = 0; @@ -3302,17 +3302,19 @@ class ReceiveCommits { } for (String changeId : c.getFooterLines(FooterConstants.CHANGE_ID)) { - if (byKey == null) { - byKey = executeIndexQuery(() -> openChangesByKeyByBranch(branch)); + if (changeDataByKey == null) { + changeDataByKey = executeIndexQuery(() -> openChangesByKeyByBranch(branch)); } - ChangeNotes onto = byKey.get(Change.key(changeId.trim())); + ChangeData onto = changeDataByKey.get(Change.key(changeId.trim())); if (onto != null) { newPatchSets++; // Hold onto this until we're done with the walk, as the call to // req.validate below calls isMergedInto which resets the walk. - ReplaceRequest req = new ReplaceRequest(onto.getChangeId(), c, cmd, false); - req.notes = onto; + ChangeNotes ontoNotes = onto.notes(); + ReplaceRequest req = + new ReplaceRequest(ontoNotes.getChangeId(), c, cmd, false); + req.notes = ontoNotes; replaceAndClose.add(req); continue COMMIT; } @@ -3384,13 +3386,16 @@ class ReceiveCommits { } } - private Map<Change.Key, ChangeNotes> openChangesByKeyByBranch(BranchNameKey branch) { + private Map<Change.Key, ChangeData> openChangesByKeyByBranch(BranchNameKey branch) { try (TraceTimer traceTimer = newTimer("openChangesByKeyByBranch", Metadata.builder().branchName(branch.branch()))) { - Map<Change.Key, ChangeNotes> r = new HashMap<>(); + Map<Change.Key, ChangeData> r = new HashMap<>(); for (ChangeData cd : queryProvider.get().byBranchOpen(branch)) { try { - r.put(cd.change().getKey(), cd.notes()); + // ChangeData is not materialised into a ChangeNotes for avoiding + // to load a potentially large number of changes meta-data into memory + // which would cause unnecessary disk I/O, CPU and heap utilisation. + r.put(cd.change().getKey(), cd); } catch (NoSuchChangeException e) { // Ignore deleted change } |