Mercurial > hg
comparison contrib/packaging/hgpackaging/py2exe.py @ 43076:2372284d9457
formatting: blacken the codebase
This is using my patch to black
(https://github.com/psf/black/pull/826) so we don't un-wrap collection
literals.
Done with:
hg files 'set:**.py - mercurial/thirdparty/** - "contrib/python-zstandard/**"' | xargs black -S
# skip-blame mass-reformatting only
# no-check-commit reformats foo_bar functions
Differential Revision: https://phab.mercurial-scm.org/D6971
author | Augie Fackler <augie@google.com> |
---|---|
date | Sun, 06 Oct 2019 09:45:02 -0400 |
parents | 399ed3e86a49 |
children | d053d3f10b6a |
comparison
equal
deleted
inserted
replaced
43075:57875cf423c9 | 43076:2372284d9457 |
---|---|
9 | 9 |
10 import os | 10 import os |
11 import pathlib | 11 import pathlib |
12 import subprocess | 12 import subprocess |
13 | 13 |
14 from .downloads import ( | 14 from .downloads import download_entry |
15 download_entry, | |
16 ) | |
17 from .util import ( | 15 from .util import ( |
18 extract_tar_to_directory, | 16 extract_tar_to_directory, |
19 extract_zip_to_directory, | 17 extract_zip_to_directory, |
20 python_exe_info, | 18 python_exe_info, |
21 ) | 19 ) |
22 | 20 |
23 | 21 |
24 def build_py2exe(source_dir: pathlib.Path, build_dir: pathlib.Path, | 22 def build_py2exe( |
25 python_exe: pathlib.Path, build_name: str, | 23 source_dir: pathlib.Path, |
26 venv_requirements_txt: pathlib.Path, | 24 build_dir: pathlib.Path, |
27 extra_packages=None, extra_excludes=None, | 25 python_exe: pathlib.Path, |
28 extra_dll_excludes=None, | 26 build_name: str, |
29 extra_packages_script=None): | 27 venv_requirements_txt: pathlib.Path, |
28 extra_packages=None, | |
29 extra_excludes=None, | |
30 extra_dll_excludes=None, | |
31 extra_packages_script=None, | |
32 ): | |
30 """Build Mercurial with py2exe. | 33 """Build Mercurial with py2exe. |
31 | 34 |
32 Build files will be placed in ``build_dir``. | 35 Build files will be placed in ``build_dir``. |
33 | 36 |
34 py2exe's setup.py doesn't use setuptools. It doesn't have modern logic | 37 py2exe's setup.py doesn't use setuptools. It doesn't have modern logic |
35 for finding the Python 2.7 toolchain. So, we require the environment | 38 for finding the Python 2.7 toolchain. So, we require the environment |
36 to already be configured with an active toolchain. | 39 to already be configured with an active toolchain. |
37 """ | 40 """ |
38 if 'VCINSTALLDIR' not in os.environ: | 41 if 'VCINSTALLDIR' not in os.environ: |
39 raise Exception('not running from a Visual C++ build environment; ' | 42 raise Exception( |
40 'execute the "Visual C++ <version> Command Prompt" ' | 43 'not running from a Visual C++ build environment; ' |
41 'application shortcut or a vcsvarsall.bat file') | 44 'execute the "Visual C++ <version> Command Prompt" ' |
45 'application shortcut or a vcsvarsall.bat file' | |
46 ) | |
42 | 47 |
43 # Identity x86/x64 and validate the environment matches the Python | 48 # Identity x86/x64 and validate the environment matches the Python |
44 # architecture. | 49 # architecture. |
45 vc_x64 = r'\x64' in os.environ['LIB'] | 50 vc_x64 = r'\x64' in os.environ['LIB'] |
46 | 51 |
47 py_info = python_exe_info(python_exe) | 52 py_info = python_exe_info(python_exe) |
48 | 53 |
49 if vc_x64: | 54 if vc_x64: |
50 if py_info['arch'] != '64bit': | 55 if py_info['arch'] != '64bit': |
51 raise Exception('architecture mismatch: Visual C++ environment ' | 56 raise Exception( |
52 'is configured for 64-bit but Python is 32-bit') | 57 'architecture mismatch: Visual C++ environment ' |
58 'is configured for 64-bit but Python is 32-bit' | |
59 ) | |
53 else: | 60 else: |
54 if py_info['arch'] != '32bit': | 61 if py_info['arch'] != '32bit': |
55 raise Exception('architecture mismatch: Visual C++ environment ' | 62 raise Exception( |
56 'is configured for 32-bit but Python is 64-bit') | 63 'architecture mismatch: Visual C++ environment ' |
64 'is configured for 32-bit but Python is 64-bit' | |
65 ) | |
57 | 66 |
58 if py_info['py3']: | 67 if py_info['py3']: |
59 raise Exception('Only Python 2 is currently supported') | 68 raise Exception('Only Python 2 is currently supported') |
60 | 69 |
61 build_dir.mkdir(exist_ok=True) | 70 build_dir.mkdir(exist_ok=True) |
63 gettext_pkg, gettext_entry = download_entry('gettext', build_dir) | 72 gettext_pkg, gettext_entry = download_entry('gettext', build_dir) |
64 gettext_dep_pkg = download_entry('gettext-dep', build_dir)[0] | 73 gettext_dep_pkg = download_entry('gettext-dep', build_dir)[0] |
65 virtualenv_pkg, virtualenv_entry = download_entry('virtualenv', build_dir) | 74 virtualenv_pkg, virtualenv_entry = download_entry('virtualenv', build_dir) |
66 py2exe_pkg, py2exe_entry = download_entry('py2exe', build_dir) | 75 py2exe_pkg, py2exe_entry = download_entry('py2exe', build_dir) |
67 | 76 |
68 venv_path = build_dir / ('venv-%s-%s' % (build_name, | 77 venv_path = build_dir / ( |
69 'x64' if vc_x64 else 'x86')) | 78 'venv-%s-%s' % (build_name, 'x64' if vc_x64 else 'x86') |
79 ) | |
70 | 80 |
71 gettext_root = build_dir / ( | 81 gettext_root = build_dir / ('gettext-win-%s' % gettext_entry['version']) |
72 'gettext-win-%s' % gettext_entry['version']) | |
73 | 82 |
74 if not gettext_root.exists(): | 83 if not gettext_root.exists(): |
75 extract_zip_to_directory(gettext_pkg, gettext_root) | 84 extract_zip_to_directory(gettext_pkg, gettext_root) |
76 extract_zip_to_directory(gettext_dep_pkg, gettext_root) | 85 extract_zip_to_directory(gettext_dep_pkg, gettext_root) |
77 | 86 |
78 # This assumes Python 2. We don't need virtualenv on Python 3. | 87 # This assumes Python 2. We don't need virtualenv on Python 3. |
79 virtualenv_src_path = build_dir / ( | 88 virtualenv_src_path = build_dir / ( |
80 'virtualenv-%s' % virtualenv_entry['version']) | 89 'virtualenv-%s' % virtualenv_entry['version'] |
90 ) | |
81 virtualenv_py = virtualenv_src_path / 'virtualenv.py' | 91 virtualenv_py = virtualenv_src_path / 'virtualenv.py' |
82 | 92 |
83 if not virtualenv_src_path.exists(): | 93 if not virtualenv_src_path.exists(): |
84 extract_tar_to_directory(virtualenv_pkg, build_dir) | 94 extract_tar_to_directory(virtualenv_pkg, build_dir) |
85 | 95 |
89 extract_zip_to_directory(py2exe_pkg, build_dir) | 99 extract_zip_to_directory(py2exe_pkg, build_dir) |
90 | 100 |
91 if not venv_path.exists(): | 101 if not venv_path.exists(): |
92 print('creating virtualenv with dependencies') | 102 print('creating virtualenv with dependencies') |
93 subprocess.run( | 103 subprocess.run( |
94 [str(python_exe), str(virtualenv_py), str(venv_path)], | 104 [str(python_exe), str(virtualenv_py), str(venv_path)], check=True |
95 check=True) | 105 ) |
96 | 106 |
97 venv_python = venv_path / 'Scripts' / 'python.exe' | 107 venv_python = venv_path / 'Scripts' / 'python.exe' |
98 venv_pip = venv_path / 'Scripts' / 'pip.exe' | 108 venv_pip = venv_path / 'Scripts' / 'pip.exe' |
99 | 109 |
100 subprocess.run([str(venv_pip), 'install', '-r', str(venv_requirements_txt)], | 110 subprocess.run( |
101 check=True) | 111 [str(venv_pip), 'install', '-r', str(venv_requirements_txt)], check=True |
112 ) | |
102 | 113 |
103 # Force distutils to use VC++ settings from environment, which was | 114 # Force distutils to use VC++ settings from environment, which was |
104 # validated above. | 115 # validated above. |
105 env = dict(os.environ) | 116 env = dict(os.environ) |
106 env['DISTUTILS_USE_SDK'] = '1' | 117 env['DISTUTILS_USE_SDK'] = '1' |
107 env['MSSdk'] = '1' | 118 env['MSSdk'] = '1' |
108 | 119 |
109 if extra_packages_script: | 120 if extra_packages_script: |
110 more_packages = set(subprocess.check_output( | 121 more_packages = set( |
111 extra_packages_script, | 122 subprocess.check_output(extra_packages_script, cwd=build_dir) |
112 cwd=build_dir).split(b'\0')[-1].strip().decode('utf-8').splitlines()) | 123 .split(b'\0')[-1] |
124 .strip() | |
125 .decode('utf-8') | |
126 .splitlines() | |
127 ) | |
113 if more_packages: | 128 if more_packages: |
114 if not extra_packages: | 129 if not extra_packages: |
115 extra_packages = more_packages | 130 extra_packages = more_packages |
116 else: | 131 else: |
117 extra_packages |= more_packages | 132 extra_packages |= more_packages |
118 | 133 |
119 if extra_packages: | 134 if extra_packages: |
120 env['HG_PY2EXE_EXTRA_PACKAGES'] = ' '.join(sorted(extra_packages)) | 135 env['HG_PY2EXE_EXTRA_PACKAGES'] = ' '.join(sorted(extra_packages)) |
121 hgext3rd_extras = sorted( | 136 hgext3rd_extras = sorted( |
122 e for e in extra_packages if e.startswith('hgext3rd.')) | 137 e for e in extra_packages if e.startswith('hgext3rd.') |
138 ) | |
123 if hgext3rd_extras: | 139 if hgext3rd_extras: |
124 env['HG_PY2EXE_EXTRA_INSTALL_PACKAGES'] = ' '.join(hgext3rd_extras) | 140 env['HG_PY2EXE_EXTRA_INSTALL_PACKAGES'] = ' '.join(hgext3rd_extras) |
125 if extra_excludes: | 141 if extra_excludes: |
126 env['HG_PY2EXE_EXTRA_EXCLUDES'] = ' '.join(sorted(extra_excludes)) | 142 env['HG_PY2EXE_EXTRA_EXCLUDES'] = ' '.join(sorted(extra_excludes)) |
127 if extra_dll_excludes: | 143 if extra_dll_excludes: |
128 env['HG_PY2EXE_EXTRA_DLL_EXCLUDES'] = ' '.join( | 144 env['HG_PY2EXE_EXTRA_DLL_EXCLUDES'] = ' '.join( |
129 sorted(extra_dll_excludes)) | 145 sorted(extra_dll_excludes) |
146 ) | |
130 | 147 |
131 py2exe_py_path = venv_path / 'Lib' / 'site-packages' / 'py2exe' | 148 py2exe_py_path = venv_path / 'Lib' / 'site-packages' / 'py2exe' |
132 if not py2exe_py_path.exists(): | 149 if not py2exe_py_path.exists(): |
133 print('building py2exe') | 150 print('building py2exe') |
134 subprocess.run([str(venv_python), 'setup.py', 'install'], | 151 subprocess.run( |
135 cwd=py2exe_source_path, | 152 [str(venv_python), 'setup.py', 'install'], |
136 env=env, | 153 cwd=py2exe_source_path, |
137 check=True) | 154 env=env, |
155 check=True, | |
156 ) | |
138 | 157 |
139 # Register location of msgfmt and other binaries. | 158 # Register location of msgfmt and other binaries. |
140 env['PATH'] = '%s%s%s' % ( | 159 env['PATH'] = '%s%s%s' % ( |
141 env['PATH'], os.pathsep, str(gettext_root / 'bin')) | 160 env['PATH'], |
161 os.pathsep, | |
162 str(gettext_root / 'bin'), | |
163 ) | |
142 | 164 |
143 print('building Mercurial') | 165 print('building Mercurial') |
144 subprocess.run( | 166 subprocess.run( |
145 [str(venv_python), 'setup.py', | 167 [str(venv_python), 'setup.py', 'py2exe', 'build_doc', '--html'], |
146 'py2exe', | |
147 'build_doc', '--html'], | |
148 cwd=str(source_dir), | 168 cwd=str(source_dir), |
149 env=env, | 169 env=env, |
150 check=True) | 170 check=True, |
171 ) |