Любопытный казус привел к исследованию совместимости процессора Apple M1, и оказалось, что не все так просто...
Впрочем, обо всем по порядку. Мой коллега, владелец MacBook Pro с M1 обратился ко мне с просьбой помочь с установкой библиотеки.
У меня почти такой же MacBook, но на Intel Core i5, macOS Big Sur. При попытке поставить библиотеку
pip install qvd
ERROR: Could not find a version that satisfies the requirement qvd (from versions: none)
ERROR: No matching distribution found for qvd
Обычно такое бывает, когда в составе пакета есть какой-то модуль, несовместимый с текущей ОС. В такой ситуации первое, что я делаю - пытаюсь установить библиотеку в docker container, там у меня очень широкий выбор возможных ОС и настроек.
Dockerfile:
FROM python:3.8-slim-buster
RUN apt-get update && apt-get install -y netcat
COPY . /app
WORKDIR /app
RUN pip install --upgrade pip
RUN pip install -r requirements.txt
CMD ["python", "main.py"]
requirements.txt:
qvd==0.0.10
main.py:
import qvd
if __name__ == '__main__':
print('Hello, qvd')
Далее выполняем команду:
docker build -t testqvd:latest .
И оп-ля, все работает, библиотека встает, образ собирается, контейнер запускается:
docker run testqvd
Hello, qvd
Добавлю (не имеет отношения к данной теме), что библиотека работает по-настоящему, я подключал настоящие файлы и обрабатывал их этой библиотекой.
Отдаю проект коллеге, но у него не собирается!
docker -v
Docker version 20.10.7, build f0df350
У нас обоих версия docker совпадает. В чем может быть причина? Ведь выполнение кода из Dockerfile реально идет в образе python:3.8-slim-buster, он одинаковый у нас. Надо погружаться глубже, разбираться с pip
Для начала посмотрим, почему qvd не ставится на Big Sur:
pip install -vvv qvd
Эта команда выводит очень много текста, но главное, что понятно - none of the wheel's tags (cp37-none-win_amd64) are compatible (run pip debug --verbose to show compatible tags), таких строчек очень много и среди них встречаются только win и manylinux.
Запустим
pip debug --verbose
и получим список подходящих тэгов pip. Никаких win там, конечно, нет, а есть py32-none-macosx_10_13_x86_64 (и похожие). Всех интересующихся, что это значит отсылаю сюда: https://github.com/pypa/manylinux
Тэги совместимости не совпадают, вероятно, по веским причинам - есть библиотеки, которые не смогут запуститься на Big Sur. ОК, понятно, нет вопросов, но есть вопросы, почему при сборке образа на одной и той же ОС из одного и того же источника есть такое существенное отличие.
Добавляю в Dockerfile строчку:
FROM python:3.8-slim-buster
RUN apt-get update && apt-get install -y netcat
COPY . /app
WORKDIR /app
RUN pip install --upgrade pip
RUN pip debug --verbose > /tmp/pip.txt
RUN pip install -r requirements.txt
CMD ["python", "main.py"]
и запускаю сборку вот такой командой:
docker build -t testqvd:latest -o /tmp/buildlogs
В результате получаю файл /tmp/buildlogs/tmp/pip.txt с результатами тэгов pip во время сборки. То же самое делает мой коллега. И они (тэги) получаются разными, у меня, например, - py38-none-manylinux_2_16_x86_64, у коллеги py37-none-manylinux_2_28_aarch64
Вот так, процессор M1 (очевидно) не совпадает с Intel Core и никакими хитрыми docker - технологиями исправить ничего нельзя. Я пока поостерегусь переходить на M1 и другим разработчикам отсоветую.
Комментарии (13)
IRT
04.11.2021 08:20+29Вы серьзно или шутите? Даже я, ни коим боком не относящийся к Python-разработке, и то в курсе, что эти ваши Wheel в питоне в основном служат для дистрибуции предкомпилированных бинарных библиотек под определенную архитектуру. И раз их не нашлось готовых под Darwin/ARM64, то их надо собрать под процессор M1 из исходников, разве нет? И никакой докер в вопросах кроссплатформенности вам не поможет, поскольку это не система виртуализации и программы в докере выполняются на реальном процессоре с соответствующей архитектурой. И в одном и том же контейнере под разными процессорами будет выполняться разный код.
funca
04.11.2021 09:28+4Вообще-то Docker Desktop для MacOS/m1 может запускать как наивные ARM так и x86 контейнеры. Нужно лишь установить Rosetta 2 и при запуске контейнера указать флажок --platform linux/amd64 в командной строке. Это штатная фича из коробки. Производительность так себе, ибо процессор эмулируется, но для разработки на локалхосте в большинстве случаев этого достаточно.
Без флажка, по умолчанию, docker пытается собирать нативные контейнеры под ARM, что может приводить к таким вот казусам как в статье.
vsb
04.11.2021 11:02+1Кстати говоря можно и на x86 запускать ARM-контейнеры (по крайней мере в Linux).
vanyas
04.11.2021 11:10+4Вот именно, всё работает в x86 эмуляции, а не: "никакими хитрыми docker - технологиями исправить ничего нельзя"
apro
04.11.2021 11:56+3поможет, поскольку это не система виртуализации
Насколько я знаю под macos в docker используется именно виртуализация, если точнее то https://developer.apple.com/documentation/hypervisor . Именно поэтому docker настолько медленнее под macos по сравнению с linux.
symbix
04.11.2021 13:11+1На маке через гипервизор запускается линуксовая "хостнода", а в ней уже контейнеры. К ней можно screen-ом подцепиться.
Все тормоза от взаимодействия между "внешней" и "внутренней" хостнодой - в основном тупит I/O.
nikita_dol
04.11.2021 09:24+4Обычно, для запуска кода, который не хочет работать под m1, используют этот префикс:
arch -x86_64 {command}
42p
04.11.2021 10:25+10При наследовании образа укажите --platform=linux/amd64 (укажите свою)
НапримерFROM --platform=linux/amd64 debian:buster-slim
И пакеты будут находиться корректно. Потому что поиск пакетов учитывает то, что система запускается на arm и ищет пакеты под соотвествующую архитектуру. А их делают не всегда.
qant
04.11.2021 14:37+3Статья конечно так себе... но за то сколько дельных и полезных комментариев! Спасибо вам народ!
grigoryvp
05.11.2021 09:03+1Это "бинарный пакет", qvd · PyPI. Автор библиотеки собрал ее из Rust исходников на своем ноутбуке под несколько комбинаций операционка-проц-версия-пайтона. При этом сами исходники он не приложил. Получилась очень "калечная" версия библиотеки которая не будет работать в окружении, сильно отличающемся от окружения создавшего ее разработчика. Хорошим тоном считается делать версию с исходниками, которая бы собиралась на компьютере разработчика. Например, как это делают авторы подавляющего большинства библиотек с нативным кодом: Pillow · PyPI - обратите внимание на "source" дистрибьюцию в списке. Ну и зацените, насколько больше список предсобранных комбинаций.
Berserkr
Серьезно? И инвайт за это?
Kromeshnaja
Синдром вахтёра?
funca
Надо ещё влепить минусов статье и слить автору карму, чтобы всем показать как он неправ. Хабр это же теперь филиал дзен для лириков, а не технических тем.
Ректор университета просмотрел смету, которую ему принес декан физфака, и, вздохнув, сказал: — Почему это физики всегда требуют такое дорогое оборудование? Вот, например, математики просят лишь деньги на бумагу, карандаши и ластики. И, подумав, добавил: — А философы, те ещё лучше. Им даже ластики не нужны.