diff options
author | Daniel Smith <[email protected]> | 2025-08-18 11:38:18 +0200 |
---|---|---|
committer | Daniel Smith <[email protected]> | 2025-08-18 12:01:37 +0000 |
commit | a941ffb3443ed90ceac7cbeff9db1b1ccab1bd3a (patch) | |
tree | b96ad7933d304956cba276df4d6bd28c2b9437a0 | |
parent | 7b949aea7a4f6534fe6eb3dcca5688dee06231eb (diff) |
Allow configurable exceptions to empty-commit staging restrictionsv3.10-based
In the case of [ChangeLog] tagged commits, it can be appropriate
to stage/merge an empty commit which acts as an update to
Changelog generators, but does not modify code.
Fixes: QTQAINFRA-7343
Change-Id: I173e050866e58c357db4020dc80590d5cc1166bc
Reviewed-by: Jukka Jokiniva <[email protected]>
-rw-r--r-- | src/main/java/com/googlesource/gerrit/plugins/qtcodereview/QtCherryPickPatch.java | 31 | ||||
-rw-r--r-- | src/test/java/com/googlesource/gerrit/plugins/qtcodereview/QtStageIT.java | 26 |
2 files changed, 56 insertions, 1 deletions
diff --git a/src/main/java/com/googlesource/gerrit/plugins/qtcodereview/QtCherryPickPatch.java b/src/main/java/com/googlesource/gerrit/plugins/qtcodereview/QtCherryPickPatch.java index 23ec133..ef9c1e5 100644 --- a/src/main/java/com/googlesource/gerrit/plugins/qtcodereview/QtCherryPickPatch.java +++ b/src/main/java/com/googlesource/gerrit/plugins/qtcodereview/QtCherryPickPatch.java @@ -26,16 +26,22 @@ import com.google.gerrit.server.update.context.RefUpdateContext; import com.google.inject.Inject; import com.google.inject.Provider; import com.google.inject.Singleton; +import java.io.IOException; import java.sql.Timestamp; import java.util.Arrays; import java.util.Date; import java.util.List; +import org.eclipse.jgit.errors.ConfigInvalidException; +import org.eclipse.jgit.lib.Config; import org.eclipse.jgit.lib.ObjectId; import org.eclipse.jgit.lib.ObjectInserter; import org.eclipse.jgit.lib.ObjectReader; import org.eclipse.jgit.lib.PersonIdent; import org.eclipse.jgit.lib.Repository; import org.eclipse.jgit.revwalk.RevCommit; +import org.eclipse.jgit.storage.file.FileBasedConfig; +import org.eclipse.jgit.util.FS; +import org.eclipse.jgit.util.SystemReader; @Singleton public class QtCherryPickPatch { @@ -145,7 +151,30 @@ public class QtCherryPickPatch { false); // allowConflicts if (cherryPickCommit.getTree().equals(baseCommit.getTree())) { - throw new IntegrationConflictException("Cannot stage change: The patch set is empty."); + Config cfg; + try { + FileBasedConfig userConfig = SystemReader.getInstance().openUserConfig(null, FS.DETECTED); + userConfig.load(); + cfg = userConfig; + } catch (IOException | ConfigInvalidException e) { + logger.atWarning().withCause(e).log("Could not load user gitconfig"); + cfg = new Config(); + } + String exceptions = cfg.getString("qtcodereview", null, "emptyCommitExceptions"); + logger.atInfo().log( + "Found empty commit exceptions: %s", exceptions); + boolean allowed = false; + if (exceptions != null && !exceptions.isEmpty()) { + String originalCommitMessage = commitToCherryPick.getFullMessage(); + allowed = + Arrays.stream(exceptions.split(",")) + .map(String::trim) + .filter(s -> !s.isEmpty()) + .anyMatch(originalCommitMessage::contains); + } + if (!allowed) { + throw new IntegrationConflictException("Cannot stage change: The patch set is empty."); + } } boolean patchSetNotChanged = cherryPickCommit.equals(commitToCherryPick); diff --git a/src/test/java/com/googlesource/gerrit/plugins/qtcodereview/QtStageIT.java b/src/test/java/com/googlesource/gerrit/plugins/qtcodereview/QtStageIT.java index 5c9b616..dee9a1d 100644 --- a/src/test/java/com/googlesource/gerrit/plugins/qtcodereview/QtStageIT.java +++ b/src/test/java/com/googlesource/gerrit/plugins/qtcodereview/QtStageIT.java @@ -23,8 +23,11 @@ import com.google.gerrit.extensions.client.ChangeStatus; import java.util.ArrayList; import org.apache.http.HttpStatus; import org.eclipse.jgit.revwalk.RevCommit; +import org.eclipse.jgit.storage.file.FileBasedConfig; import org.eclipse.jgit.transport.PushResult; import org.eclipse.jgit.transport.RemoteRefUpdate; +import org.eclipse.jgit.util.FS; +import org.eclipse.jgit.util.SystemReader; import org.junit.Before; import org.junit.Test; @@ -147,6 +150,29 @@ public class QtStageIT extends QtCodeReviewIT { } @Test + public void emptyChange_Stage_AllowException() throws Exception { + + // Store exception string + FileBasedConfig gitConfig = SystemReader.getInstance().openUserConfig(null, FS.DETECTED); + gitConfig.load(); + gitConfig.setString("qtcodereview", null, "emptyCommitExceptions", "[ChangeLog]"); + gitConfig.save(); + + RevCommit initialHead = getRemoteHead(); + PushOneCommit.Result c = pushCommit("master", "1st commit]", "afile", ""); + approve(c.getChangeId()); + RevCommit stagingHead = qtStage(c); + assertApproval(c.getChangeId(), admin); + + // no changes in this commit, but an exception string in commit message + c = pushCommit("master", "2nd commit:no content\n[ChangeLog]", "afile", ""); + approve(c.getChangeId()); + + stagingHead = qtStage(c); + assertApproval(c.getChangeId(), admin); + } + + @Test public void emptyChange_Stage_expectFail() throws Exception { RevCommit initialHead = getRemoteHead(); PushOneCommit.Result c = pushCommit("master", "1st commit", "afile", ""); |