From 9312ca7f0dda6d00a5cc23d6e6ed6e57f455ac69 Mon Sep 17 00:00:00 2001 From: Ivan Kravets Date: Sat, 26 Dec 2015 14:47:42 +0200 Subject: [PATCH] Moved SCons to PlatformIO packages. PlatformIO does not require SCons to be installed in your system. Significantly simplified installation process of PlatformIO. "pip install platformio" rocks! --- HISTORY.rst | 5 ++- docs/platforms/creating_platform.rst | 3 ++ docs/platforms/native.rst | 2 +- platformio/__init__.py | 2 +- platformio/builder/main.py | 25 +------------ platformio/exception.py | 8 ---- platformio/platforms/base.py | 52 +++++++++++++++++--------- platformio/util.py | 55 ---------------------------- scripts/get-platformio.py | 51 -------------------------- setup.py | 25 ++++--------- 10 files changed, 52 insertions(+), 176 deletions(-) diff --git a/HISTORY.rst b/HISTORY.rst index 63701178..98b4544c 100644 --- a/HISTORY.rst +++ b/HISTORY.rst @@ -4,9 +4,12 @@ Release History PlatformIO 2.0 -------------- -2.6.4 (2015-12-??) +2.7.0 (2015-12-??) ~~~~~~~~~~~~~~~~~~ +* Moved SCons to PlatformIO packages. PlatformIO does not require SCons to be + installed in your system. Significantly simplified installation process of + PlatformIO. ``pip install platformio`` rocks! * Added support for the new Adafruit boards Bluefruit Micro and Feather (`issue #403 `_) * Updated Arduino framework for Atmel AVR development platform to 1.6.7 diff --git a/docs/platforms/creating_platform.rst b/docs/platforms/creating_platform.rst index 14cdb8dc..e1ba86d9 100644 --- a/docs/platforms/creating_platform.rst +++ b/docs/platforms/creating_platform.rst @@ -113,6 +113,9 @@ Packages * - ``tool-mspdebug`` - `MSPDebug `_ + * - ``tool-scons`` + - `SCons software construction tool `_ + * - ``tool-stlink`` - `ST-Link `_ diff --git a/docs/platforms/native.rst b/docs/platforms/native.rst index ba4864d0..7fb12ec3 100644 --- a/docs/platforms/native.rst +++ b/docs/platforms/native.rst @@ -13,7 +13,7 @@ Platform ``native`` =================== -Native development platform is intended to be used for desktop OS. This platform uses built-in tool chains (preferable based on GCC), frameworks, libs from particular OS where it will be run. +Native development platform is intended to be used for desktop OS. This platform uses built-in toolchains (preferable based on GCC), frameworks, libs from particular OS where it will be run. For more detailed information please visit `vendor site `_. diff --git a/platformio/__init__.py b/platformio/__init__.py index ac3c20e8..558be264 100644 --- a/platformio/__init__.py +++ b/platformio/__init__.py @@ -12,7 +12,7 @@ # See the License for the specific language governing permissions and # limitations under the License. -VERSION = (2, 6, "4.dev1") +VERSION = (2, 7, "0.dev0") __version__ = ".".join([str(s) for s in VERSION]) __title__ = "platformio" diff --git a/platformio/builder/main.py b/platformio/builder/main.py index 1f5debdd..23f377e9 100644 --- a/platformio/builder/main.py +++ b/platformio/builder/main.py @@ -12,30 +12,6 @@ # See the License for the specific language governing permissions and # limitations under the License. -# pylint: disable=wrong-import-position,wrong-import-order,unused-import - -try: - from platformio import util -except ImportError: - import sys - for p in sys.path: - _new_paths = [] - for item in ("dist-packages", "site-packages"): - if not p.endswith(item) and item in p: - _new_paths.append(p[:p.rfind(item) + len(item)]) - if "platformio" in p: - _new_paths.append(p[:p.rfind("platformio") - 1]) - - for _p in _new_paths: - if _p not in sys.path: - sys.path.insert(0, _p) - try: - from platformio import util - import lockfile # NOQA - break - except ImportError: - pass - import json from os import environ from os.path import isfile, join @@ -43,6 +19,7 @@ from time import time from SCons.Script import COMMAND_LINE_TARGETS, DefaultEnvironment, Variables +from platformio import util from platformio.exception import UnknownBoard # AllowSubstExceptions() diff --git a/platformio/exception.py b/platformio/exception.py index bd1ec52a..fd66ad7d 100644 --- a/platformio/exception.py +++ b/platformio/exception.py @@ -191,14 +191,6 @@ class CIBuildEnvsEmpty(PlatformioException): "predefined environments using `--project-conf` option" -class SConsNotInstalledError(PlatformioException): - - MESSAGE = "SCons is not installed in your system. "\ - "More details in FAQ/Troubleshooting section: "\ - "http://docs.platformio.org/en/latest/faq.html"\ - "#scons-is-not-installed-in-your-system" - - class UpgradeError(PlatformioException): MESSAGE = """{0} diff --git a/platformio/platforms/base.py b/platformio/platforms/base.py index 88d5377d..b76f70d2 100644 --- a/platformio/platforms/base.py +++ b/platformio/platforms/base.py @@ -14,6 +14,7 @@ import os import re +import sys from imp import load_source from multiprocessing import cpu_count from os.path import isdir, isfile, join @@ -112,6 +113,9 @@ PLATFORM_PACKAGES = { ("msp-gcc", "http://sourceforge.net/projects/mspgcc/"), ("GDB", "http://www.gnu.org/software/gdb/") ], + "tool-scons": [ + ("SCons software construction tool", "http://www.scons.org") + ], "tool-avrdude": [ ("AVRDUDE", "http://www.nongnu.org/avrdude/") ], @@ -365,6 +369,9 @@ class BasePlatform(object): if framework in pkg_name: self.PACKAGES[pkg_name]['default'] = True + # append SCons tool + self.PACKAGES['tool-scons'] = {"default": True} + # enable upload tools for upload targets if any(["upload" in t for t in targets] + ["program" in targets]): for _name, _opts in self.PACKAGES.iteritems(): @@ -429,24 +436,7 @@ class BasePlatform(object): "PIOPACKAGE_%s=%s" % (options['alias'].upper(), name)) self._found_error = False - try: - # test that SCons is installed correctly - assert util.test_scons() - - result = util.exec_command( - [ - "scons", - "-Q", - "-j %d" % self.get_job_nums(), - "--warn=no-no-parallel-support", - "-f", join(util.get_source_dir(), "builder", "main.py") - ] + variables + targets, - stdout=util.AsyncPipe(self.on_run_out), - stderr=util.AsyncPipe(self.on_run_err) - ) - except (OSError, AssertionError): - raise exception.SConsNotInstalledError() - + result = self._run_scons(variables, targets) assert "returncode" in result # if self._found_error: # result['returncode'] = 1 @@ -456,6 +446,32 @@ class BasePlatform(object): return result + def _run_scons(self, variables, targets): + # pass current PYTHONPATH to SCons + if "PYTHONPATH" in os.environ: + _PYTHONPATH = os.environ.get("PYTHONPATH").split(os.pathsep) + else: + _PYTHONPATH = [] + for p in os.sys.path: + if p not in _PYTHONPATH: + _PYTHONPATH.append(p) + os.environ['PYTHONPATH'] = os.pathsep.join(_PYTHONPATH) + + result = util.exec_command( + [ + os.path.normpath(sys.executable), + join(util.get_home_dir(), "packages", "tool-scons", + "script", "scons"), + "-Q", + "-j %d" % self.get_job_nums(), + "--warn=no-no-parallel-support", + "-f", join(util.get_source_dir(), "builder", "main.py") + ] + variables + targets, + stdout=util.AsyncPipe(self.on_run_out), + stderr=util.AsyncPipe(self.on_run_err) + ) + return result + def on_run_out(self, line): self._echo_line(line, level=3) diff --git a/platformio/util.py b/platformio/util.py index 8ace7aa7..816627d8 100644 --- a/platformio/util.py +++ b/platformio/util.py @@ -18,7 +18,6 @@ import json import os import re import subprocess -import sys from glob import glob from os.path import (abspath, basename, dirname, expanduser, isdir, isfile, join, realpath) @@ -330,60 +329,6 @@ def get_api_result(path, params=None, data=None): return result -def test_scons(): - try: - r = exec_command(["scons", "--version"]) - if "ImportError: No module named SCons.Script" in r['err']: - _PYTHONPATH = [] - for p in sys.path: - if not p.endswith("-packages"): - continue - for item in glob(join(p, "scons*")): - if isdir(join(item, "SCons")) and item not in sys.path: - _PYTHONPATH.append(item) - sys.path.insert(0, item) - if _PYTHONPATH: - _PYTHONPATH = str(os.pathsep).join(_PYTHONPATH) - if os.getenv("PYTHONPATH"): - os.environ['PYTHONPATH'] += os.pathsep + _PYTHONPATH - else: - os.environ['PYTHONPATH'] = _PYTHONPATH - r = exec_command(["scons", "--version"]) - assert r['returncode'] == 0 - return True - except (OSError, AssertionError): - for p in sys.path: - try: - r = exec_command([join(p, "scons"), "--version"]) - assert r['returncode'] == 0 - os.environ['PATH'] += os.pathsep + p - return True - except (OSError, AssertionError): - pass - return False - - -def install_scons(): - cmds = ( - ["pip", "install", "-U", "scons"], - ["pip", "install", "--egg", "scons", - '--install-option="--no-install-man"'], - ["easy_install", "scons"] - ) - for cmd in cmds: - r = exec_command(cmd) - if r['returncode'] == 0: - return True - return False - - -def scons_in_pip(): - r = exec_command(["pip", "list"]) - if r['returncode'] != 0: - return False - return "scons (" in r['out'].lower() - - @memoized def _lookup_boards(): boards = {} diff --git a/scripts/get-platformio.py b/scripts/get-platformio.py index e0e72da6..9e81692b 100644 --- a/scripts/get-platformio.py +++ b/scripts/get-platformio.py @@ -15,8 +15,6 @@ import os import subprocess import sys -from glob import glob -from os.path import isdir, join from platform import system from tempfile import NamedTemporaryFile @@ -94,53 +92,6 @@ def print_exec_result(result): raise Exception("\n".join([result['out'], result['err']])) -def test_scons(): - try: - r = exec_command(["scons", "--version"]) - if "ImportError: No module named SCons.Script" in r['err']: - _PYTHONPATH = [] - for p in sys.path: - if not p.endswith("-packages"): - continue - for item in glob(join(p, "scons*")): - if isdir(join(item, "SCons")) and item not in sys.path: - _PYTHONPATH.append(item) - sys.path.insert(0, item) - if _PYTHONPATH: - _PYTHONPATH = str(os.pathsep).join(_PYTHONPATH) - if os.getenv("PYTHONPATH"): - os.environ['PYTHONPATH'] += os.pathsep + _PYTHONPATH - else: - os.environ['PYTHONPATH'] = _PYTHONPATH - r = exec_command(["scons", "--version"]) - assert r['returncode'] == 0 - return True - except (OSError, AssertionError): - for p in sys.path: - try: - r = exec_command([join(p, "scons"), "--version"]) - assert r['returncode'] == 0 - os.environ['PATH'] += os.pathsep + p - return True - except (OSError, AssertionError): - pass - return False - - -def install_scons(): - cmds = ( - ["pip", "install", "-U", "scons"], - ["pip", "install", "--egg", "scons", - '--install-option="--no-install-man"'], - ["easy_install", "scons"] - ) - for cmd in cmds: - r = exec_command(cmd) - if r['returncode'] == 0: - return True - return False - - def exec_python_cmd(args): return exec_command([CURINTERPRETER_PATH] + args) @@ -175,8 +126,6 @@ def install_platformio(): cmd + ["--no-cache-dir", "install", "-U", "platformio"]) if r: print_exec_result(r) - if not test_scons(): - install_scons() def main(): diff --git a/setup.py b/setup.py index 810d5b0b..c82961a3 100644 --- a/setup.py +++ b/setup.py @@ -12,28 +12,12 @@ # See the License for the specific language governing permissions and # limitations under the License. -from platform import system from setuptools import find_packages, setup from platformio import (__author__, __description__, __email__, __license__, __title__, __url__, __version__, util) -install_requires = [ - "bottle", - "click>=3.2,<6", - "lockfile>=0.9.1", - "pyserial", - "requests>=2.4.0" -] - -if system() == "Windows": - install_requires.append("colorama") - -if not util.test_scons(): - util.install_scons() -elif util.scons_in_pip(): - install_requires.append("scons") setup( name=__title__, @@ -44,7 +28,14 @@ setup( author_email=__email__, url=__url__, license=__license__, - install_requires=install_requires, + install_requires=[ + "bottle", + "click>=3.2,<6", + "lockfile>=0.9.1", + "pyserial", + "requests>=2.4.0", + "colorama" + ], packages=find_packages(), package_data={ "platformio": [