Merge "Remove obsolete methods and props from KeyboardShortcutMixinInterface"
diff --git a/java/com/google/gerrit/server/notedb/CommitRewriter.java b/java/com/google/gerrit/server/notedb/CommitRewriter.java
index 7d743dc..7f13731 100644
--- a/java/com/google/gerrit/server/notedb/CommitRewriter.java
+++ b/java/com/google/gerrit/server/notedb/CommitRewriter.java
@@ -58,7 +58,6 @@
import java.util.HashSet;
import java.util.List;
import java.util.Map;
-import java.util.Map.Entry;
import java.util.Objects;
import java.util.Optional;
import java.util.Set;
@@ -386,7 +385,7 @@
RevCommit originalCommit;
boolean rewriteStarted = false;
- ChangeFixProgress changeFixProgress = new ChangeFixProgress();
+ ChangeFixProgress changeFixProgress = new ChangeFixProgress(ref.getName());
while ((originalCommit = revWalk.next()) != null) {
changeFixProgress.updateAuthorId =
@@ -538,7 +537,9 @@
return Optional.of(
"Assignee deleted: "
+ getPossibleAccountReplacement(
- changeFixProgress, oldAssignee, assigneeDeletedMatcher.group(1)));
+ changeFixProgress,
+ oldAssignee,
+ ParsedAccountInfo.create(assigneeDeletedMatcher.group(1))));
}
return Optional.empty();
}
@@ -549,7 +550,9 @@
return Optional.of(
"Assignee added: "
+ getPossibleAccountReplacement(
- changeFixProgress, newAssignee, assigneeAddedMatcher.group(1)));
+ changeFixProgress,
+ newAssignee,
+ ParsedAccountInfo.create(assigneeAddedMatcher.group(1))));
}
return Optional.empty();
}
@@ -561,9 +564,13 @@
String.format(
"Assignee changed from: %s to: %s",
getPossibleAccountReplacement(
- changeFixProgress, oldAssignee, assigneeChangedMatcher.group(1)),
+ changeFixProgress,
+ oldAssignee,
+ ParsedAccountInfo.create(assigneeChangedMatcher.group(1))),
getPossibleAccountReplacement(
- changeFixProgress, newAssignee, assigneeChangedMatcher.group(2))));
+ changeFixProgress,
+ newAssignee,
+ ParsedAccountInfo.create(assigneeChangedMatcher.group(2)))));
}
return Optional.empty();
}
@@ -599,7 +606,7 @@
"Removed %s by %s",
matcher.group(1),
getPossibleAccountReplacement(
- changeFixProgress, reviewer, getNameFromNameEmail(matcher.group(2)))));
+ changeFixProgress, reviewer, getAccountInfoFromNameEmail(matcher.group(2)))));
}
return Optional.empty();
}
@@ -612,21 +619,27 @@
}
String[] lines = originalChangeMessage.split("\\r?\\n");
StringBuilder fixedLines = new StringBuilder();
+ boolean anyFixed = false;
for (int i = 1; i < lines.length; i++) {
if (lines[i].isEmpty()) {
continue;
}
Matcher matcher = REMOVED_VOTES_CHANGE_MESSAGE_PATTERN.matcher(lines[i]);
+ String replacementLine = lines[i];
if (matcher.matches() && !NON_REPLACE_ACCOUNT_PATTERN.matcher(matcher.group(2)).matches()) {
- fixedLines.append(
+ anyFixed = true;
+ replacementLine =
String.format(
"* %s by %s\n",
matcher.group(1),
getPossibleAccountReplacement(
- changeFixProgress, Optional.empty(), getNameFromNameEmail(matcher.group(2)))));
+ changeFixProgress,
+ Optional.empty(),
+ getAccountInfoFromNameEmail(matcher.group(2))));
}
+ fixedLines.append(replacementLine);
}
- if (fixedLines.length() == 0) {
+ if (!anyFixed) {
return Optional.empty();
}
return Optional.of(REMOVED_VOTES_CHANGE_MESSAGE_START + "\n" + fixedLines);
@@ -687,7 +700,8 @@
while (onAddReviewerMatcher.find()) {
String reviewerName = normalizeOnCodeOwnerAddReviewerMatch(onAddReviewerMatcher.group(1));
String replacementName =
- getPossibleAccountReplacement(changeFixProgress, Optional.empty(), reviewerName);
+ getPossibleAccountReplacement(
+ changeFixProgress, Optional.empty(), ParsedAccountInfo.create(reviewerName));
onAddReviewerMatcher.appendReplacement(
sb, replacementName + ", who was added as reviewer owns the following files");
}
@@ -971,9 +985,10 @@
private Optional<Account.Id> parseIdent(ChangeFixProgress changeFixProgress, PersonIdent ident) {
Optional<Account.Id> account = NoteDbUtil.parseIdent(ident);
if (account.isPresent()) {
- changeFixProgress.parsedAccounts.putIfAbsent(account.get(), "");
+ changeFixProgress.parsedAccounts.putIfAbsent(account.get(), Optional.empty());
} else {
- logger.atWarning().log("Failed to parse id %s", ident);
+ logger.atWarning().log(
+ "Fixing ref %s, failed to parse id %s", changeFixProgress.changeMetaRef, ident);
}
return account;
}
@@ -1022,10 +1037,16 @@
return fixIdentResult;
}
- /** Extracts {@link Account#getName} from {@link Account#getNameEmail} */
- private String getNameFromNameEmail(String nameEmail) {
+ /** Extracts {@link ParsedAccountInfo} from {@link Account#getNameEmail} */
+ private ParsedAccountInfo getAccountInfoFromNameEmail(String nameEmail) {
Matcher nameEmailMatcher = NAME_EMAIL_PATTERN.matcher(nameEmail);
- return nameEmailMatcher.matches() ? nameEmailMatcher.group(1) : nameEmail;
+ if (!nameEmailMatcher.matches()) {
+ return ParsedAccountInfo.create(nameEmail);
+ }
+
+ return ParsedAccountInfo.create(
+ nameEmailMatcher.group(1),
+ nameEmailMatcher.group(2).substring(1, nameEmailMatcher.group(2).length() - 1));
}
/**
@@ -1038,39 +1059,73 @@
*
* @param changeFixProgress see {@link ChangeFixProgress}
* @param account account that should be used for replacement, if known
- * @param accountName {@link Account#getName} to replace.
+ * @param accountInfo {@link ParsedAccountInfo} to replace.
* @return replacement for {@code accountName}
*/
private String getPossibleAccountReplacement(
- ChangeFixProgress changeFixProgress, Optional<Account.Id> account, String accountName) {
+ ChangeFixProgress changeFixProgress,
+ Optional<Account.Id> account,
+ ParsedAccountInfo accountInfo) {
if (account.isPresent()) {
return AccountTemplateUtil.getAccountTemplate(account.get());
}
// Retrieve reviewer accounts from cache and try to match by their name.
- Map<Account.Id, AccountState> missingUserNameReviewers =
+ Map<Account.Id, AccountState> missingAccountStateReviewers =
accountCache.get(
changeFixProgress.parsedAccounts.entrySet().stream()
- .filter(entry -> entry.getValue().isEmpty())
+ .filter(entry -> !entry.getValue().isPresent())
.map(Map.Entry::getKey)
.collect(ImmutableSet.toImmutableSet()));
changeFixProgress.parsedAccounts.putAll(
- missingUserNameReviewers.entrySet().stream()
+ missingAccountStateReviewers.entrySet().stream()
.collect(
ImmutableMap.toImmutableMap(
- Map.Entry::getKey, e -> e.getValue().account().getName())));
- Set<Account.Id> possibleReplacements =
- changeFixProgress.parsedAccounts.entrySet().stream()
- .filter(e -> e.getValue().equals(accountName))
- .map(Entry::getKey)
- .collect(ImmutableSet.toImmutableSet());
+ Map.Entry::getKey, e -> Optional.ofNullable(e.getValue()))));
+ Map<Account.Id, AccountState> possibleReplacements = ImmutableMap.of();
+ if (accountInfo.email().isPresent()) {
+ possibleReplacements =
+ changeFixProgress.parsedAccounts.entrySet().stream()
+ .filter(
+ e ->
+ e.getValue().isPresent()
+ && Objects.equals(
+ e.getValue().get().account().preferredEmail(),
+ accountInfo.email().get()))
+ .collect(ImmutableMap.toImmutableMap(Map.Entry::getKey, e -> e.getValue().get()));
+ // Filter further so we match both email & name
+ if (possibleReplacements.size() > 1) {
+ logger.atWarning().log(
+ "Fixing ref %s, multiple accounts found with the same email address, while replacing %s",
+ changeFixProgress.changeMetaRef, accountInfo);
+ possibleReplacements =
+ possibleReplacements.entrySet().stream()
+ .filter(e -> Objects.equals(e.getValue().account().getName(), accountInfo.name()))
+ .collect(ImmutableMap.toImmutableMap(Map.Entry::getKey, Map.Entry::getValue));
+ }
+ }
+ if (possibleReplacements.isEmpty()) {
+ possibleReplacements =
+ changeFixProgress.parsedAccounts.entrySet().stream()
+ .filter(
+ e ->
+ e.getValue().isPresent()
+ && Objects.equals(
+ e.getValue().get().account().getName(), accountInfo.name()))
+ .collect(ImmutableMap.toImmutableMap(Map.Entry::getKey, e -> e.getValue().get()));
+ }
String replacementName = DEFAULT_ACCOUNT_REPLACEMENT;
if (possibleReplacements.isEmpty()) {
- logger.atWarning().log("Could not find reviewer account matching name %s", accountName);
+ logger.atWarning().log(
+ "Fixing ref %s, could not find reviewer account matching name %s",
+ changeFixProgress.changeMetaRef, accountInfo);
} else if (possibleReplacements.size() > 1) {
- logger.atWarning().log("Found multiple reviewer account matching name %s", accountName);
+ logger.atWarning().log(
+ "Fixing ref %s found multiple reviewer account matching name %s",
+ changeFixProgress.changeMetaRef, accountInfo);
} else {
replacementName =
- AccountTemplateUtil.getAccountTemplate(Iterables.getOnlyElement(possibleReplacements));
+ AccountTemplateUtil.getAccountTemplate(
+ Iterables.getOnlyElement(possibleReplacements.keySet()));
}
return replacementName;
}
@@ -1135,6 +1190,10 @@
* recent update.
*/
private static class ChangeFixProgress {
+
+ /** {@link RefNames#changeMetaRef} of the change that is being fixed. */
+ final String changeMetaRef;
+
/** Assignee at current commit update. */
Account.Id assigneeId = null;
@@ -1146,7 +1205,7 @@
* #accountCache} if needed by rewrite. Maps to empty string if was not requested from cache
* yet.
*/
- Map<Account.Id, String> parsedAccounts = new HashMap<>();
+ Map<Account.Id, Optional<AccountState>> parsedAccounts = new HashMap<>();
/** Id of the current commit in rewriter walk. */
ObjectId newTipId = null;
@@ -1160,5 +1219,29 @@
boolean isValidAfterFix = true;
List<CommitDiff> commitDiffs = new ArrayList<>();
+
+ public ChangeFixProgress(String changeMetaRef) {
+ this.changeMetaRef = changeMetaRef;
+ }
+ }
+
+ /**
+ * Account info parsed from {@link Account#getNameEmail}. See {@link
+ * #getAccountInfoFromNameEmail}.
+ */
+ @AutoValue
+ abstract static class ParsedAccountInfo {
+
+ static ParsedAccountInfo create(String fullName, String email) {
+ return new AutoValue_CommitRewriter_ParsedAccountInfo(fullName, Optional.ofNullable(email));
+ }
+
+ static ParsedAccountInfo create(String fullName) {
+ return new AutoValue_CommitRewriter_ParsedAccountInfo(fullName, Optional.empty());
+ }
+
+ abstract String name();
+
+ abstract Optional<String> email();
}
}
diff --git a/javatests/com/google/gerrit/server/notedb/CommitRewriterTest.java b/javatests/com/google/gerrit/server/notedb/CommitRewriterTest.java
index 26e1881..f316660 100644
--- a/javatests/com/google/gerrit/server/notedb/CommitRewriterTest.java
+++ b/javatests/com/google/gerrit/server/notedb/CommitRewriterTest.java
@@ -837,6 +837,118 @@
}
@Test
+ public void fixRemoveVoteChangeMessageWithNoFooterLabel_matchByEmail() throws Exception {
+ Change c = newChange();
+ ChangeUpdate approvalUpdate = newUpdate(c, changeOwner);
+ approvalUpdate.putApproval(VERIFIED, (short) +2);
+
+ approvalUpdate.putApprovalFor(otherUserId, VERIFIED, (short) -1);
+ approvalUpdate.commit();
+ writeUpdate(
+ RefNames.changeMetaRef(c.getId()),
+ getChangeUpdateBody(
+ c, /*changeMessage=*/ "Removed Verified+2 by Renamed Change Owner <change@owner.com>"),
+ getAuthorIdent(changeOwner.getAccount()));
+
+ RunOptions options = new RunOptions();
+ options.dryRun = false;
+ BackfillResult result = rewriter.backfillProject(project, repo, options);
+ assertThat(result.fixedRefDiff.keySet()).containsExactly(RefNames.changeMetaRef(c.getId()));
+
+ List<String> commitHistoryDiff = commitHistoryDiff(result, c.getId());
+ assertThat(commitHistoryDiff)
+ .containsExactly(
+ "@@ -6 +6 @@\n"
+ + "-Removed Verified+2 by Renamed Change Owner <change@owner.com>\n"
+ + "+Removed Verified+2 by <GERRIT_ACCOUNT_1>\n");
+ BackfillResult secondRunResult = rewriter.backfillProject(project, repo, options);
+ assertThat(secondRunResult.fixedRefDiff.keySet()).isEmpty();
+ assertThat(secondRunResult.refsFailedToFix).isEmpty();
+ }
+
+ @Test
+ public void fixRemoveVoteChangeMessageWithNoFooterLabel_matchByName() throws Exception {
+ Change c = newChange();
+ ChangeUpdate approvalUpdate = newUpdate(c, changeOwner);
+ approvalUpdate.putApproval(VERIFIED, (short) +2);
+
+ approvalUpdate.putApprovalFor(otherUserId, VERIFIED, (short) -1);
+ approvalUpdate.commit();
+ writeUpdate(
+ RefNames.changeMetaRef(c.getId()),
+ getChangeUpdateBody(c, /*changeMessage=*/ "Removed Verified+2 by Change Owner"),
+ getAuthorIdent(changeOwner.getAccount()));
+
+ RunOptions options = new RunOptions();
+ options.dryRun = false;
+ BackfillResult result = rewriter.backfillProject(project, repo, options);
+ assertThat(result.fixedRefDiff.keySet()).containsExactly(RefNames.changeMetaRef(c.getId()));
+
+ List<String> commitHistoryDiff = commitHistoryDiff(result, c.getId());
+ assertThat(commitHistoryDiff)
+ .containsExactly(
+ "@@ -6 +6 @@\n"
+ + "-Removed Verified+2 by Change Owner\n"
+ + "+Removed Verified+2 by <GERRIT_ACCOUNT_1>\n");
+ BackfillResult secondRunResult = rewriter.backfillProject(project, repo, options);
+ assertThat(secondRunResult.fixedRefDiff.keySet()).isEmpty();
+ assertThat(secondRunResult.refsFailedToFix).isEmpty();
+ }
+
+ @Test
+ public void fixRemoveVoteChangeMessageWithNoFooterLabel_matchDuplicateAccounts()
+ throws Exception {
+ Account duplicateCodeOwner =
+ Account.builder(Account.id(4), TimeUtil.nowTs())
+ .setFullName(changeOwner.getName())
+ .setPreferredEmail("other@test.com")
+ .build();
+ accountCache.put(duplicateCodeOwner);
+ Change c = newChange();
+ ChangeUpdate approvalUpdate = newUpdate(c, changeOwner);
+ approvalUpdate.putApproval(VERIFIED, (short) +2);
+
+ approvalUpdate.putApprovalFor(duplicateCodeOwner.id(), VERIFIED, (short) -1);
+ approvalUpdate.commit();
+ writeUpdate(
+ RefNames.changeMetaRef(c.getId()),
+ getChangeUpdateBody(
+ c, /*changeMessage=*/ "Removed Verified+2 by Change Owner <other@test.com>"),
+ getAuthorIdent(changeOwner.getAccount()));
+ writeUpdate(
+ RefNames.changeMetaRef(c.getId()),
+ getChangeUpdateBody(
+ c, /*changeMessage=*/ "Removed Verified+2 by Change Owner <change@owner.com>"),
+ getAuthorIdent(changeOwner.getAccount()));
+ writeUpdate(
+ RefNames.changeMetaRef(c.getId()),
+ getChangeUpdateBody(
+ c, /*changeMessage=*/ "Removed Verified-1 by Change Owner <other@test.com>"),
+ getAuthorIdent(changeOwner.getAccount()));
+
+ RunOptions options = new RunOptions();
+ options.dryRun = false;
+ BackfillResult result = rewriter.backfillProject(project, repo, options);
+ assertThat(result.fixedRefDiff.keySet()).containsExactly(RefNames.changeMetaRef(c.getId()));
+
+ List<String> commitHistoryDiff = commitHistoryDiff(result, c.getId());
+ assertThat(commitHistoryDiff)
+ .containsExactly(
+ "@@ -6 +6 @@\n"
+ + "-Removed Verified+2 by Change Owner <other@test.com>\n"
+ + "+Removed Verified+2 by <GERRIT_ACCOUNT_4>\n",
+ "@@ -6 +6 @@\n"
+ + "-Removed Verified+2 by Change Owner <change@owner.com>\n"
+ + "+Removed Verified+2 by <GERRIT_ACCOUNT_1>\n",
+ "@@ -6 +6 @@\n"
+ + "-Removed Verified-1 by Change Owner <other@test.com>\n"
+ + "+Removed Verified-1 by <GERRIT_ACCOUNT_4>\n");
+ BackfillResult secondRunResult = rewriter.backfillProject(project, repo, options);
+ assertThat(secondRunResult.fixedRefDiff.keySet()).isEmpty();
+ assertThat(secondRunResult.refsFailedToFix).isEmpty();
+ }
+
+ @Test
public void fixRemoveVotesChangeMessage() throws Exception {
Change c = newChange();
ChangeUpdate approvalUpdate = newUpdate(c, changeOwner);
diff --git a/plugins/plugin-manager b/plugins/plugin-manager
index 5b87f63..ea992c3 160000
--- a/plugins/plugin-manager
+++ b/plugins/plugin-manager
@@ -1 +1 @@
-Subproject commit 5b87f63f3e9c5817bcddf008c0b4005494059368
+Subproject commit ea992c3b37eed5493c7031ee20faba9dd875170f
diff --git a/polygerrit-ui/app/elements/change-list/gr-user-header/gr-user-header.ts b/polygerrit-ui/app/elements/change-list/gr-user-header/gr-user-header.ts
index e87b4f9..05b5390 100644
--- a/polygerrit-ui/app/elements/change-list/gr-user-header/gr-user-header.ts
+++ b/polygerrit-ui/app/elements/change-list/gr-user-header/gr-user-header.ts
@@ -85,7 +85,7 @@
<div>
<span>Joined:</span>
<gr-date-formatter
- date-str="${this._computeDetail(
+ dateStr="${this._computeDetail(
this._accountDetails,
'registered_on'
)}"
diff --git a/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list.ts b/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list.ts
index b8f01de..40a2e1f 100644
--- a/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list.ts
+++ b/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list.ts
@@ -227,9 +227,6 @@
@property({type: Object, notify: true, observer: '_updateDiffPreferences'})
diffPrefs?: DiffPreferencesInfo;
- @property({type: Boolean})
- _showInlineDiffs?: boolean;
-
@property({type: Number, notify: true})
numFilesShown: number = DEFAULT_NUM_FILES_SHOWN;
@@ -629,8 +626,6 @@
}
expandAllDiffs() {
- this._showInlineDiffs = true;
-
// Find the list of paths that are in the file list, but not in the
// expanded list.
const newFiles: PatchSetFile[] = [];
@@ -646,7 +641,6 @@
}
collapseAllDiffs() {
- this._showInlineDiffs = false;
this._expandedFiles = [];
this.filesExpanded = this._computeExpandedFiles(
this._expandedFiles.length,
@@ -950,7 +944,7 @@
return;
}
- if (this._showInlineDiffs) {
+ if (this.filesExpanded === FilesExpandedState.ALL) {
e.preventDefault();
this.diffCursor.moveDown();
this._displayLine = true;
@@ -970,7 +964,7 @@
return;
}
- if (this._showInlineDiffs) {
+ if (this.filesExpanded === FilesExpandedState.ALL) {
e.preventDefault();
this.diffCursor.moveUp();
this._displayLine = true;
@@ -1020,7 +1014,7 @@
}
e.preventDefault();
- if (this._showInlineDiffs) {
+ if (this.filesExpanded === FilesExpandedState.ALL) {
this._openCursorFile();
return;
}
@@ -1086,7 +1080,7 @@
}
_toggleInlineDiffs() {
- if (this._showInlineDiffs) {
+ if (this.filesExpanded === FilesExpandedState.ALL) {
this.collapseAllDiffs();
} else {
this.expandAllDiffs();
diff --git a/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list_test.js b/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list_test.js
index 4acf245..b8c6cde 100644
--- a/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list_test.js
+++ b/polygerrit-ui/app/elements/change/gr-file-list/gr-file-list_test.js
@@ -593,7 +593,8 @@
for (const diff of element.diffs) {
assert.isTrue(element._expandedFiles.some(f => f.path === diff.path));
}
-
+ // since _expandedFilesChanged is stubbed
+ element.filesExpanded = FilesExpandedState.ALL;
MockInteractions.keyUpOn(element, 73, 'shift', 'i');
flush();
assert.equal(element.diffs.length, 0);
@@ -653,17 +654,17 @@
});
test('open from selected file', () => {
- element._showInlineDiffs = false;
+ element.filesExpanded = FilesExpandedState.NONE;
assert.deepEqual(interact(), {opened_selected: true});
});
test('open from diff cursor', () => {
- element._showInlineDiffs = true;
+ element.filesExpanded = FilesExpandedState.ALL;
assert.deepEqual(interact(), {opened_cursor: true});
});
test('expand when user prefers', () => {
- element._showInlineDiffs = false;
+ element.filesExpanded = FilesExpandedState.NONE;
assert.deepEqual(interact(), {opened_selected: true});
element._userPrefs = {};
assert.deepEqual(interact(), {opened_selected: true});
@@ -929,14 +930,14 @@
element._filesByPath = {[path]: {}};
element.expandAllDiffs();
flush();
- assert.isTrue(element._showInlineDiffs);
+ assert.equal(element.filesExpanded, FilesExpandedState.ALL);
assert.isTrue(reInitStub.calledOnce);
assert.equal(collapseStub.lastCall.args[0].length, 0);
element.collapseAllDiffs();
flush();
assert.equal(element._expandedFiles.length, 0);
- assert.isFalse(element._showInlineDiffs);
+ assert.equal(element.filesExpanded, FilesExpandedState.NONE);
assert.isTrue(cursorUpdateStub.calledOnce);
assert.equal(collapseStub.lastCall.args[0].length, 1);
});
@@ -1699,7 +1700,7 @@
// This is also called in diffCursor.moveToFirstChunk.
assert.equal(nextChunkStub.callCount, 1);
- assert.isTrue(element._showInlineDiffs);
+ assert.equal(element.filesExpanded, FilesExpandedState.ALL);
});
test('n key without all files expanded and no shift key', async () => {
@@ -1712,7 +1713,7 @@
// This is also called in diffCursor.moveToFirstChunk.
assert.equal(nextChunkStub.callCount, 0);
- assert.isTrue(element._showInlineDiffs);
+ assert.equal(element.filesExpanded, FilesExpandedState.ALL);
});
});
@@ -1736,7 +1737,7 @@
.callsFake(() => false);
sinon.stub(element, 'modifierPressed')
.callsFake(() => false);
- element._showInlineDiffs = true;
+ element.filesExpanded = FilesExpandedState.ALL;
const mockEvent = {preventDefault() {}};
element._displayLine = false;
diff --git a/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host.ts b/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host.ts
index 463163c..4641897 100644
--- a/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host.ts
+++ b/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host.ts
@@ -223,9 +223,6 @@
@property({type: Boolean})
_loggedIn = false;
- @property({type: Boolean})
- disableTokenHighlighting = false;
-
@property({type: String})
_errorMessage: string | null = null;
@@ -303,11 +300,6 @@
this.addEventListener('diff-context-expanded', event =>
this._handleDiffContextExpanded(event)
);
- appContext.restApiService.getPreferences().then(prefs => {
- if (prefs?.disable_token_highlighting) {
- this.disableTokenHighlighting = prefs.disable_token_highlighting;
- }
- });
}
override ready() {
@@ -335,18 +327,21 @@
super.disconnectedCallback();
}
- initLayers() {
- return getPluginLoader()
- .awaitPluginsLoaded()
- .then(() => {
- assertIsDefined(this.path, 'path');
- this._layers = this._getLayers(this.path);
- this._coverageRanges = [];
- // We kick off fetching the data here, but we don't return the promise,
- // so awaiting initLayers() will not wait for coverage data to be
- // completely loaded.
- this._getCoverageData();
- });
+ async initLayers() {
+ const preferencesPromise = appContext.restApiService.getPreferences();
+ await getPluginLoader().awaitPluginsLoaded();
+ const prefs = await preferencesPromise;
+ const enableTokenHighlight =
+ appContext.flagsService.isEnabled(KnownExperimentId.TOKEN_HIGHLIGHTING) &&
+ !prefs?.disable_token_highlighting;
+
+ assertIsDefined(this.path, 'path');
+ this._layers = this.getLayers(this.path, enableTokenHighlight);
+ this._coverageRanges = [];
+ // We kick off fetching the data here, but we don't return the promise,
+ // so awaiting initLayers() will not wait for coverage data to be
+ // completely loaded.
+ this._getCoverageData();
}
diffChanged(diff?: DiffInfo) {
@@ -418,12 +413,9 @@
}
}
- private _getLayers(path: string): DiffLayer[] {
+ private getLayers(path: string, enableTokenHighlight: boolean): DiffLayer[] {
const layers = [];
- if (
- appContext.flagsService.isEnabled(KnownExperimentId.TOKEN_HIGHLIGHTING) &&
- !this.disableTokenHighlighting
- ) {
+ if (enableTokenHighlight) {
layers.push(new TokenHighlightLayer(this));
}
layers.push(this.syntaxLayer);
@@ -740,7 +732,9 @@
_threadsChanged(threads: CommentThread[]) {
const threadEls = new Set<Object>();
for (const thread of threads) {
- threadEls.add(this._getOrCreateThread(thread));
+ const threadEl = this._createThreadElement(thread);
+ this._attachThreadElement(threadEl);
+ threadEls.add(threadEl);
}
// Remove all threads that are no longer existing.
for (const threadEl of this.getThreadEls()) {
diff --git a/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host_test.js b/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host_test.js
index 344f9d8..ed3ffe0 100644
--- a/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host_test.js
+++ b/polygerrit-ui/app/elements/diff/gr-diff-host/gr-diff-host_test.js
@@ -17,19 +17,16 @@
import '../../../test/common-test-setup-karma.js';
import './gr-diff-host.js';
-import {GrDiffBuilderImage} from '../gr-diff-builder/gr-diff-builder-image.js';
-import {GerritNav} from '../../core/gr-navigation/gr-navigation.js';
+
import {dom} from '@polymer/polymer/lib/legacy/polymer.dom.js';
-import {Side, createDefaultDiffPrefs} from '../../../constants/constants.js';
-import {createChange} from '../../../test/test-data-generators.js';
-import {CoverageType} from '../../../types/types.js';
-import {
- addListenerForTest,
- mockPromise,
- stubRestApi,
-} from '../../../test/test-utils.js';
-import {EditPatchSetNum, ParentPatchSetNum} from '../../../types/common.js';
+import {createDefaultDiffPrefs, Side} from '../../../constants/constants.js';
import {_testOnly_resetState} from '../../../services/comments/comments-model.js';
+import {createChange, createComment, createCommentThread} from '../../../test/test-data-generators.js';
+import {addListenerForTest, mockPromise, stubRestApi} from '../../../test/test-utils.js';
+import {EditPatchSetNum, ParentPatchSetNum} from '../../../types/common.js';
+import {CoverageType} from '../../../types/types.js';
+import {GerritNav} from '../../core/gr-navigation/gr-navigation.js';
+import {GrDiffBuilderImage} from '../gr-diff-builder/gr-diff-builder-image.js';
const basicFixture = fixtureFromElement('gr-diff-host');
@@ -1127,6 +1124,35 @@
assert.equal(threads[0].path, element.file.path);
});
+ test('multiple threads created on the same range', () => {
+ element.patchRange = {
+ basePatchNum: 2,
+ patchNum: 3,
+ };
+ element.file = {basePath: 'file_renamed.txt', path: element.path};
+
+ const comment = createComment();
+ comment.range = {
+ start_line: 1,
+ start_character: 1,
+ end_line: 2,
+ end_character: 2,
+ };
+ const thread = createCommentThread([comment]);
+ element.threads = [thread];
+
+ let threads = dom(element.$.diff)
+ .queryDistributedElements('gr-comment-thread');
+
+ assert.equal(threads.length, 1);
+
+ element.threads= [...element.threads, thread];
+
+ threads = dom(element.$.diff)
+ .queryDistributedElements('gr-comment-thread');
+ assert.equal(threads.length, 2);
+ });
+
test('thread should use new file path if first created' +
'on patch set (left) but is base', () => {
const diffSide = Side.LEFT;
@@ -1143,8 +1169,8 @@
},
}));
- const threads = dom(element.$.diff)
- .queryDistributedElements('gr-comment-thread');
+ const threads =
+ dom(element.$.diff).queryDistributedElements('gr-comment-thread');
assert.equal(threads.length, 1);
assert.equal(threads[0].diffSide, diffSide);
@@ -1167,8 +1193,8 @@
},
}));
- const threads = dom(element.$.diff)
- .queryDistributedElements('gr-comment-thread');
+ const threads =
+ dom(element.$.diff).queryDistributedElements('gr-comment-thread');
assert.equal(threads.length, 0);
assert.isTrue(alertSpy.called);
});
diff --git a/polygerrit-ui/app/elements/diff/gr-selection-action-box/gr-selection-action-box.ts b/polygerrit-ui/app/elements/diff/gr-selection-action-box/gr-selection-action-box.ts
index 3b026b3..8821725 100644
--- a/polygerrit-ui/app/elements/diff/gr-selection-action-box/gr-selection-action-box.ts
+++ b/polygerrit-ui/app/elements/diff/gr-selection-action-box/gr-selection-action-box.ts
@@ -15,6 +15,7 @@
* limitations under the License.
*/
import '../../../styles/shared-styles';
+import '../../shared/gr-tooltip/gr-tooltip';
import {GrTooltip} from '../../shared/gr-tooltip/gr-tooltip';
import {customElement, property} from '@polymer/decorators';
import {flush} from '@polymer/polymer/lib/legacy/polymer.dom';
diff --git a/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread.ts b/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread.ts
index b37613a..fe4a66a 100644
--- a/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread.ts
+++ b/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread.ts
@@ -57,7 +57,7 @@
import {GrButton} from '../gr-button/gr-button';
import {KnownExperimentId} from '../../../services/flags/flags';
import {DiffInfo, DiffPreferencesInfo} from '../../../types/diff';
-import {RenderPreferences} from '../../../api/diff';
+import {DiffLayer, RenderPreferences} from '../../../api/diff';
import {
check,
assertIsDefined,
@@ -205,8 +205,8 @@
@property({type: Object})
_selfAccount?: AccountDetailInfo;
- @property({type: Boolean})
- disableTokenHighlighting = false;
+ @property({type: Array})
+ layers: DiffLayer[] = [];
get keyBindings() {
return {
@@ -232,9 +232,7 @@
this._handleCommentUpdate(e as CustomEvent)
);
appContext.restApiService.getPreferences().then(prefs => {
- if (prefs?.disable_token_highlighting) {
- this.disableTokenHighlighting = prefs.disable_token_highlighting;
- }
+ this._initLayers(!!prefs?.disable_token_highlighting);
});
}
@@ -366,17 +364,14 @@
return undefined;
}
- _getLayers(diff?: DiffInfo) {
- if (!diff) return [];
- const layers = [];
+ _initLayers(disableTokenHighlighting: boolean) {
if (
this.flagsService.isEnabled(KnownExperimentId.TOKEN_HIGHLIGHTING) &&
- !this.disableTokenHighlighting
+ !disableTokenHighlighting
) {
- layers.push(new TokenHighlightLayer(this));
+ this.layers.push(new TokenHighlightLayer(this));
}
- layers.push(this.syntaxLayer);
- return layers;
+ this.layers.push(this.syntaxLayer);
}
_getUrlForViewDiff(
diff --git a/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread_html.ts b/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread_html.ts
index 0752a82..245f71c 100644
--- a/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread_html.ts
+++ b/polygerrit-ui/app/elements/shared/gr-comment-thread/gr-comment-thread_html.ts
@@ -232,7 +232,7 @@
id="diff"
change-num="[[changeNum]]"
diff="[[_diff]]"
- layers="[[_getLayers(_diff)]]"
+ layers="[[layers]]"
path="[[path]]"
prefs="[[_prefs]]"
render-prefs="[[_renderPrefs]]"