push: add option to block hg push if no reason is provided

Summary:
We want to start tracking down why people use hg push instead of arc
land. To begin with, let's add an option that will require they provide a reason
to run hg push directly. Later we may block pushes or limit it to a whitelist in
some way.

Reviewed By: quark-zju

Differential Revision: D16156871

fbshipit-source-id: f46c039a91073fa3380d3b4b7f35722829eeb72a
This commit is contained in:
Durham Goode 2019-07-10 20:10:40 -07:00 committed by Facebook Github Bot
parent e936dde821
commit 2a6a9fed8a
3 changed files with 45 additions and 0 deletions

View File

@ -4868,6 +4868,13 @@ def push(ui, repo, dest=None, **opts):
[push]
pushvars.server = true
If ``push.requirereason`` is set to true, users will need to pass
``--pushvars PUSH_REASON="..."`` in order to push, and their reason will
be logged via ``ui.log(...)``.
``push.requirereasonmsg`` can be used to set the message shown to users
when they don't provide a reason.
Returns 0 if push was successful, 1 if nothing to push.
"""
@ -4914,6 +4921,16 @@ def push(ui, repo, dest=None, **opts):
_("default push revset for path evaluates to an " "empty set")
)
if ui.configbool("push", "requirereason"):
pushvar = "PUSH_REASON="
reasons = list(v for v in opts.get("pushvars", []) if v.startswith(pushvar))
if reasons:
reason = reasons[-1][len(pushvar):]
ui.log("pushreason", "bypassing push block with reason: %s", reason, pushreason=reason)
else:
msg = ui.config("push", "requirereasonmsg")
raise error.Abort(msg, hint="use `--pushvars PUSH_REASON='because ...'`")
opargs = dict(opts.get("opargs", {})) # copy opargs since we may mutate it
opargs.setdefault("pushvars", []).extend(opts.get("pushvars", []))

View File

@ -404,6 +404,8 @@ coreconfigitem("progress", "renderer", default="classic")
coreconfigitem("progress", "width", default=dynamicdefault)
coreconfigitem("pull", "automigrate", default=True)
coreconfigitem("push", "pushvars.server", default=True)
coreconfigitem("push", "requirereason", default=False)
coreconfigitem("push", "requirereasonmsg", default="")
coreconfigitem("sendunbundlereplay", "respondlightly", default=True)
coreconfigitem("server", "bookmarks-pushkey-compat", default=True)
coreconfigitem("server", "bundle1", default=True)

View File

@ -80,6 +80,7 @@ Test Python hooks
> ui.write("Got pushvar: %s=%s\n" % (k, v))
> EOF
$ cp $HGRCPATH $TESTTMP/hgrc.bak
$ cat >> $HGRCPATH << EOF
> [hooks]
> pretxnchangegroup.pyhook = python:$TESTTMP/pyhook.py:hook
@ -94,3 +95,28 @@ Test Python hooks
added 1 changesets with 1 changes to 1 files
Got pushvar: USERVAR_A=1
Got pushvar: USERVAR_B=2
$ cp $TESTTMP/hgrc.bak $HGRCPATH
Test pushvars for enforcing push reasons
$ cat >> .hg/hgrc <<EOF
> [push]
> requirereason=True
> requirereasonmsg="Because I said so"
> EOF
$ echo c >> a
$ hg commit -Aqm c
$ hg push
pushing to $TESTTMP/repo
abort: "Because I said so"
(use `--pushvars PUSH_REASON='because ...'`)
[255]
$ hg push --pushvars PUSH_REASON="I want to"
pushing to $TESTTMP/repo
searching for changes
adding changesets
adding manifests
adding file changes
added 1 changesets with 1 changes to 1 files
$ hg blackbox --pattern '{"legacy_log": {"service": "pushreason"}}'
* [legacy][pushreason] bypassing push block with reason: I want to (glob)
$ cp $TESTTMP/hgrc.bak $HGRCPATH