changeset 6743:ab60707314e9 stable

topic: new experimental.tns-reject-push config to refuse changesets with tns
author Anton Shestakov <av6@dwimlabs.net>
date Fri, 15 Mar 2024 17:05:09 -0300
parents 0592ae24c470
children 107c5af631a7
files hgext3rd/topic/__init__.py hgext3rd/topic/flow.py tests/test-namespaces-reject.t
diffstat 3 files changed, 125 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/hgext3rd/topic/__init__.py	Thu Mar 14 16:08:59 2024 -0300
+++ b/hgext3rd/topic/__init__.py	Fri Mar 15 17:05:09 2024 -0300
@@ -296,6 +296,9 @@
 configitem(b'experimental', b'tns-default-pull-namespaces',
            default=configitems.dynamicdefault,
 )
+configitem(b'experimental', b'tns-reject-push',
+           default=False,
+)
 configitem(b'experimental', b'topic-mode.server',
            default=configitems.dynamicdefault,
 )
@@ -914,6 +917,25 @@
                 else:
                     tr.addvalidator(b'000-reject-publish', _validate_publish)
 
+            if self.ui.configbool(b'experimental', b'tns-reject-push'):
+                if util.safehasattr(tr, '_validator'):
+                    # hg <= 5.3 (36f08ae87ef6)
+                    origvalidator_publish = tr._validator
+
+                def _validate_csets_with_tns(tr2):
+                    repo = reporef()
+                    flow.reject_csets_with_tns(repo, tr2)
+
+                def validator(tr2):
+                    _validate_csets_with_tns(tr2)
+                    return origvalidator_publish(tr2)
+
+                if util.safehasattr(tr, '_validator'):
+                    # hg <= 5.3 (36f08ae87ef6)
+                    tr._validator = validator
+                else:
+                    tr.addvalidator(b'000-reject-csets-with-tns', _validate_csets_with_tns)
+
             if util.safehasattr(tr, '_validator'):
                 # hg <= 5.3 (36f08ae87ef6)
                 origvalidator_affected_tns = tr._validator
--- a/hgext3rd/topic/flow.py	Thu Mar 14 16:08:59 2024 -0300
+++ b/hgext3rd/topic/flow.py	Fri Mar 15 17:05:09 2024 -0300
@@ -83,6 +83,29 @@
             msg += b' and %d others' % (len(published) - 1)
         raise error.Abort(msg)
 
+def reject_csets_with_tns(repo, tr):
+    """Reject the push if there are changesets with any topic namespace"""
+    if b'node' not in tr.hookargs: # no new revs
+        return
+
+    reject = repo.ui.config(b'experimental', b'tns-reject-push')
+    if not reject:
+        return
+
+    startnode = node.bin(tr.hookargs[b'node'])
+    repo = repo.unfiltered()
+    with_tns = repo.revs(b'not public() and extra("topic-namespace") and (%n:) - hidden()', startnode)
+    if with_tns:
+        num = len(with_tns)
+        cl = repo.changelog
+        fnode = node.short(cl.node(with_tns.first()))
+        if num == 1:
+            msg = _(b"%s") % fnode
+        else:
+            msg = _(b"%s and %d more") % (fnode, num - 1)
+        fullmsg = _(b"rejecting draft changesets with topic namespace: %s")
+        raise error.Abort(fullmsg % msg)
+
 def wrappush(orig, repo, remote, *args, **kwargs):
     """interpret the --publish flag and pass it to the push operation"""
     newargs = kwargs.copy()
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/tests/test-namespaces-reject.t	Fri Mar 15 17:05:09 2024 -0300
@@ -0,0 +1,80 @@
+Rejecting changesets with any topic namespaces during push
+
+  $ . "$TESTDIR/testlib/common.sh"
+
+  $ cat >> $HGRCPATH << EOF
+  > [extensions]
+  > topic =
+  > [phases]
+  > publish = no
+  > [devel]
+  > tns-report-transactions = push
+  > [ui]
+  > logtemplate = "{rev}: {desc} {fqbn} ({phase})\n"
+  > EOF
+
+  $ hg init orig
+  $ hg clone orig clone -q
+
+  $ cd clone
+
+changesets without topic namespace are freely exchanged
+
+  $ echo apple > a
+  $ hg debug-topic-namespace --clear
+  $ hg topic apple
+  marked working directory as topic: apple
+  $ hg ci -qAm apple
+
+  $ hg log -r . -T '{rev}: {join(extras, " ")}\n'
+  0: branch=default topic=apple
+
+  $ hg push
+  pushing to * (glob)
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  added 1 changesets with 1 changes to 1 files
+
+changesets with topic namespaces are rejected when server configuration disallows
+
+  $ cat >> ../orig/.hg/hgrc << EOF
+  > [experimental]
+  > tns-reject-push = yes
+  > EOF
+
+  $ echo banana > b
+  $ hg debug-topic-namespace bob
+  marked working directory as topic namespace: bob
+  $ hg topic banana
+  $ hg ci -qAm 'banana'
+
+  $ hg push
+  pushing to $TESTTMP/orig
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  transaction abort!
+  rollback completed
+  abort: rejecting draft changesets with topic namespace: ed9751f04a18
+  [255]
+
+changesets with topic namespaces are only exchanged if server configuration allows
+
+  $ cat >> ../orig/.hg/hgrc << EOF
+  > [experimental]
+  > tns-reject-push = no
+  > EOF
+
+  $ hg push
+  pushing to $TESTTMP/orig
+  searching for changes
+  adding changesets
+  adding manifests
+  adding file changes
+  topic namespaces affected: bob
+  added 1 changesets with 1 changes to 1 files
+
+  $ cd ..