annotate mercurial/hook.py @ 40815:e2697acd9381

cleanup: some Yoda conditions, this patch removes It seems the factor 20 is less than the frequency of " < \d" compared to " \d > ". Differential Revision: https://phab.mercurial-scm.org/D4862
author Martin von Zweigbergk <martinvonz@google.com>
date Wed, 03 Oct 2018 10:27:44 -0700
parents 24e493ec2229
children 8c8fcb385c46
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
1 # hook.py - hook support for mercurial
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
2 #
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
3 # Copyright 2007 Matt Mackall <mpm@selenic.com>
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
4 #
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 8209
diff changeset
5 # This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 10103
diff changeset
6 # GNU General Public License version 2 or any later version.
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
7
26537
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
8 from __future__ import absolute_import
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
9
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
10 import os
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
11 import sys
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
12
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
13 from .i18n import _
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
14 from . import (
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
15 demandimport,
33425
c032e137e494 py3: convert exception to bytes to pass into ui.warn()
Pulkit Goyal <7895pulkit@gmail.com>
parents: 33397
diff changeset
16 encoding,
26537
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
17 error,
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
18 extensions,
31298
20a42325fdef py3: use pycompat.getcwd() instead of os.getcwd()
Pulkit Goyal <7895pulkit@gmail.com>
parents: 31252
diff changeset
19 pycompat,
26537
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
20 util,
d15b279ddade hook: use absolute_import
Gregory Szorc <gregory.szorc@gmail.com>
parents: 26214
diff changeset
21 )
37905
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
22 from .utils import (
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
23 procutil,
38537
483de34f23b1 hook: use stringutil.pprint instead of reinventing it
Augie Fackler <augie@google.com>
parents: 38249
diff changeset
24 stringutil,
37905
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
25 )
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
26
38827
242eb5132203 filemerge: support specifying a python function to custom merge-tools
hindlemail <tom_hindle@sil.org>
parents: 38728
diff changeset
27 def pythonhook(ui, repo, htype, hname, funcname, args, throw):
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
28 '''call python hook. hook is callable object, looked up as
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
29 name in python module. if callable returns "true", hook
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
30 fails, else passes. if hook raises exception, treated as
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
31 hook failure. exception propagates if throw is "true".
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
32
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
33 reason for "true" meaning "hook failed" is so that
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
34 unmodified commands (e.g. mercurial.commands.update) can
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
35 be run as hooks without wrappers to convert return values.'''
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
36
21797
b009dd135aa0 hook: restore use of callable() since it was readded in Python 3.2
Augie Fackler <raf@durin42.com>
parents: 20548
diff changeset
37 if callable(funcname):
20548
5bd6a9fec103 hooks: for python hooks, consistently use __name__ etc as name, not the repr
Mads Kiilerich <madski@unity3d.com>
parents: 20547
diff changeset
38 obj = funcname
33397
4b426ae96ff2 py3: ensure that we don't concat bytes and str and the end result is bytes
Pulkit Goyal <7895pulkit@gmail.com>
parents: 32526
diff changeset
39 funcname = pycompat.sysbytes(obj.__module__ + r"." + obj.__name__)
20548
5bd6a9fec103 hooks: for python hooks, consistently use __name__ etc as name, not the repr
Mads Kiilerich <madski@unity3d.com>
parents: 20547
diff changeset
40 else:
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
41 d = funcname.rfind('.')
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
42 if d == -1:
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
43 raise error.HookLoadError(
28777
cedbe8723d99 hook: even fewer parentheses for load errors
Siddharth Agarwal <sid0@fb.com>
parents: 28751
diff changeset
44 _('%s hook is invalid: "%s" not in a module')
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
45 % (hname, funcname))
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
46 modname = funcname[:d]
10103
37679dbf2ee3 hook: fix bug (reuse of variable) introduced in 872d49dd577a
Sune Foldager <cryo@cyanite.org>
parents: 9851
diff changeset
47 oldpaths = sys.path
37906
a8a902d7176e procutil: bulk-replace function calls to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37905
diff changeset
48 if procutil.mainfrozen():
9332
872d49dd577a hook: fix full path imports on Windows (issue1779)
Steve Borho <steve@borho.org>
parents: 8366
diff changeset
49 # binary installs require sys.path manipulation
10103
37679dbf2ee3 hook: fix bug (reuse of variable) introduced in 872d49dd577a
Sune Foldager <cryo@cyanite.org>
parents: 9851
diff changeset
50 modpath, modfile = os.path.split(modname)
37679dbf2ee3 hook: fix bug (reuse of variable) introduced in 872d49dd577a
Sune Foldager <cryo@cyanite.org>
parents: 9851
diff changeset
51 if modpath and modfile:
37679dbf2ee3 hook: fix bug (reuse of variable) introduced in 872d49dd577a
Sune Foldager <cryo@cyanite.org>
parents: 9851
diff changeset
52 sys.path = sys.path[:] + [modpath]
37679dbf2ee3 hook: fix bug (reuse of variable) introduced in 872d49dd577a
Sune Foldager <cryo@cyanite.org>
parents: 9851
diff changeset
53 modname = modfile
25812
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
54 with demandimport.deactivated():
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
55 try:
36894
c4146cf4dd20 py3: use system strings when calling __import__
Gregory Szorc <gregory.szorc@gmail.com>
parents: 36140
diff changeset
56 obj = __import__(pycompat.sysstr(modname))
28780
b892e424f88c hook: don't crash on syntax errors in python hooks
Siddharth Agarwal <sid0@fb.com>
parents: 28779
diff changeset
57 except (ImportError, SyntaxError):
28749
2058e1a894f2 hook: use sys.exc_info rather than the deprecated equivalents
Siddharth Agarwal <sid0@fb.com>
parents: 27868
diff changeset
58 e1 = sys.exc_info()
25812
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
59 try:
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
60 # extensions are loaded with hgext_ prefix
36894
c4146cf4dd20 py3: use system strings when calling __import__
Gregory Szorc <gregory.szorc@gmail.com>
parents: 36140
diff changeset
61 obj = __import__(r"hgext_%s" % pycompat.sysstr(modname))
28780
b892e424f88c hook: don't crash on syntax errors in python hooks
Siddharth Agarwal <sid0@fb.com>
parents: 28779
diff changeset
62 except (ImportError, SyntaxError):
28749
2058e1a894f2 hook: use sys.exc_info rather than the deprecated equivalents
Siddharth Agarwal <sid0@fb.com>
parents: 27868
diff changeset
63 e2 = sys.exc_info()
25812
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
64 if ui.tracebackflag:
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
65 ui.warn(_('exception from first failed import '
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
66 'attempt:\n'))
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
67 ui.traceback(e1)
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
68 if ui.tracebackflag:
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
69 ui.warn(_('exception from second failed import '
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
70 'attempt:\n'))
2cfb0bbf83a1 hooks: replace if-try-finally with a "with" statement
Jordi Gutiérrez Hermoso <jordigh@octave.org>
parents: 25619
diff changeset
71 ui.traceback(e2)
28751
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
72
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
73 if not ui.tracebackflag:
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
74 tracebackhint = _(
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
75 'run with --traceback for stack trace')
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
76 else:
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
77 tracebackhint = None
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
78 raise error.HookLoadError(
28750
0c9e914029be hook: fewer parentheses for hook load errors
Siddharth Agarwal <sid0@fb.com>
parents: 28749
diff changeset
79 _('%s hook is invalid: import of "%s" failed') %
28751
37b818cad146 hook: for python hook ImportErrors, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28750
diff changeset
80 (hname, modname), hint=tracebackhint)
9332
872d49dd577a hook: fix full path imports on Windows (issue1779)
Steve Borho <steve@borho.org>
parents: 8366
diff changeset
81 sys.path = oldpaths
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
82 try:
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
83 for p in funcname.split('.')[1:]:
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
84 obj = getattr(obj, p)
7278
810ca383da9c remove unused variables
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 6764
diff changeset
85 except AttributeError:
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
86 raise error.HookLoadError(
28750
0c9e914029be hook: fewer parentheses for hook load errors
Siddharth Agarwal <sid0@fb.com>
parents: 28749
diff changeset
87 _('%s hook is invalid: "%s" is not defined')
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
88 % (hname, funcname))
21797
b009dd135aa0 hook: restore use of callable() since it was readded in Python 3.2
Augie Fackler <raf@durin42.com>
parents: 20548
diff changeset
89 if not callable(obj):
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
90 raise error.HookLoadError(
28750
0c9e914029be hook: fewer parentheses for hook load errors
Siddharth Agarwal <sid0@fb.com>
parents: 28749
diff changeset
91 _('%s hook is invalid: "%s" is not callable')
27332
8d1cfd77b64f hook: raise a separate exception for when loading a hook fails
Siddharth Agarwal <sid0@fb.com>
parents: 27227
diff changeset
92 % (hname, funcname))
20547
9d9f8ccffead hooks: move logging of hook name to after we have found the hook
Mads Kiilerich <madski@unity3d.com>
parents: 20422
diff changeset
93
9d9f8ccffead hooks: move logging of hook name to after we have found the hook
Mads Kiilerich <madski@unity3d.com>
parents: 20422
diff changeset
94 ui.note(_("calling hook %s: %s\n") % (hname, funcname))
31754
22fbca1d11ed mercurial: switch to util.timer for all interval timings
Simon Farnsworth <simonfar@fb.com>
parents: 31298
diff changeset
95 starttime = util.timer()
20547
9d9f8ccffead hooks: move logging of hook name to after we have found the hook
Mads Kiilerich <madski@unity3d.com>
parents: 20422
diff changeset
96
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
97 try:
36140
056a9c8813aa py3: handle keyword arguments correctly in hook.py
Pulkit Goyal <7895pulkit@gmail.com>
parents: 35470
diff changeset
98 r = obj(ui=ui, repo=repo, hooktype=htype, **pycompat.strkwargs(args))
26214
328739ea70c3 global: mass rewrite to use modern exception syntax
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25812
diff changeset
99 except Exception as exc:
27227
56b2bcea2529 error: get Abort from 'error' instead of 'util'
Pierre-Yves David <pierre-yves.david@fb.com>
parents: 26537
diff changeset
100 if isinstance(exc, error.Abort):
25495
7046c7e7fcb4 hooks: use try/except/finally
Matt Mackall <mpm@selenic.com>
parents: 24860
diff changeset
101 ui.warn(_('error: %s hook failed: %s\n') %
7046c7e7fcb4 hooks: use try/except/finally
Matt Mackall <mpm@selenic.com>
parents: 24860
diff changeset
102 (hname, exc.args[0]))
7046c7e7fcb4 hooks: use try/except/finally
Matt Mackall <mpm@selenic.com>
parents: 24860
diff changeset
103 else:
7046c7e7fcb4 hooks: use try/except/finally
Matt Mackall <mpm@selenic.com>
parents: 24860
diff changeset
104 ui.warn(_('error: %s hook raised an exception: '
33425
c032e137e494 py3: convert exception to bytes to pass into ui.warn()
Pulkit Goyal <7895pulkit@gmail.com>
parents: 33397
diff changeset
105 '%s\n') % (hname, encoding.strtolocal(str(exc))))
25495
7046c7e7fcb4 hooks: use try/except/finally
Matt Mackall <mpm@selenic.com>
parents: 24860
diff changeset
106 if throw:
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
107 raise
28779
2a71d9483199 hook: for python hook exceptions, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28777
diff changeset
108 if not ui.tracebackflag:
2a71d9483199 hook: for python hook exceptions, add note to run with --traceback
Siddharth Agarwal <sid0@fb.com>
parents: 28777
diff changeset
109 ui.warn(_('(run with --traceback for stack trace)\n'))
25495
7046c7e7fcb4 hooks: use try/except/finally
Matt Mackall <mpm@selenic.com>
parents: 24860
diff changeset
110 ui.traceback()
27379
8429369eeb85 hook: for python hooks, also return whether an exception was raised
Siddharth Agarwal <sid0@fb.com>
parents: 27378
diff changeset
111 return True, True
14889
a59058fd074a hooks: redirect stdout/err/in to the ui descriptors when calling python hooks
Idan Kamara <idankk86@gmail.com>
parents: 14711
diff changeset
112 finally:
31754
22fbca1d11ed mercurial: switch to util.timer for all interval timings
Simon Farnsworth <simonfar@fb.com>
parents: 31298
diff changeset
113 duration = util.timer() - starttime
18691
4f485bd68f1d blackbox: do not translate the log messages
Durham Goode <durham@fb.com>
parents: 18671
diff changeset
114 ui.log('pythonhook', 'pythonhook-%s: %s finished in %0.2f seconds\n',
32521
f243b7fbeba5 hook: use "htype" as variable name in _pythonhook
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 31984
diff changeset
115 htype, funcname, duration)
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
116 if r:
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
117 if throw:
23415
cdbb85489c41 hook: raise a more specialized HookAbort exception when a hook fails
Pierre-Yves David <pierre-yves.david@fb.com>
parents: 21797
diff changeset
118 raise error.HookAbort(_('%s hook failed') % hname)
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
119 ui.warn(_('warning: %s hook failed\n') % hname)
27379
8429369eeb85 hook: for python hooks, also return whether an exception was raised
Siddharth Agarwal <sid0@fb.com>
parents: 27378
diff changeset
120 return r, False
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
121
32525
0fa30fbccc34 hook: provide hook type information to external hook
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32524
diff changeset
122 def _exthook(ui, repo, htype, name, cmd, args, throw):
31754
22fbca1d11ed mercurial: switch to util.timer for all interval timings
Simon Farnsworth <simonfar@fb.com>
parents: 31298
diff changeset
123 starttime = util.timer()
7787
b8d750daadde Introduce HG_PREPEND to solve pretxn races
Matt Mackall <mpm@selenic.com>
parents: 7644
diff changeset
124 env = {}
27391
520defbc0335 hook: centralize passing HG_PENDING to external hook process
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 27379
diff changeset
125
520defbc0335 hook: centralize passing HG_PENDING to external hook process
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 27379
diff changeset
126 # make in-memory changes visible to external process
27868
10695f8f3323 dirstate: don't write repo.currenttransaction to repo.dirstate if repo
Sietse Brouwer <sbbrouwer@gmail.com>
parents: 27501
diff changeset
127 if repo is not None:
10695f8f3323 dirstate: don't write repo.currenttransaction to repo.dirstate if repo
Sietse Brouwer <sbbrouwer@gmail.com>
parents: 27501
diff changeset
128 tr = repo.currenttransaction()
10695f8f3323 dirstate: don't write repo.currenttransaction to repo.dirstate if repo
Sietse Brouwer <sbbrouwer@gmail.com>
parents: 27501
diff changeset
129 repo.dirstate.write(tr)
10695f8f3323 dirstate: don't write repo.currenttransaction to repo.dirstate if repo
Sietse Brouwer <sbbrouwer@gmail.com>
parents: 27501
diff changeset
130 if tr and tr.writepending():
10695f8f3323 dirstate: don't write repo.currenttransaction to repo.dirstate if repo
Sietse Brouwer <sbbrouwer@gmail.com>
parents: 27501
diff changeset
131 env['HG_PENDING'] = repo.root
32525
0fa30fbccc34 hook: provide hook type information to external hook
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32524
diff changeset
132 env['HG_HOOKTYPE'] = htype
32526
aff7b32b3c05 hook: add hook name information to external hook
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32525
diff changeset
133 env['HG_HOOKNAME'] = name
27391
520defbc0335 hook: centralize passing HG_PENDING to external hook process
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 27379
diff changeset
134
7787
b8d750daadde Introduce HG_PREPEND to solve pretxn races
Matt Mackall <mpm@selenic.com>
parents: 7644
diff changeset
135 for k, v in args.iteritems():
21797
b009dd135aa0 hook: restore use of callable() since it was readded in Python 3.2
Augie Fackler <raf@durin42.com>
parents: 20548
diff changeset
136 if callable(v):
7787
b8d750daadde Introduce HG_PREPEND to solve pretxn races
Matt Mackall <mpm@selenic.com>
parents: 7644
diff changeset
137 v = v()
38538
63b7415e37a5 hook: also use pprint on lists for stable output on py2/3
Augie Fackler <augie@google.com>
parents: 38537
diff changeset
138 if isinstance(v, (dict, list)):
38728
32bc3815efae stringutil: flip the default of pprint() to bprefix=False
Yuya Nishihara <yuya@tcha.org>
parents: 38538
diff changeset
139 v = stringutil.pprint(v)
7787
b8d750daadde Introduce HG_PREPEND to solve pretxn races
Matt Mackall <mpm@selenic.com>
parents: 7644
diff changeset
140 env['HG_' + k.upper()] = v
b8d750daadde Introduce HG_PREPEND to solve pretxn races
Matt Mackall <mpm@selenic.com>
parents: 7644
diff changeset
141
39508
2009d84f245a hook: disable the shell to native command translation by default
Matt Harbison <matt_harbison@yahoo.com>
parents: 39415
diff changeset
142 if ui.configbool('hooks', 'tonative.%s' % name, False):
39509
f9b2d996ffa5 hook: only print the note about native cmd translation if it actually changes
Matt Harbison <matt_harbison@yahoo.com>
parents: 39508
diff changeset
143 oldcmd = cmd
39415
38dfd308fe9d hook: add support for disabling the shell to native command translation
Matt Harbison <matt_harbison@yahoo.com>
parents: 39414
diff changeset
144 cmd = procutil.shelltonative(cmd, env)
39509
f9b2d996ffa5 hook: only print the note about native cmd translation if it actually changes
Matt Harbison <matt_harbison@yahoo.com>
parents: 39508
diff changeset
145 if cmd != oldcmd:
f9b2d996ffa5 hook: only print the note about native cmd translation if it actually changes
Matt Harbison <matt_harbison@yahoo.com>
parents: 39508
diff changeset
146 ui.note(_('converting hook "%s" to native\n') % name)
39270
e9e61fbac787 hooks: allow Unix style environment variables on external Windows hooks
Matt Harbison <matt_harbison@yahoo.com>
parents: 38827
diff changeset
147
e9e61fbac787 hooks: allow Unix style environment variables on external Windows hooks
Matt Harbison <matt_harbison@yahoo.com>
parents: 38827
diff changeset
148 ui.note(_("running hook %s: %s\n") % (name, cmd))
e9e61fbac787 hooks: allow Unix style environment variables on external Windows hooks
Matt Harbison <matt_harbison@yahoo.com>
parents: 38827
diff changeset
149
5876
2c565b9598b8 hooks: fix pre- and post- hooks specified in .hg/hgrc
Matt Mackall <mpm@selenic.com>
parents: 5834
diff changeset
150 if repo:
2c565b9598b8 hooks: fix pre- and post- hooks specified in .hg/hgrc
Matt Mackall <mpm@selenic.com>
parents: 5834
diff changeset
151 cwd = repo.root
2c565b9598b8 hooks: fix pre- and post- hooks specified in .hg/hgrc
Matt Mackall <mpm@selenic.com>
parents: 5834
diff changeset
152 else:
40604
24e493ec2229 py3: rename pycompat.getcwd() to encoding.getcwd() (API)
Matt Harbison <matt_harbison@yahoo.com>
parents: 39509
diff changeset
153 cwd = encoding.getcwd()
31984
a48c6ac5c13a hook: give exthooks tags for blocking time
Simon Farnsworth <simonfar@fb.com>
parents: 31754
diff changeset
154 r = ui.system(cmd, environ=env, cwd=cwd, blockedtag='exthook-%s' % (name,))
18671
1c305128e5b9 blackbox: logs python and extension hooks via ui.log()
Durham Goode <durham@fb.com>
parents: 18111
diff changeset
155
31754
22fbca1d11ed mercurial: switch to util.timer for all interval timings
Simon Farnsworth <simonfar@fb.com>
parents: 31298
diff changeset
156 duration = util.timer() - starttime
18691
4f485bd68f1d blackbox: do not translate the log messages
Durham Goode <durham@fb.com>
parents: 18671
diff changeset
157 ui.log('exthook', 'exthook-%s: %s finished in %0.2f seconds\n',
18671
1c305128e5b9 blackbox: logs python and extension hooks via ui.log()
Durham Goode <durham@fb.com>
parents: 18111
diff changeset
158 name, cmd, duration)
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
159 if r:
38249
bbd240f81ac5 procutil: make explainexit() simply return a message (API)
Yuya Nishihara <yuya@tcha.org>
parents: 37906
diff changeset
160 desc = procutil.explainexit(r)
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
161 if throw:
23415
cdbb85489c41 hook: raise a more specialized HookAbort exception when a hook fails
Pierre-Yves David <pierre-yves.david@fb.com>
parents: 21797
diff changeset
162 raise error.HookAbort(_('%s hook %s') % (name, desc))
4623
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
163 ui.warn(_('warning: %s hook %s\n') % (name, desc))
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
164 return r
fff50306e6dd hooks: separate hook code into a separate module
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
165
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
166 # represent an untrusted hook command
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
167 _fromuntrusted = object()
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
168
15896
30c34fde40cc hooks: prioritize run order of hooks
Matt Zuba <matt.zuba@goodwillaz.org>
parents: 15521
diff changeset
169 def _allhooks(ui):
29687
3112c5e18835 hook: split config reading further
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29686
diff changeset
170 """return a list of (hook-id, cmd) pairs sorted by priority"""
3112c5e18835 hook: split config reading further
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29686
diff changeset
171 hooks = _hookitems(ui)
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
172 # Be careful in this section, propagating the real commands from untrusted
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
173 # sources would create a security vulnerability, make sure anything altered
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
174 # in that section uses "_fromuntrusted" as its command.
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
175 untrustedhooks = _hookitems(ui, _untrusted=True)
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
176 for name, value in untrustedhooks.items():
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
177 trustedvalue = hooks.get(name, (None, None, name, _fromuntrusted))
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
178 if value != trustedvalue:
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
179 (lp, lo, lk, lv) = trustedvalue
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
180 hooks[name] = (lp, lo, lk, _fromuntrusted)
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
181 # (end of the security sensitive section)
29687
3112c5e18835 hook: split config reading further
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29686
diff changeset
182 return [(k, v) for p, o, k, v in sorted(hooks.values())]
3112c5e18835 hook: split config reading further
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29686
diff changeset
183
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
184 def _hookitems(ui, _untrusted=False):
29687
3112c5e18835 hook: split config reading further
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29686
diff changeset
185 """return all hooks items ready to be sorted"""
29686
44bd37af54e5 hook: small refactor to store hooks as dict instead of list
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 28780
diff changeset
186 hooks = {}
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
187 for name, cmd in ui.configitems('hooks', untrusted=_untrusted):
39415
38dfd308fe9d hook: add support for disabling the shell to native command translation
Matt Harbison <matt_harbison@yahoo.com>
parents: 39414
diff changeset
188 if name.startswith('priority.') or name.startswith('tonative.'):
38dfd308fe9d hook: add support for disabling the shell to native command translation
Matt Harbison <matt_harbison@yahoo.com>
parents: 39414
diff changeset
189 continue
38dfd308fe9d hook: add support for disabling the shell to native command translation
Matt Harbison <matt_harbison@yahoo.com>
parents: 39414
diff changeset
190
38dfd308fe9d hook: add support for disabling the shell to native command translation
Matt Harbison <matt_harbison@yahoo.com>
parents: 39414
diff changeset
191 priority = ui.configint('hooks', 'priority.%s' % name, 0)
38dfd308fe9d hook: add support for disabling the shell to native command translation
Matt Harbison <matt_harbison@yahoo.com>
parents: 39414
diff changeset
192 hooks[name] = (-priority, len(hooks), name, cmd)
29687
3112c5e18835 hook: split config reading further
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29686
diff changeset
193 return hooks
15896
30c34fde40cc hooks: prioritize run order of hooks
Matt Zuba <matt.zuba@goodwillaz.org>
parents: 15521
diff changeset
194
5834
323b9c55b328 hook: redirect stdout to stderr for ssh and http servers
Matt Mackall <mpm@selenic.com>
parents: 4623
diff changeset
195 _redirect = False
323b9c55b328 hook: redirect stdout to stderr for ssh and http servers
Matt Mackall <mpm@selenic.com>
parents: 4623
diff changeset
196 def redirect(state):
6266
9f76df0edb7d hook.py: fix redirections introduced by 323b9c55b328
Alexis S. L. Carvalho <alexis@cecm.usp.br>
parents: 5876
diff changeset
197 global _redirect
5834
323b9c55b328 hook: redirect stdout to stderr for ssh and http servers
Matt Mackall <mpm@selenic.com>
parents: 4623
diff changeset
198 _redirect = state
323b9c55b328 hook: redirect stdout to stderr for ssh and http servers
Matt Mackall <mpm@selenic.com>
parents: 4623
diff changeset
199
35470
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
200 def hashook(ui, htype):
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
201 """return True if a hook is configured for 'htype'"""
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
202 if not ui.callhooks:
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
203 return False
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
204 for hname, cmd in _allhooks(ui):
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
205 if hname.split('.')[0] == htype and cmd:
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
206 return True
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
207 return False
e79b6300d97c hook: add a 'hashook' function to test for hook existence
Boris Feld <boris.feld@octobus.net>
parents: 33680
diff changeset
208
32524
33504b54863e hook: use 'htype' in 'hook'
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32523
diff changeset
209 def hook(ui, repo, htype, throw=False, **args):
17052
15d4d475de9e ui: add a variable to control whether hooks should be called
Idan Kamara <idankk86@gmail.com>
parents: 15896
diff changeset
210 if not ui.callhooks:
15d4d475de9e ui: add a variable to control whether hooks should be called
Idan Kamara <idankk86@gmail.com>
parents: 15896
diff changeset
211 return False
15d4d475de9e ui: add a variable to control whether hooks should be called
Idan Kamara <idankk86@gmail.com>
parents: 15896
diff changeset
212
27377
a930d66a04af hook: factor out determination of hooks from running them
Siddharth Agarwal <sid0@fb.com>
parents: 27332
diff changeset
213 hooks = []
a930d66a04af hook: factor out determination of hooks from running them
Siddharth Agarwal <sid0@fb.com>
parents: 27332
diff changeset
214 for hname, cmd in _allhooks(ui):
32524
33504b54863e hook: use 'htype' in 'hook'
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32523
diff changeset
215 if hname.split('.')[0] == htype and cmd:
27377
a930d66a04af hook: factor out determination of hooks from running them
Siddharth Agarwal <sid0@fb.com>
parents: 27332
diff changeset
216 hooks.append((hname, cmd))
a930d66a04af hook: factor out determination of hooks from running them
Siddharth Agarwal <sid0@fb.com>
parents: 27332
diff changeset
217
32524
33504b54863e hook: use 'htype' in 'hook'
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32523
diff changeset
218 res = runhooks(ui, repo, htype, hooks, throw=throw, **args)
27378
9abc2c921bbd hook.runhooks: return a dict of result values
Siddharth Agarwal <sid0@fb.com>
parents: 27377
diff changeset
219 r = False
9abc2c921bbd hook.runhooks: return a dict of result values
Siddharth Agarwal <sid0@fb.com>
parents: 27377
diff changeset
220 for hname, cmd in hooks:
27379
8429369eeb85 hook: for python hooks, also return whether an exception was raised
Siddharth Agarwal <sid0@fb.com>
parents: 27378
diff changeset
221 r = res[hname][0] or r
27378
9abc2c921bbd hook.runhooks: return a dict of result values
Siddharth Agarwal <sid0@fb.com>
parents: 27377
diff changeset
222 return r
27377
a930d66a04af hook: factor out determination of hooks from running them
Siddharth Agarwal <sid0@fb.com>
parents: 27332
diff changeset
223
32523
5678496659e9 hook: use 'htype' in 'runhooks'
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32522
diff changeset
224 def runhooks(ui, repo, htype, hooks, throw=False, **args):
33680
799db2af824c py3: convert keys of kwargs back to bytes using pycompat.byteskwargs()
Pulkit Goyal <7895pulkit@gmail.com>
parents: 33425
diff changeset
225 args = pycompat.byteskwargs(args)
27378
9abc2c921bbd hook.runhooks: return a dict of result values
Siddharth Agarwal <sid0@fb.com>
parents: 27377
diff changeset
226 res = {}
9658
852b1f3032d2 hook: only redirect stdout if it and stderr are valid files
Sune Foldager <cryo@cyanite.org>
parents: 9332
diff changeset
227 oldstdout = -1
5834
323b9c55b328 hook: redirect stdout to stderr for ssh and http servers
Matt Mackall <mpm@selenic.com>
parents: 4623
diff changeset
228
7427
196b05a548d0 hooks: restore io correctly on exception
Jesse Long <jesse@virtualpostman.co.za>
parents: 7278
diff changeset
229 try:
27377
a930d66a04af hook: factor out determination of hooks from running them
Siddharth Agarwal <sid0@fb.com>
parents: 27332
diff changeset
230 for hname, cmd in hooks:
17975
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
231 if oldstdout == -1 and _redirect:
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
232 try:
37905
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
233 stdoutno = procutil.stdout.fileno()
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
234 stderrno = procutil.stderr.fileno()
17975
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
235 # temporarily redirect stdout to stderr, if possible
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
236 if stdoutno >= 0 and stderrno >= 0:
37905
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
237 procutil.stdout.flush()
17975
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
238 oldstdout = os.dup(stdoutno)
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
239 os.dup2(stderrno, stdoutno)
17976
2c63896783e3 hooks: be even more forgiven of non-fd descriptors (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17975
diff changeset
240 except (OSError, AttributeError):
2c63896783e3 hooks: be even more forgiven of non-fd descriptors (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17975
diff changeset
241 # files seem to be bogus, give up on redirecting (WSGI, etc)
17975
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
242 pass
6180dcb29ec5 hooks: delay I/O redirection until we actually run a hook (issue3711)
Matt Mackall <mpm@selenic.com>
parents: 17411
diff changeset
243
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
244 if cmd is _fromuntrusted:
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
245 if throw:
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
246 raise error.HookAbort(
32522
f610c3220eec hook: fix name used in untrusted message
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32521
diff changeset
247 _('untrusted hook %s not executed') % hname,
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
248 hint = _("see 'hg help config.trusted'"))
32522
f610c3220eec hook: fix name used in untrusted message
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32521
diff changeset
249 ui.warn(_('warning: untrusted hook %s not executed\n') % hname)
29688
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
250 r = 1
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
251 raised = False
ea1fec3e9aba hook: report untrusted hooks as failure (issue5110) (BC)
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 29687
diff changeset
252 elif callable(cmd):
38827
242eb5132203 filemerge: support specifying a python function to custom merge-tools
hindlemail <tom_hindle@sil.org>
parents: 38728
diff changeset
253 r, raised = pythonhook(ui, repo, htype, hname, cmd, args,
32523
5678496659e9 hook: use 'htype' in 'runhooks'
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32522
diff changeset
254 throw)
7427
196b05a548d0 hooks: restore io correctly on exception
Jesse Long <jesse@virtualpostman.co.za>
parents: 7278
diff changeset
255 elif cmd.startswith('python:'):
9332
872d49dd577a hook: fix full path imports on Windows (issue1779)
Steve Borho <steve@borho.org>
parents: 8366
diff changeset
256 if cmd.count(':') >= 2:
872d49dd577a hook: fix full path imports on Windows (issue1779)
Steve Borho <steve@borho.org>
parents: 8366
diff changeset
257 path, cmd = cmd[7:].rsplit(':', 1)
13120
789e0fa2fcea hook: assume relative path to hook is given from repo root
Alexander Solovyov <alexander@solovyov.net>
parents: 11469
diff changeset
258 path = util.expandpath(path)
13121
ecf7d6e0eef0 hook: fix import path handling for repo=None
Matt Mackall <mpm@selenic.com>
parents: 13120
diff changeset
259 if repo:
ecf7d6e0eef0 hook: fix import path handling for repo=None
Matt Mackall <mpm@selenic.com>
parents: 13120
diff changeset
260 path = os.path.join(repo.root, path)
17219
1b2b727a885f hooks: print out more information when loading a python hook fails
Simon Heimberg <simohe@besonet.ch>
parents: 17052
diff changeset
261 try:
1b2b727a885f hooks: print out more information when loading a python hook fails
Simon Heimberg <simohe@besonet.ch>
parents: 17052
diff changeset
262 mod = extensions.loadpath(path, 'hghook.%s' % hname)
1b2b727a885f hooks: print out more information when loading a python hook fails
Simon Heimberg <simohe@besonet.ch>
parents: 17052
diff changeset
263 except Exception:
1b2b727a885f hooks: print out more information when loading a python hook fails
Simon Heimberg <simohe@besonet.ch>
parents: 17052
diff changeset
264 ui.write(_("loading %s hook failed:\n") % hname)
1b2b727a885f hooks: print out more information when loading a python hook fails
Simon Heimberg <simohe@besonet.ch>
parents: 17052
diff changeset
265 raise
7916
f779e1996e23 ability to load hooks from arbitrary python module
Alexander Solovyov <piranha@piranha.org.ua>
parents: 7787
diff changeset
266 hookfn = getattr(mod, cmd)
f779e1996e23 ability to load hooks from arbitrary python module
Alexander Solovyov <piranha@piranha.org.ua>
parents: 7787
diff changeset
267 else:
f779e1996e23 ability to load hooks from arbitrary python module
Alexander Solovyov <piranha@piranha.org.ua>
parents: 7787
diff changeset
268 hookfn = cmd[7:].strip()
38827
242eb5132203 filemerge: support specifying a python function to custom merge-tools
hindlemail <tom_hindle@sil.org>
parents: 38728
diff changeset
269 r, raised = pythonhook(ui, repo, htype, hname, hookfn, args,
27379
8429369eeb85 hook: for python hooks, also return whether an exception was raised
Siddharth Agarwal <sid0@fb.com>
parents: 27378
diff changeset
270 throw)
7427
196b05a548d0 hooks: restore io correctly on exception
Jesse Long <jesse@virtualpostman.co.za>
parents: 7278
diff changeset
271 else:
32525
0fa30fbccc34 hook: provide hook type information to external hook
Pierre-Yves David <pierre-yves.david@ens-lyon.org>
parents: 32524
diff changeset
272 r = _exthook(ui, repo, htype, hname, cmd, args, throw)
27379
8429369eeb85 hook: for python hooks, also return whether an exception was raised
Siddharth Agarwal <sid0@fb.com>
parents: 27378
diff changeset
273 raised = False
27378
9abc2c921bbd hook.runhooks: return a dict of result values
Siddharth Agarwal <sid0@fb.com>
parents: 27377
diff changeset
274
27379
8429369eeb85 hook: for python hooks, also return whether an exception was raised
Siddharth Agarwal <sid0@fb.com>
parents: 27378
diff changeset
275 res[hname] = r, raised
37627
9c636ec1ef37 hook: ensure stderr is flushed when an exception is raised, for test stability
Matt Harbison <matt_harbison@yahoo.com>
parents: 36894
diff changeset
276 finally:
9c636ec1ef37 hook: ensure stderr is flushed when an exception is raised, for test stability
Matt Harbison <matt_harbison@yahoo.com>
parents: 36894
diff changeset
277 # The stderr is fully buffered on Windows when connected to a pipe.
9c636ec1ef37 hook: ensure stderr is flushed when an exception is raised, for test stability
Matt Harbison <matt_harbison@yahoo.com>
parents: 36894
diff changeset
278 # A forcible flush is required to make small stderr data in the
9c636ec1ef37 hook: ensure stderr is flushed when an exception is raised, for test stability
Matt Harbison <matt_harbison@yahoo.com>
parents: 36894
diff changeset
279 # remote side available to the client immediately.
37905
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
280 procutil.stderr.flush()
24860
2abbf4750915 hook: forcibly flush stderr for Windows test stability
Matt Harbison <matt_harbison@yahoo.com>
parents: 23426
diff changeset
281
9658
852b1f3032d2 hook: only redirect stdout if it and stderr are valid files
Sune Foldager <cryo@cyanite.org>
parents: 9332
diff changeset
282 if _redirect and oldstdout >= 0:
37905
d4a2e0d5d042 procutil: bulk-replace util.std* to point to new module
Yuya Nishihara <yuya@tcha.org>
parents: 37627
diff changeset
283 procutil.stdout.flush() # write hook output to stderr fd
9658
852b1f3032d2 hook: only redirect stdout if it and stderr are valid files
Sune Foldager <cryo@cyanite.org>
parents: 9332
diff changeset
284 os.dup2(oldstdout, stdoutno)
7427
196b05a548d0 hooks: restore io correctly on exception
Jesse Long <jesse@virtualpostman.co.za>
parents: 7278
diff changeset
285 os.close(oldstdout)
6266
9f76df0edb7d hook.py: fix redirections introduced by 323b9c55b328
Alexis S. L. Carvalho <alexis@cecm.usp.br>
parents: 5876
diff changeset
286
27378
9abc2c921bbd hook.runhooks: return a dict of result values
Siddharth Agarwal <sid0@fb.com>
parents: 27377
diff changeset
287 return res