Merge pull request #265 from YannickJadoul/drop-2.7
Dropping Python 2.7 host support
This commit is contained in:
+8
-25
@@ -1,11 +1,11 @@
|
||||
version: 2
|
||||
|
||||
jobs:
|
||||
osx-python2:
|
||||
osx-python3.6:
|
||||
macos:
|
||||
xcode: "10.0.0"
|
||||
xcode: "9.4.1"
|
||||
environment:
|
||||
PYTHON: python2
|
||||
PYTHON: python3
|
||||
steps:
|
||||
- checkout
|
||||
|
||||
@@ -16,7 +16,7 @@ jobs:
|
||||
name: Test.
|
||||
command: venv/bin/python ./bin/run_tests.py
|
||||
|
||||
osx-python3:
|
||||
osx-python3.7:
|
||||
macos:
|
||||
xcode: "10.0.0"
|
||||
environment:
|
||||
@@ -31,23 +31,7 @@ jobs:
|
||||
name: Test.
|
||||
command: venv/bin/python ./bin/run_tests.py
|
||||
|
||||
linux-python2:
|
||||
docker:
|
||||
- image: circleci/python:2.7
|
||||
environment:
|
||||
PYTHON: python2
|
||||
steps:
|
||||
- checkout
|
||||
- setup_remote_docker
|
||||
|
||||
- run:
|
||||
name: Prepare the environment.
|
||||
command: bash .circleci/prepare.sh
|
||||
- run:
|
||||
name: Test.
|
||||
command: venv/bin/python ./bin/run_tests.py
|
||||
|
||||
linux-python3:
|
||||
linux-python3.6:
|
||||
docker:
|
||||
- image: circleci/python:3.6
|
||||
environment:
|
||||
@@ -67,7 +51,6 @@ workflows:
|
||||
version: 2
|
||||
all-tests:
|
||||
jobs:
|
||||
- osx-python2
|
||||
- osx-python3
|
||||
- linux-python2
|
||||
- linux-python3
|
||||
- osx-python3.6
|
||||
- osx-python3.7
|
||||
- linux-python3.6
|
||||
|
||||
@@ -2,13 +2,6 @@ language: generic
|
||||
|
||||
matrix:
|
||||
include:
|
||||
# Linux Python 2
|
||||
- sudo: required
|
||||
language: python
|
||||
python: 2.7
|
||||
services: docker
|
||||
env: PYTHON=python
|
||||
|
||||
# Linux Python 3
|
||||
- sudo: required
|
||||
language: python
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
This is a summary of the Python versions and platforms covered by the different CI platforms:
|
||||
|
||||
| | 3.5 | 3.6 | 3.7 | 3.8 |
|
||||
|----------|------------------|------------------|-----------------------|------------------|
|
||||
| Linux | Travis CI | CircleCI | AppVeyor | Azure Pipelines |
|
||||
| macOS | Azure Pipelines | CircleCI | Travis CI¹ / CircleCI | Azure Pipelines |
|
||||
| Windows | TravisCI | Azure Pipelines | AppVeyor | Azure Pipelines |
|
||||
|
||||
> ¹ Python version not really pinned, but dependent on the (default) version of image used.
|
||||
+2
-2
@@ -3,9 +3,9 @@ image:
|
||||
- Visual Studio 2015
|
||||
|
||||
build_script:
|
||||
- cmd: "C:\\Python27\\python.exe -m pip install -r requirements-dev.txt"
|
||||
- cmd: "C:\\Python37\\python.exe -m pip install -r requirements-dev.txt"
|
||||
- sh: "${HOME}/.localpython3.7.4/bin/python3 -m pip install -r requirements-dev.txt"
|
||||
# the '-u' flag is required so the output is in the correct order.
|
||||
# See https://github.com/joerick/cibuildwheel/pull/24 for more info.
|
||||
- cmd: "C:\\Python27\\python.exe -u ./bin/run_tests.py"
|
||||
- cmd: "C:\\Python37\\python.exe -u ./bin/run_tests.py"
|
||||
- sh: "${HOME}/.localpython3.7.4/bin/python3 ./bin/run_tests.py"
|
||||
|
||||
+25
-3
@@ -1,5 +1,5 @@
|
||||
jobs:
|
||||
- job: linux
|
||||
- job: linux_38
|
||||
pool: {vmImage: 'Ubuntu-18.04'}
|
||||
steps:
|
||||
- task: UsePythonVersion@0
|
||||
@@ -9,7 +9,17 @@ jobs:
|
||||
python -m pip install -r requirements-dev.txt
|
||||
python ./bin/run_tests.py
|
||||
|
||||
- job: macos
|
||||
- job: macos_35
|
||||
pool: {vmImage: 'macOS-10.13'}
|
||||
steps:
|
||||
- task: UsePythonVersion@0
|
||||
inputs:
|
||||
versionSpec: '3.5'
|
||||
- bash: |
|
||||
python -m pip install -r requirements-dev.txt
|
||||
python ./bin/run_tests.py
|
||||
|
||||
- job: macos_38
|
||||
pool: {vmImage: 'macOS-10.13'}
|
||||
steps:
|
||||
- task: UsePythonVersion@0
|
||||
@@ -19,7 +29,19 @@ jobs:
|
||||
python -m pip install -r requirements-dev.txt
|
||||
python ./bin/run_tests.py
|
||||
|
||||
- job: windows
|
||||
- job: windows_36
|
||||
pool: {vmImage: 'vs2017-win2016'}
|
||||
steps:
|
||||
- task: UsePythonVersion@0
|
||||
inputs:
|
||||
versionSpec: '3.6'
|
||||
- script: choco install vcpython27 -f -y
|
||||
displayName: Install Visual C++ for Python 2.7
|
||||
- bash: |
|
||||
python -m pip install -r requirements-dev.txt
|
||||
python ./bin/run_tests.py
|
||||
|
||||
- job: windows_38
|
||||
pool: {vmImage: 'vs2017-win2016'}
|
||||
steps:
|
||||
- task: UsePythonVersion@0
|
||||
|
||||
+1
-2
@@ -1,6 +1,5 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import os, sys, subprocess, shutil
|
||||
|
||||
|
||||
|
||||
+1
-2
@@ -1,6 +1,5 @@
|
||||
#!/usr/bin/env python
|
||||
#!/usr/bin/env python3
|
||||
|
||||
from __future__ import print_function
|
||||
import os, sys, subprocess, shutil, json
|
||||
from glob import glob
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
from __future__ import print_function
|
||||
import argparse, os, subprocess, sys, textwrap
|
||||
|
||||
import cibuildwheel
|
||||
|
||||
@@ -60,12 +60,8 @@ def evaluate_word_node(node, context):
|
||||
def evaluate_command_node(node, context):
|
||||
words = [evaluate_node(part, context=context) for part in node.parts]
|
||||
command = ' '.join(words)
|
||||
output = subprocess.check_output(shlex.split(command), env=context.environment)
|
||||
return subprocess.check_output(shlex.split(command), env=context.environment, universal_newlines=True)
|
||||
|
||||
if sys.version_info[0] >= 3:
|
||||
return output.decode('utf8', 'replace')
|
||||
else:
|
||||
return output
|
||||
|
||||
def evaluate_parameter_node(node, context):
|
||||
return context.environment.get(node.value, '')
|
||||
|
||||
@@ -41,7 +41,7 @@ def split_env_items(env_string):
|
||||
return result
|
||||
|
||||
|
||||
class EnvironmentAssignment(object):
|
||||
class EnvironmentAssignment:
|
||||
def __init__(self, assignment):
|
||||
name, equals, value = assignment.partition('=')
|
||||
if not equals:
|
||||
@@ -60,7 +60,7 @@ class EnvironmentAssignment(object):
|
||||
return '%s=%s' % (self.name, self.value)
|
||||
|
||||
|
||||
class ParsedEnvironment(object):
|
||||
class ParsedEnvironment:
|
||||
def __init__(self, assignments):
|
||||
self.assignments = assignments
|
||||
|
||||
|
||||
+15
-35
@@ -1,13 +1,7 @@
|
||||
from __future__ import print_function
|
||||
import os, subprocess, sys, uuid, textwrap
|
||||
import os, shlex, subprocess, sys, textwrap, uuid
|
||||
from collections import namedtuple
|
||||
from .util import prepare_command, get_build_verbosity_extra_flags
|
||||
|
||||
try:
|
||||
from shlex import quote as shlex_quote
|
||||
except ImportError:
|
||||
from pipes import quote as shlex_quote
|
||||
|
||||
|
||||
def get_python_configurations(build_selector):
|
||||
PythonConfiguration = namedtuple('PythonConfiguration', ['identifier', 'path'])
|
||||
@@ -132,14 +126,14 @@ def build(project_dir, output_dir, test_command, test_requires, test_extras, bef
|
||||
pybin_paths=' '.join(c.path+'/bin' for c in platform_configs),
|
||||
test_requires=' '.join(test_requires),
|
||||
test_extras=test_extras,
|
||||
test_command=shlex_quote(
|
||||
test_command=shlex.quote(
|
||||
prepare_command(test_command, project='/project') if test_command else ''
|
||||
),
|
||||
before_build=shlex_quote(
|
||||
before_build=shlex.quote(
|
||||
prepare_command(before_build, project='/project') if before_build else ''
|
||||
),
|
||||
build_verbosity_flag=' '.join(get_build_verbosity_extra_flags(build_verbosity)),
|
||||
repair_command=shlex_quote(
|
||||
repair_command=shlex.quote(
|
||||
prepare_command(repair_command, wheel='"$1"', dest_dir='/tmp/repaired_wheels') if repair_command else ''
|
||||
),
|
||||
environment_exports='\n'.join(environment.as_shell_commands()),
|
||||
@@ -147,38 +141,24 @@ def build(project_dir, output_dir, test_command, test_requires, test_extras, bef
|
||||
gid=os.getgid(),
|
||||
)
|
||||
|
||||
def run_docker(command, stdin_str=None):
|
||||
print('docker command: docker {}'.format(' '.join(map(shlex_quote, command))))
|
||||
if stdin_str is None:
|
||||
subprocess.check_call(['docker'] + command)
|
||||
else:
|
||||
args = ['docker'] + command
|
||||
process = subprocess.Popen(args, stdin=subprocess.PIPE, universal_newlines=True)
|
||||
try:
|
||||
process.communicate(stdin_str)
|
||||
except KeyboardInterrupt:
|
||||
process.kill()
|
||||
process.wait()
|
||||
if process.returncode != 0:
|
||||
raise subprocess.CalledProcessError(process.returncode, args)
|
||||
|
||||
container_name = 'cibuildwheel-{}'.format(uuid.uuid4())
|
||||
try:
|
||||
run_docker(['create',
|
||||
'--env', 'CIBUILDWHEEL',
|
||||
'--name', container_name,
|
||||
'-i',
|
||||
'-v', '/:/host', # ignored on Circle
|
||||
docker_image, '/bin/bash'])
|
||||
run_docker(['cp', os.path.abspath(project_dir) + '/.', container_name + ':/project'])
|
||||
run_docker(['start', '-i', '-a', container_name], stdin_str=bash_script)
|
||||
run_docker(['cp', container_name + ':/output/.', os.path.abspath(output_dir)])
|
||||
subprocess.run(['docker', 'create',
|
||||
'--env', 'CIBUILDWHEEL',
|
||||
'--name', container_name,
|
||||
'-i',
|
||||
'-v', '/:/host', # ignored on CircleCI
|
||||
docker_image, '/bin/bash'],
|
||||
check=True)
|
||||
subprocess.run(['docker', 'cp', os.path.abspath(project_dir) + '/.', container_name + ':/project'], check=True)
|
||||
subprocess.run(['docker', 'start', '-i', '-a', container_name], input=bash_script, universal_newlines=True, check=True)
|
||||
subprocess.run(['docker', 'cp', container_name + ':/output/.', os.path.abspath(output_dir)], check=True)
|
||||
except subprocess.CalledProcessError as error:
|
||||
troubleshoot(project_dir, error)
|
||||
exit(1)
|
||||
finally:
|
||||
# Still gets executed, even when 'exit(1)' gets called
|
||||
run_docker(['rm', '--force', '-v', container_name])
|
||||
subprocess.run(['docker', 'rm', '--force', '-v', container_name], check=True)
|
||||
|
||||
|
||||
def troubleshoot(project_dir, error):
|
||||
|
||||
@@ -1,12 +1,7 @@
|
||||
from __future__ import print_function
|
||||
import tempfile
|
||||
import os, subprocess, shlex, sys, shutil
|
||||
from collections import namedtuple
|
||||
from glob import glob
|
||||
try:
|
||||
from shlex import quote as shlex_quote
|
||||
except ImportError:
|
||||
from pipes import quote as shlex_quote
|
||||
|
||||
from .util import prepare_command, get_build_verbosity_extra_flags, download
|
||||
|
||||
@@ -36,9 +31,7 @@ def build(project_dir, output_dir, test_command, test_requires, test_extras, bef
|
||||
get_pip_url = 'https://bootstrap.pypa.io/get-pip.py'
|
||||
get_pip_script = '/tmp/get-pip.py'
|
||||
|
||||
pkgs_output = subprocess.check_output(['pkgutil', '--pkgs'])
|
||||
if sys.version_info[0] >= 3:
|
||||
pkgs_output = pkgs_output.decode('utf8')
|
||||
pkgs_output = subprocess.check_output(['pkgutil', '--pkgs'], universal_newlines=True)
|
||||
installed_system_packages = pkgs_output.splitlines()
|
||||
|
||||
def call(args, env=None, cwd=None, shell=False):
|
||||
@@ -46,7 +39,7 @@ def build(project_dir, output_dir, test_command, test_requires, test_extras, bef
|
||||
if shell:
|
||||
print('+ %s' % args)
|
||||
else:
|
||||
print('+ ' + ' '.join(shlex_quote(a) for a in args))
|
||||
print('+ ' + ' '.join(shlex.quote(a) for a in args))
|
||||
|
||||
return subprocess.check_call(args, env=env, cwd=cwd, shell=shell)
|
||||
|
||||
|
||||
@@ -1,13 +1,8 @@
|
||||
from fnmatch import fnmatch
|
||||
import warnings
|
||||
import os
|
||||
import os, urllib.request
|
||||
from time import sleep
|
||||
|
||||
try:
|
||||
from urllib.request import urlopen
|
||||
except ImportError:
|
||||
from urllib2 import urlopen
|
||||
|
||||
|
||||
def prepare_command(command, **kwargs):
|
||||
'''
|
||||
@@ -28,7 +23,7 @@ def get_build_verbosity_extra_flags(level):
|
||||
return []
|
||||
|
||||
|
||||
class BuildSelector(object):
|
||||
class BuildSelector:
|
||||
def __init__(self, build_config, skip_config):
|
||||
self.build_patterns = build_config.split()
|
||||
self.skip_patterns = skip_config.split()
|
||||
@@ -43,7 +38,7 @@ class BuildSelector(object):
|
||||
|
||||
|
||||
# Taken from https://stackoverflow.com/a/107717
|
||||
class Unbuffered(object):
|
||||
class Unbuffered:
|
||||
def __init__(self, stream):
|
||||
self.stream = stream
|
||||
|
||||
@@ -68,7 +63,7 @@ def download(url, dest):
|
||||
repeat_num = 3
|
||||
for i in range(repeat_num):
|
||||
try:
|
||||
response = urlopen(url)
|
||||
response = urllib.request.urlopen(url)
|
||||
except:
|
||||
if i == repeat_num - 1:
|
||||
raise
|
||||
|
||||
@@ -1,13 +1,7 @@
|
||||
from __future__ import print_function
|
||||
import os, tempfile, subprocess, shutil, sys
|
||||
from collections import namedtuple
|
||||
from glob import glob
|
||||
|
||||
try:
|
||||
from shlex import quote as shlex_quote
|
||||
except ImportError:
|
||||
from pipes import quote as shlex_quote
|
||||
|
||||
from .util import prepare_command, get_build_verbosity_extra_flags, download
|
||||
|
||||
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
#!/usr/bin/env python
|
||||
# -*- coding: utf-8 -*-
|
||||
import os, io
|
||||
|
||||
@@ -28,12 +27,11 @@ setup(
|
||||
'cibuildwheel': ['resources/*'],
|
||||
},
|
||||
# Supported python versions
|
||||
python_requires='>=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*',
|
||||
python_requires='>=3.5',
|
||||
keywords='ci wheel packaging pypi travis appveyor macos linux windows',
|
||||
classifiers=[
|
||||
'Intended Audience :: Developers',
|
||||
'Natural Language :: English',
|
||||
'Programming Language :: Python :: 2',
|
||||
'Programming Language :: Python :: 3',
|
||||
'Development Status :: 5 - Production/Stable',
|
||||
'License :: OSI Approved :: BSD License',
|
||||
|
||||
@@ -7,7 +7,7 @@ import subprocess
|
||||
from cibuildwheel import linux, macos, windows, util
|
||||
|
||||
|
||||
class ArgsInterceptor(object):
|
||||
class ArgsInterceptor:
|
||||
def __call__(self, *args, **kwargs):
|
||||
self.args = args
|
||||
self.kwargs = kwargs
|
||||
|
||||
Reference in New Issue
Block a user