Skip to content

Commit 3c89307

Browse files
committed
Some progress on new prerequisites management
1 parent 4baec32 commit 3c89307

File tree

6 files changed

+421
-21
lines changed

6 files changed

+421
-21
lines changed

.github/workflows/push.yml

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -122,7 +122,6 @@ jobs:
122122
run: |
123123
source ci/osx_ci.sh
124124
arm64_set_path_and_python_version 3.9.7
125-
brew install autoconf automake libtool openssl pkg-config
126125
make --file ci/makefiles/osx.mk
127126
- name: Build multi-arch apk Python 3 (armeabi-v7a, arm64-v8a, x86_64, x86)
128127
run: |
@@ -207,7 +206,6 @@ jobs:
207206
run: |
208207
source ci/osx_ci.sh
209208
arm64_set_path_and_python_version 3.9.7
210-
brew install autoconf automake libtool openssl pkg-config
211209
make --file ci/makefiles/osx.mk
212210
- name: Build multi-arch aab Python 3 (armeabi-v7a, arm64-v8a, x86_64, x86)
213211
run: |
@@ -293,7 +291,6 @@ jobs:
293291
run: |
294292
source ci/osx_ci.sh
295293
arm64_set_path_and_python_version 3.9.7
296-
brew install autoconf automake libtool openssl pkg-config
297294
make --file ci/makefiles/osx.mk
298295
- name: Rebuild updated recipes
299296
run: |

ci/makefiles/osx.mk

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# installs java 1.8, android's SDK/NDK, cython and p4a
1+
# installs Android's SDK/NDK, cython
22

33
# The following variable/s can be override when running the file
44
ANDROID_HOME ?= $(HOME)/.android
@@ -10,4 +10,4 @@ upgrade_cython:
1010

1111
install_android_ndk_sdk:
1212
mkdir -p $(ANDROID_HOME)
13-
make -f ci/makefiles/android.mk JAVA_HOME=`/usr/libexec/java_home -v 13`
13+
make -f ci/makefiles/android.mk

pythonforandroid/prerequisites.py

Lines changed: 153 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -4,20 +4,20 @@
44
import platform
55
import os
66
import subprocess
7+
import shutil
78
from pythonforandroid.logger import info, warning, error
89

910

1011
class Prerequisite(object):
1112
name = "Default"
12-
mandatory = True
13-
darwin_installer_is_supported = False
14-
linux_installer_is_supported = False
13+
mandatory = dict(linux=False, darwin=False)
14+
installer_is_supported = dict(linux=False, darwin=False)
1515

1616
def is_valid(self):
1717
if self.checker():
1818
info(f"Prerequisite {self.name} is met")
1919
return (True, "")
20-
elif not self.mandatory:
20+
elif not self.mandatory[sys.platform]:
2121
warning(
2222
f"Prerequisite {self.name} is not met, but is marked as non-mandatory"
2323
)
@@ -73,10 +73,7 @@ def show_helper(self):
7373
raise Exception("Unsupported platform")
7474

7575
def install_is_supported(self):
76-
if sys.platform == "darwin":
77-
return self.darwin_installer_is_supported
78-
elif sys.platform == "linux":
79-
return self.linux_installer_is_supported
76+
return self.installer_is_supported[sys.platform]
8077

8178
def linux_checker(self):
8279
raise Exception(f"Unsupported prerequisite check on linux for {self.name}")
@@ -96,11 +93,42 @@ def darwin_helper(self):
9693
def linux_helper(self):
9794
info(f"No helper available for prerequisite: {self.name} on linux")
9895

96+
def _darwin_get_brew_formula_location_prefix(self, formula, installed=False):
97+
opts = ["--installed"] if installed else []
98+
p = subprocess.Popen(
99+
["brew", "--prefix", formula, *opts],
100+
stdout=subprocess.PIPE,
101+
stderr=subprocess.PIPE,
102+
)
103+
_stdout_res, _stderr_res = p.communicate()
104+
105+
if p.returncode != 0:
106+
error(_stderr_res.decode("utf-8").strip())
107+
return None
108+
else:
109+
return _stdout_res.decode("utf-8").strip()
110+
111+
112+
class HomebrewPrerequisite(Prerequisite):
113+
name = "homebrew"
114+
mandatory = dict(linux=False, darwin=True)
115+
installer_is_supported = dict(linux=False, darwin=False)
116+
117+
def darwin_checker(self):
118+
return shutil.which("brew") is not None
119+
120+
def darwin_helper(self):
121+
info(
122+
"Installer for homebrew is not yet supported on macOS,"
123+
"the nice news is that the installation process is easy!"
124+
"See: https://brew.sh for further instructions."
125+
)
126+
99127

100128
class JDKPrerequisite(Prerequisite):
101129
name = "JDK"
102-
mandatory = True
103-
darwin_installer_is_supported = True
130+
mandatory = dict(linux=False, darwin=True)
131+
installer_is_supported = dict(linux=False, darwin=True)
104132
min_supported_version = 11
105133

106134
def darwin_checker(self):
@@ -216,13 +244,123 @@ def darwin_installer(self):
216244
os.environ["JAVA_HOME"] = jdk_path
217245

218246

219-
def check_and_install_default_prerequisites():
220-
DEFAULT_PREREQUISITES = dict(darwin=[JDKPrerequisite()], linux=[], all_platforms=[])
247+
class OpenSSLPrerequisite(Prerequisite):
248+
name = "openssl@1.1"
249+
mandatory = dict(linux=False, darwin=True)
250+
installer_is_supported = dict(linux=False, darwin=True)
251+
252+
def darwin_checker(self):
253+
return (
254+
self._darwin_get_brew_formula_location_prefix("openssl@1.1", installed=True)
255+
is not None
256+
)
257+
258+
def darwin_installer(self):
259+
info("Installing OpenSSL ...")
260+
subprocess.check_output(["brew", "install", "openssl@1.1"])
261+
262+
263+
class AutoconfPrerequisite(Prerequisite):
264+
name = "autoconf"
265+
mandatory = dict(linux=False, darwin=True)
266+
installer_is_supported = dict(linux=False, darwin=True)
267+
268+
def darwin_checker(self):
269+
return (
270+
self._darwin_get_brew_formula_location_prefix("autoconf", installed=True)
271+
is not None
272+
)
273+
274+
def darwin_installer(self):
275+
info("Installing Autoconf ...")
276+
subprocess.check_output(["brew", "install", "autoconf"])
277+
278+
279+
class AutomakePrerequisite(Prerequisite):
280+
name = "automake"
281+
mandatory = dict(linux=False, darwin=True)
282+
installer_is_supported = dict(linux=False, darwin=True)
221283

222-
required_prerequisites = (
223-
DEFAULT_PREREQUISITES["all_platforms"] + DEFAULT_PREREQUISITES[sys.platform]
284+
def darwin_checker(self):
285+
return (
286+
self._darwin_get_brew_formula_location_prefix("automake", installed=True)
287+
is not None
288+
)
289+
290+
def darwin_installer(self):
291+
info("Installing Automake ...")
292+
subprocess.check_output(["brew", "install", "automake"])
293+
294+
295+
class LibtoolPrerequisite(Prerequisite):
296+
name = "libtool"
297+
mandatory = dict(linux=False, darwin=True)
298+
installer_is_supported = dict(linux=False, darwin=True)
299+
300+
def darwin_checker(self):
301+
return (
302+
self._darwin_get_brew_formula_location_prefix("libtool", installed=True)
303+
is not None
304+
)
305+
306+
def darwin_installer(self):
307+
info("Installing Libtool ...")
308+
subprocess.check_output(["brew", "install", "libtool"])
309+
310+
311+
class PkgConfigPrerequisite(Prerequisite):
312+
name = "pkg-config"
313+
mandatory = dict(linux=False, darwin=True)
314+
installer_is_supported = dict(linux=False, darwin=True)
315+
316+
def darwin_checker(self):
317+
return (
318+
self._darwin_get_brew_formula_location_prefix("pkg-config", installed=True)
319+
is not None
320+
)
321+
322+
def darwin_installer(self):
323+
info("Installing Pkg-Config ...")
324+
subprocess.check_output(["brew", "install", "pkg-config"])
325+
326+
327+
class CmakePrerequisite(Prerequisite):
328+
name = "cmake"
329+
mandatory = dict(linux=False, darwin=True)
330+
installer_is_supported = dict(linux=False, darwin=True)
331+
332+
def darwin_checker(self):
333+
return (
334+
self._darwin_get_brew_formula_location_prefix("cmake", installed=True)
335+
is not None
336+
)
337+
338+
def darwin_installer(self):
339+
info("Installing cmake ...")
340+
subprocess.check_output(["brew", "install", "cmake"])
341+
342+
343+
def get_required_prerequisites(platform="linux"):
344+
DEFAULT_PREREQUISITES = dict(
345+
darwin=[
346+
HomebrewPrerequisite(),
347+
AutoconfPrerequisite(),
348+
AutomakePrerequisite(),
349+
LibtoolPrerequisite(),
350+
PkgConfigPrerequisite(),
351+
CmakePrerequisite(),
352+
OpenSSLPrerequisite(),
353+
JDKPrerequisite(),
354+
],
355+
linux=[],
356+
all_platforms=[],
224357
)
225358

359+
return DEFAULT_PREREQUISITES["all_platforms"] + DEFAULT_PREREQUISITES[platform]
360+
361+
362+
def check_and_install_default_prerequisites():
363+
226364
prerequisites_not_met = []
227365

228366
warning(
@@ -232,7 +370,7 @@ def check_and_install_default_prerequisites():
232370

233371
# Phase 1: Check if all prerequisites are met and add the ones
234372
# which are not to `prerequisites_not_met`
235-
for prerequisite in required_prerequisites:
373+
for prerequisite in get_required_prerequisites(sys.platform):
236374
if not prerequisite.is_valid():
237375
prerequisites_not_met.append(prerequisite)
238376

pythonforandroid/toolchain.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,8 @@ def check_python_dependencies():
6767
exit(1)
6868

6969

70-
check_and_install_default_prerequisites()
70+
if not environ.get('SKIP_PREREQUISITES_CHECK', '0') == '1':
71+
check_and_install_default_prerequisites()
7172
check_python_dependencies()
7273

7374

0 commit comments

Comments
 (0)