Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Linux and Mac arm platforms #352

Merged
merged 40 commits into from
Feb 14, 2022
Merged
Show file tree
Hide file tree
Changes from 23 commits
Commits
Show all changes
40 commits
Select commit Hold shift + click to select a range
4d7615d
forgot tqdm in dev env
AlbertDeFusco Sep 1, 2021
509901e
VSCode settings, debug config, and devcontainer
AlbertDeFusco Sep 10, 2021
3fa9dc2
explicit file name
AlbertDeFusco Sep 27, 2021
1c0950a
fix kwargs for streaming_popen
AlbertDeFusco Jan 11, 2022
c105f7e
add arm platforms and modernize subdir hack
AlbertDeFusco Jan 11, 2022
3b4151f
fix non-x86 platform test
AlbertDeFusco Jan 11, 2022
0ac08c8
remove potential recursion
AlbertDeFusco Jan 11, 2022
23d408b
fix one more test
AlbertDeFusco Jan 11, 2022
682707f
lint
AlbertDeFusco Jan 11, 2022
847cacf
Merge branch 'test-fixes' into arm
AlbertDeFusco Jan 11, 2022
9afa9d3
odd test behavior may be due to py 3.10
AlbertDeFusco Jan 11, 2022
967a2a7
don't forget the defaults channel
AlbertDeFusco Jan 11, 2022
58bf595
matchspec typo
AlbertDeFusco Jan 11, 2022
a257175
it's ok to have msys2 in channels list
AlbertDeFusco Jan 12, 2022
358e5f5
remove unused function
AlbertDeFusco Jan 13, 2022
74708bb
improve coverage
AlbertDeFusco Jan 13, 2022
b03ce0b
lint
AlbertDeFusco Jan 13, 2022
26b9c9e
override channels and update slow tests
AlbertDeFusco Feb 6, 2022
43f5afe
update versions in slow test
AlbertDeFusco Feb 6, 2022
11cdcb3
hmmm
AlbertDeFusco Feb 6, 2022
1c36a0d
expand conda version support
AlbertDeFusco Feb 7, 2022
4821c91
versions are strings
AlbertDeFusco Feb 7, 2022
f934b14
why was pytest pinned in github action?
AlbertDeFusco Feb 7, 2022
393bc9e
try slightly older windows image on github
AlbertDeFusco Feb 9, 2022
97c9933
maybe something odd happened to chardet
AlbertDeFusco Feb 9, 2022
0d8b48d
need for info on failure
AlbertDeFusco Feb 9, 2022
39ee51a
oh, pip was missing!
AlbertDeFusco Feb 9, 2022
1f0728d
refactor offending test on windows
AlbertDeFusco Feb 9, 2022
a65f427
trim failed test combinations
AlbertDeFusco Feb 10, 2022
be6eeaf
one more exclusion
AlbertDeFusco Feb 10, 2022
23ea722
osx-arm64 test fixes
AlbertDeFusco Feb 11, 2022
4201e1e
real conda manager test
AlbertDeFusco Feb 11, 2022
a0e5cff
add osx-arm64 where platforms provided
AlbertDeFusco Feb 11, 2022
7fe44c1
mock logical hash when default platforms are injected
AlbertDeFusco Feb 11, 2022
c3f588e
formatting fixes
AlbertDeFusco Feb 11, 2022
68456c6
update package versions for osx-arm64
AlbertDeFusco Feb 11, 2022
591a22d
skip redis server tests if osx-arm64
AlbertDeFusco Feb 11, 2022
cdbeb4b
update versions for osx-arm64 support
AlbertDeFusco Feb 11, 2022
5d1b5d2
avoid searching for site-packages for now
AlbertDeFusco Feb 11, 2022
3cd280d
slight version adjustment
AlbertDeFusco Feb 11, 2022
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 29 additions & 0 deletions .devcontainer/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
ARG MINICONDA_VERSION='latest'
FROM continuumio/miniconda3:${MINICONDA_VERSION}

ARG USERNAME="vscode"
ARG UID=1000
ARG GID=${UID}
ARG PYTHON_VERSION="3.9"
ARG ENV_NAME="dev"
ARG ENV_YAML=''

##########################################
## It is not a good idea to use root since
## the source directory will be mounted
## into the container. Let's make a new
## user.
RUN groupadd --gid ${GID} ${USERNAME} \
&& useradd --gid ${GID} --uid ${UID} -m ${USERNAME} --create-home --shell /bin/bash
WORKDIR /home/${USERNAME}
USER ${USERNAME}
RUN conda config --prepend pkgs_dirs /home/${USERNAME}/.conda/pkgs

# Environment creation is done in two steps.
# 1. create env with desired Python version
# 2. apply required packages from specified environment.yml file
COPY ${ENV_YAML} /tmp/conda-tmp/environment.yml
RUN conda create -n ${ENV_NAME} python=${PYTHON_VERSION} \
&& if [ -f "/tmp/conda-tmp/environment.yml" ]; then \
conda env update -n ${ENV_NAME} -f /tmp/conda-tmp/environment.yml; \
fi
26 changes: 26 additions & 0 deletions .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"name": "Miniconda",
"build": {
"context": "..",
"dockerfile": "Dockerfile",
"args": {
"MINICONDA_VERSION": "4.8.2",
"PYTHON_VERSION": "3.7.10",
"ENV_NAME": "dev",
"ENV_YAML": "environment.yml"
}
},

// Set *default* container specific settings.json values on container create.
"settings": {
"python.condaPath": "/opt/conda/bin/conda",
},

// Add the IDs of extensions you want installed when the container is created.
"extensions": [
"ms-python.python",
"ms-python.vscode-pylance"
],

"remoteUser": "vscode"
}
17 changes: 13 additions & 4 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ jobs:
matrix:
os: [macos-latest,ubuntu-latest,windows-latest]
pyver: [2.7,3.6,3.7,3.8]
cver: [4.6,4.7,4.8]
cver: [4.6,4.7,4.8, 4.9, "4.10", "4.11"]
exclude:
# Cannot instantiate these environment for these yet
- pyver: 3.8
Expand All @@ -84,12 +84,21 @@ jobs:
cver: 4.7
- pyver: 2.7
cver: 4.8
- pyver: 2.7
cver: 4.9
- pyver: 2.7
cver: "4.10"
- pyver: 2.7
cver: "4.11"
# Conda dropped py36 for base env
- pyver: 3.6
cver: "4.11"
# Unexplained failures in test_download
- pyver: 2.7
os: macos-latest
# https://github.com/tornadoweb/tornado/issues/2804
- pyver: 3.8
os: windows-latest
# - pyver: 3.8
# os: windows-latest
steps:
- name: Retrieve the source code
uses: actions/checkout@v2
Expand All @@ -108,7 +117,7 @@ jobs:
source ./conda/etc/profile.d/conda.sh
[ ${{ matrix.pyver }} == 2.7 ] && BACKPORTS="backports.tempfile backports.functools_lru_cache"
conda create -y -n anaconda-project-dev python=${{ matrix.pyver }} \
$BACKPORTS coverage 'pytest<5' pytest-cov redis notebook bokeh \
$BACKPORTS coverage pytest pytest-cov redis notebook bokeh \
AlbertDeFusco marked this conversation as resolved.
Show resolved Hide resolved
keyring setuptools pip local::anaconda-project
- name: Run the tests
run: |
Expand Down
1 change: 0 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@
*.tmp
*.coverage.*
.idea/
.vscode/

# Compiled source #
###################
Expand Down
24 changes: 24 additions & 0 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
{
// Use IntelliSense to learn about possible attributes.
// Hover to view descriptions of existing attributes.
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
"name": "Python: Current File",
"type": "python",
"request": "launch",
"program": "${file}",
"console": "integratedTerminal"
},
{
"name": "Debug Tests",
"type": "python",
"request": "test",
"console": "integratedTerminal",
"env": {
"PYTEST_ADDOPTS": "--no-cov -vv"
}
}
]
}
5 changes: 5 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"search.exclude": {
"**/envs": true
}
}
159 changes: 40 additions & 119 deletions anaconda_project/internal/conda_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -52,96 +52,20 @@ def _get_conda_command(extra_args):
return cmd_list


# This is obviously ridiculous, we'll work to
# find a better way (at least in newer versions
# of conda).
def _platform_hacked_conda_code(platform, bits):
return """import conda
try:
# this is conda 4.2 and 4.3

# fix whether default channels have msys
import conda.base.constants
from conda.base.constants import DEFAULT_CHANNELS_UNIX, DEFAULT_CHANNELS_WIN
if "{platform}" == 'win':
corrected_channels = DEFAULT_CHANNELS_WIN
else:
corrected_channels = DEFAULT_CHANNELS_UNIX

setattr(conda.base.constants, 'DEFAULT_CHANNELS', corrected_channels)

from conda.base.context import Context

class KapselHackedContext(Context):
@property
def subdir(self):
return "{platform}-{bits}"

@property
def bits(self):
return {bits}

setattr(conda.base.context.context, "__class__", KapselHackedContext)
except ImportError:
# this is conda 4.1
import conda.config

setattr(conda.config, "platform", "{platform}")
setattr(conda.config, "bits", "{bits}")
setattr(conda.config, "subdir", "{platform}-{bits}")

# fix up the default urls
msys_url = 'https://repo.continuum.io/pkgs/msys2'
if "{platform}" == "win":
if msys_url not in conda.config.defaults_:
conda.config.defaults_.append(msys_url)
else:
if msys_url in conda.config.defaults_:
conda.config.defaults_.remove(msys_url)


import conda.cli
import sys

sys.argv[0] = "conda"
sys.exit(conda.cli.main())
""".format(platform=platform, bits=bits).strip() + "\n"


def _get_platform_hacked_conda_command(extra_args, platform):
"""Get conda command and a string representing it in error messages."""
if platform == current_platform() or platform is None:
cmd_list = _get_conda_command(extra_args)
return (cmd_list, " ".join(cmd_list))
else:
(platform_name, bits) = platform.split("-")

conda_code = _platform_hacked_conda_code(platform_name, bits)

# this has to run with the python from the root env,
# so the conda modules will be found.
root_prefix = _get_root_prefix()
root_python = None
for location in (('bin', 'python'), ('python.exe', ), ('Scripts', 'python.exe'), ('Library', 'bin',
'python.exe')):
candidate = os.path.join(root_prefix, *location)
if os.path.isfile(candidate):
root_python = candidate
break
assert root_python is not None

cmd_list = [root_python, '-c', conda_code]
cmd_list.extend(extra_args)
return (cmd_list, " ".join(["conda"] + cmd_list[3:]))


def _call_conda(extra_args, json_mode=False, platform=None, stdout_callback=None, stderr_callback=None):
assert len(extra_args) > 0 # we deref extra_args[0] below

(cmd_list, command_in_errors) = _get_platform_hacked_conda_command(extra_args, platform=platform)
cmd_list = _get_conda_command(extra_args)
command_in_errors = " ".join(cmd_list)

env = None
if platform is not None:
env = os.environ.copy()
env['CONDA_SUBDIR'] = platform

try:
(p, stdout_lines, stderr_lines) = streaming_popen.popen(cmd_list,
env=env,
stdout_callback=stdout_callback,
stderr_callback=stderr_callback)
except OSError as e:
Expand Down Expand Up @@ -230,26 +154,18 @@ def resolve_env_to_prefix(name_or_prefix):
return None


_cached_root_prefix = None


def _get_root_prefix():
global _cached_root_prefix

if _cached_root_prefix is None:
_cached_root_prefix = resolve_env_to_prefix('root')
return _cached_root_prefix


def create(prefix, pkgs=None, channels=(), stdout_callback=None, stderr_callback=None):
"""Create an environment either by name or path with a specified set of packages."""
if os.path.exists(prefix):
raise CondaEnvExistsError('Conda environment [%s] already exists' % prefix)

cmd_list = ['create', '--yes', '--prefix', prefix]
cmd_list = ['create', '--override-channels', '--yes', '--prefix', prefix]

for channel in channels:
cmd_list.extend(['--channel', channel])
if channels:
for channel in channels:
cmd_list.extend(['--channel', channel])
else:
cmd_list.extend(['--channel', 'defaults'])

cmd_list.extend(pkgs)
_call_conda(cmd_list, stdout_callback=stdout_callback, stderr_callback=stderr_callback)
Expand All @@ -275,11 +191,14 @@ def install(prefix, pkgs=None, channels=(), stdout_callback=None, stderr_callbac
raise TypeError('must specify a list of one or more packages to install into existing environment, not %r',
pkgs)

cmd_list = ['install', '--yes']
cmd_list = ['install', '--override-channels', '--yes']
cmd_list.extend(['--prefix', prefix])

for channel in channels:
cmd_list.extend(['--channel', channel])
if channels:
for channel in channels:
cmd_list.extend(['--channel', channel])
else:
cmd_list.extend(['--channel', 'defaults'])

cmd_list.extend(pkgs)
_call_conda(cmd_list, stdout_callback=stdout_callback, stderr_callback=stderr_callback)
Expand Down Expand Up @@ -351,10 +270,19 @@ def resolve_dependencies(pkgs, channels=(), platform=None):
# after we remove it, and then conda's mkdir would fail.
os.rmdir(prefix)

cmd_list = ['create', '--yes', '--quiet', '--json', '--dry-run', '--prefix', prefix]
cmd_list = ['create', '--override-channels', '--yes', '--quiet', '--json', '--dry-run', '--prefix', prefix]

for channel in channels:
cmd_list.extend(['--channel', channel])
if channels:
for channel in channels:
cmd_list.extend(['--channel', channel])
else:
cmd_list.extend(['--channel', 'defaults'])

# This is only needed here (cross-platform solves) and not in create
# or install since Conda defaults already ensure that msys2 is present.
if platform is not None:
if 'win' in platform:
cmd_list.extend(['--channel', 'msys2'])

cmd_list.extend(pkgs)
try:
Expand Down Expand Up @@ -410,7 +338,7 @@ def _contains_conda_meta(path):
return os.path.isdir(conda_meta)


def _is_conda_bindir_unix(path):
def _is_conda_bindir_unix(path): # pragma: no cover (unix only)
if path.endswith("/"):
path = path[:-1]
if not path.endswith("/bin"):
Expand Down Expand Up @@ -636,11 +564,14 @@ def environ_set_prefix(environ, prefix, varname=conda_prefix_variable()):
default_platforms_plus_32_bit = ('linux-32', 'linux-64', 'osx-64', 'win-32', 'win-64')
assert tuple(sorted(default_platforms_plus_32_bit)) == default_platforms_plus_32_bit

_non_x86_linux_machines = {'armv6l', 'armv7l', 'ppc64le'}
_non_x86_linux_machines = {'aarch64', 'armv6l', 'armv7l', 'ppc64le'}
_non_x86_osx_machines = {'arm64'}

# this list will get outdated, unfortunately.
_known_platforms = tuple(
sorted(list(default_platforms_plus_32_bit) + ['osx-32'] + [("linux-%s" % m) for m in _non_x86_linux_machines]))
sorted(
list(default_platforms_plus_32_bit) + ['osx-32'] + [("linux-%s" % m) for m in _non_x86_linux_machines] +
[("osx-%s" % m) for m in _non_x86_osx_machines]))

known_platform_names = ('linux', 'osx', 'win')
assert tuple(sorted(known_platform_names)) == known_platform_names
Expand Down Expand Up @@ -683,18 +614,8 @@ def _known_unix_platforms():


def current_platform():
m = platform.machine()
if m in _non_x86_linux_machines:
return 'linux-%s' % m
else:
_platform_map = {
'linux2': 'linux',
'linux': 'linux',
'darwin': 'osx',
'win32': 'win',
}
p = _platform_map.get(sys.platform, 'unknown')
return '%s-%d' % (p, (8 * tuple.__itemsize__))
conda_info = info()
return conda_info.get('platform')


_default_platforms_with_current = tuple(sorted(list(set(default_platforms + (current_platform(), )))))
Expand Down
2 changes: 1 addition & 1 deletion anaconda_project/internal/streaming_popen.py
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ def ignore_line(line):
if stderr_callback is None:
stderr_callback = ignore_line

p = logged_subprocess.Popen(args, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
p = logged_subprocess.Popen(args, stdout=subprocess.PIPE, stderr=subprocess.PIPE, **kwargs)

queue = Queue()

Expand Down
Loading