Patchwork [7,of,8] mercurial: trigger C extension build automatically for developers

login
register
mail settings
Submitter Jun Wu
Date May 3, 2017, 12:20 a.m.
Message ID <ecbbee35fdb88babfb4a.1493770804@x1c>
Download mbox | patch
Permalink /patch/20380/
State Deferred
Headers show

Comments

Jun Wu - May 3, 2017, 12:20 a.m.
# HG changeset patch
# User Jun Wu <quark@fb.com>
# Date 1493228701 25200
#      Wed Apr 26 10:45:01 2017 -0700
# Node ID ecbbee35fdb88babfb4ae0223bf4ee0294135066
# Parent  05b7c1fbabfd5d4198378b32c70abcb48b9c618d
# Available At https://bitbucket.org/quark-zju/hg-draft
#              hg pull https://bitbucket.org/quark-zju/hg-draft -r ecbbee35fdb8
mercurial: trigger C extension build automatically for developers

This patch adds C module check and triggers a rebuild automatically for
developers. The feature is turned on for convenience but could be turned off
using environment variable. The code will get removed by setup.py when
building.

Patch

diff --git a/hg b/hg
--- a/hg
+++ b/hg
@@ -27,4 +27,37 @@  if libdir != '@' 'LIBDIR' '@':
     sys.path.insert(0, libdir)
 
+# {{{ remove-from-release:auto-build
+# to make developers' life easier, build outdated C modules automatically.
+try:
+    from mercurial import _dualmodules, modulepolicy
+except ImportError:
+    pass
+else:
+    if (modulepolicy == b'c' and
+        os.environ.get('HGDEVAUTOBUILD', '') != 'disable'):
+        try:
+            # test if C modules are use-able
+            for name in _dualmodules:
+                __import__(name)
+        except ImportError as ex:
+            # try rebuild them automatically
+            import subprocess
+            failed = False
+            wd = os.path.dirname(os.path.realpath(__file__))
+            try:
+                cmd = [sys.executable, 'setup.py', 'build_ext', '-i']
+                null = open(os.devnull, 'r+')
+                subprocess.check_call(cmd, cwd=wd, stdin=null, stdout=null,
+                                      stderr=null)
+            except Exception:
+                failed = True
+                # be friendly - tell people how to fix it
+                sys.stderr.write('abort: cannot find or build compatible C '
+                                 'modules\n'
+                                 '(hint: run "make local" to build manually, '
+                                 'or set HGMODULEPOLICY to "allow")\n')
+                raise ex
+# remove-from-release:auto-build }}}
+
 # enable importing on demand to reduce startup time
 try:
diff --git a/setup.py b/setup.py
--- a/setup.py
+++ b/setup.py
@@ -555,4 +555,9 @@  class hginstallscripts(install_scripts):
                 continue
 
+            # remove "remove-from-release" blocks
+            data = re.sub('\n# {{{ remove-from-release:([^\n]*).*'
+                          '# remove-from-release:\\1 }}}\n', '',
+                          data, flags=re.DOTALL)
+
             # During local installs, the shebang will be rewritten to the final
             # install path. During wheel packaging, the shebang has a special
@@ -561,7 +566,7 @@  class hginstallscripts(install_scripts):
                 log.info('not rewriting @LIBDIR@ in %s because install path '
                          'not known' % outfile)
-                continue
+            else:
+                data = data.replace(b'@LIBDIR@', libdir.encode(libdir_escape))
 
-            data = data.replace(b'@LIBDIR@', libdir.encode(libdir_escape))
             with open(outfile, 'wb') as fp:
                 fp.write(data)