В Unix-подобных системах, таких как Linux или macOS, а также Windows, Python3 теперь использует новую интерактивную оболочку. Когда пользователь запускает REPL из интерактивного терминала, интерактивная оболочка поддерживает следующие новые функции:
>>>
и ...
.help
, exit
, и quit
без необходимости использовать круглые скобки для вызова после имени команды.Если новая интерактивная оболочка нежелательна, то ее можно отключить с помощью переменной окружения PYTHON_BASIC_REPL
. Новая оболочка для Unix-подобных систем требует установленного модуля curses
.
Рекомендация: в период обучения Python3 рекомендуем установить модуль
ptpython
, который создан для этих целей
- Подсветка синтаксиса.
- Многострочное редактирование (стрелка вверх работает).
- Автодополнение.
- Поддержка мыши.
- Поддержка цветовых схем.
- Поддержка вставки в квадратных скобках.
- Привязки клавиш Vi и Emacs.
- … и многое другое.
Интерпретатор Python3.13 по умолчанию настроен на использование цветов для выделения выходных данных в определенных ситуациях, например, при отображении трассировок. Этим поведением можно управлять, устанавливая различные переменные среды.
Установка переменной окружения TERM
на dumb
отключит цвет.
Если задана переменная окружения FORCE_COLOR
, то цвет будет включен независимо от значения TERM
. Это полезно в системах CI, которые не являются терминалами, но все равно могут отображать управляющие последовательности ANSI.
Если задана переменная окружения NO_COLOR
, то Python3.13 отключит все цвета в выходных данных. Это имеет приоритет над FORCE_COLOR
.
Все эти переменные окружения используются также другими инструментами для управления выводом цвета. Для управления выводом цвета только в интерпретаторе Python можно использовать переменную окружения PYTHON_COLORS
. Эта переменная имеет приоритет над NO_COLOR
, которая, в свою очередь, имеет приоритет над FORCE_COLOR
.
Интерпретатор теперь раскрашивает сообщения об ошибках при отображении обратных трассировок по умолчанию. Этой функцией можно управлять с помощью новой переменной среды PYTHON_COLORS
, а также канонических переменных среды NO_COLOR
и FORCE_COLOR
.
При возникновении ошибки интерпретатор выводит сообщение об ошибке и трассировку стека. Затем в интерактивном режиме он возвращается к основной подсказке. Когда входные данные поступают из файла, он завершает работу с ненулевым статусом завершения после печати трассировки стека. Исключения, обрабатываемые инструкцией try
и предложением except
, не являются ошибками в данном контексте. Некоторые ошибки являются безусловно фатальными и приводят к завершению с ненулевым статусом завершения; это относится к внутренним несоответствиям и некоторым случаям нехватки памяти. Все сообщения об ошибках записываются в стандартный поток ошибок. Обычный вывод выполняемых команд записывается в стандартный вывод.
Ввод символа прерывания (обычно Ctrl-C или Delete) в основное или дополнительное приглашение отменяет ввод и возвращает к основному приглашению. Передача прерывания во время выполнения команды вызывает исключение KeyboardInterrupt
, которое может быть обработано с помощью инструкции try ... except
.
Распространенной ошибкой является написание скрипта с тем же именем, что и у модуля стандартной библиотеки. Если это приводит к ошибкам, то теперь отображается более полезное сообщение об ошибке:
$ python random.py # Traceback (most recent call last): # File "/home/random.py", line 1, in <module> # import random; print(random.randint(5)) # ^^^^^^^^^^^^^ # File "/home/random.py", line 1, in <module> # import random; print(random.randint(5)) # ^^^^^^^^^^^^^^ # AttributeError: module 'random' has no attribute 'randint' (consider renaming # '/home/random.py' since it has the same name as the standard library module # named 'random' and the import system gives it precedence)
Аналогично, если скрипт имеет то же имя, что и сторонний модуль, который он пытается импортировать, и это приводит к ошибкам, теперь также отображается более полезное сообщение об ошибке:
$ python numpy.py # Traceback (most recent call last): # File "/home/numpy.py", line 1, in <module> # import numpy as np; np.array([1,2,3]) # ^^^^^^^^^^^^^^^^^^ # File "/home/numpy.py", line 1, in <module> # import numpy as np; np.array([1,2,3]) # ^^^^^^^^ # AttributeError: module 'numpy' has no attribute 'array' # (consider renaming '/home/numpy.py' if it has the same # name as a third-party module you intended to import)
Когда в функцию передается неверный ключевой аргумент, то сообщение об ошибке теперь может указывать на правильный аргумент.
>>> "better error messages!".split(max_split=1) # Traceback (most recent call last): # File "<stdin>", line 1, in <module> # "better error messages!".split(max_split=1) # ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^ # TypeError: split() got an unexpected keyword argument 'max_split'. Did you mean 'maxsplit'?
Классы имеют новый атрибут __static_attributes__
, заполняемый компилятором кортежем имен атрибутов этого класса, доступ к которым осуществляется через self.X
из любой функции в его теле.
В системах Unix скрипты Python можно сделать исполняемыми напрямую, подобно скриптам оболочки bash, поместив строку #!/usr/bin/env python3
в начале скрипта, при условии, что путь к интерпретатору находится в пользовательском PATH
. #!
должны быть первыми двумя символами файла. На некоторых платформах эта первая строка должна заканчиваться переводом строки в стиле Unix ('\n'), а не Windows ('\r\n'). Обратите внимание, что символ хеша, '#'
, используется для начала комментария в Python.
Скрипту можно присвоить исполняемый режим или разрешение, используя команду bash chmod
: $ chmod + x myscript.py
.
В системах Windows нет понятия "исполняемый режим". Программа установки Python автоматически связывает расширение файлов .py
с python.exe
, так что двойной щелчок по файлу Python запускает его как скрипт. Расширение также может быть .pyw
, в этом случае окно консоли, которое обычно появляется, будет отключено.
При интерактивном использовании Python часто бывает удобно выполнять некоторые стандартные команды при каждом запуске интерпретатора. Это можно сделать, установив переменную окружения с именем PYTHONSTARTUP
в качестве имени файла, содержащего команды запуска. Это похоже на функцию .profile
оболочек Unix.
Этот файл читается только в интерактивных сеансах, не тогда, когда Python считывает команды из скрипта, и не тогда, когда /dev/tty
указан в качестве явного источника команд (который в противном случае ведет себя как интерактивный сеанс). Он выполняется в том же пространстве имен, где выполняются интерактивные команды, так что объекты, которые он определяет или импортирует, могут использоваться без каких-либо оговорок. Также, в этом файле можно изменить подсказки sys.ps1
и sys.ps2
.
>>> import sys >>> sys.ps1 # '>>> ' >>> sys.ps2 # '... ' >>> sys.ps1 = 'C> ' C> print('Yuck!') # Yuck! C>
Если необходимо прочитать дополнительный стартовый файл из текущего каталога, то можно запрограммировать это в глобальном стартовом файле, используя код типа if os.path.isfile('.pythonrc.py'): exec(open('.pythonrc.py').read())
. Если нужно использовать загрузочный файл в скрипте, то должны сделать это явно в скрипте:
import os filename = os.environ.get('PYTHONSTARTUP') if filename и os.path.isfile(filename): with open(filename) as fobj: startup_file = fobj.read() exec(startup_file)
Python предоставляет два хука, позволяющих его настраивать: sitecustomize
и usercustomize
. Чтобы посмотреть, как это работает, нужно сначала найти расположение пользовательских пакетов site-packages
. Запустите Python3 и выполните этот код:
>>> import site >>> site.getusersitepackages() # '/home/user/.local/lib/python3.x/site-packages'
Теперь, в этом каталоге можно создать файл с именем usercustomize.py
и поместить в него все, что захотите. Это повлияет на каждый вызов Python, если только он не запускается с опцией -s
, которая отключает автоматический импорт.
sitecustomize работает таким же образом, но обычно создается администратором компьютера в глобальном каталоге пакетов сайта и импортируется перед usercustomize. Смотрите документацию к site модулю для получения более подробной информации.
Попробовать улучшенный интерпретатор в Python 3.13 (любую новую/старую версию Python3) без компиляции исходников и установки в виртуальное окружение можно используя технологию Docker. Контейнеризация приложений при помощи Docker в настоящее время стала золотым стандартом портируемости/переносимости программного обеспечения. (Да, мы знаем, что правительство США на пару недель блокировало доступ из РФ к https://hub.docker.com, но компания Docker отстояла право быть открытой)
Практически все выпуски Python3 хранятся на странице "Официальные образы Python3" https://hub.docker.com/_/python.
Официальные образы Python3 Docker - это тщательно подобранный набор репозиториев Docker с открытым исходным кодом (вот из за этих слов был разблокирован Docker) и готовых решений. Эти образы имеют четкую документацию, пропагандируют лучшие практики и предназначены для наиболее распространенных случаев использования.
Тенденция создания многих официальных образов из исходного кода является прямым результатом попыток внимательно следовать официальным рекомендациям каждого вышестоящего разработчика относительно того, как развертывать и использовать их продукт/проект.
Для того, чтобы запустить контейнер с Python3 из образа Docker необходимо его установить. Самым простым способом установки Docker на OS Linux служит система развёртывания и управления пакетами snap
, разработанная Canonical для Ubuntu. Всё это работает на широком спектре дистрибутивов Linux и позволяет создавать дистрибутивно-независимые программы.
# ставим Docker на Desktop $ sudo snap install docker
После установки, идем на страницу https://hub.docker.com/_/python/tags и выбираем нужный образ (например, напишем в поле "Filter tags" 3.13
), пусть это будет "3.13-rc-slim". Справа от тега есть команда, которой можно загрузить выбранный образ на локальный компьютер.
# загрузка официального образа Python 3.13 # на локальный компьютер $ sudo docker pull python:3.13-rc-slim
Осталось только запустить контейнер с Python 3.13 и попробовать новый цветной интерактивный интерпретатор.
# запуск Python 3.13 в интерактивном режиме $ sudo docker run -it --rm python:3.13-rc-slim # Python 3.13.0b2 (main, Jul 2 2024, 03:33:35) [GCC 12.2.0] on linux # Type "help", "copyright", "credits" or "license" for more information. # >>> import os # >>> os.process_cpu_count() # 2
где следующие параметры означают:
-it
запускать контейнер в интерактивном режиме--rm
удалить контейнер после завершения интерактивного режимаИли по быстренькому запустить скрипт в Python 3.13.
Для примера, возьмем следующий скрипт python3:
# test.py import sys print('sys.path=', sys.path, end='\n\n') print('###########') print('sys.copyright =>', sys.copyright, end='\n\n') print('###########') print('sys.version =>', sys.version, end='\n\n') print('###########') print('sys.api_version =>', sys.api_version, end='\n\n') print('###########') print('sys.version_info =>', sys.version_info, end='\n\n') print('###########') print('sys.implementation =>', sys.implementation, end='\n\n')
и запустим его в окружении docker-python:
# запуск скрипта в Python 3.13 $ sudo docker run -v /path/to/script:/root -w /root --rm python:3.13-rc-slim python3 test.py
где следующие параметры означают:
-v /path/to/script:/root
- монтирует директорию /path/to/script
(папку, где лежит скрипт test.py
) в папку /root
запускаемого контейнера. Путь должен быть абсолютным...-w /root
- устанавливает папку /root
в качестве рабочего каталога.--rm
- удаляет контейнер после завершения работы скриптаВнимание! Вызываемый скрипт запустится от имени пользователя
root
, но при этом не сможет выйти за пределы или переместиться выше примонтированной к контейнеру папки/path/to/script
. Другими словами, папка/path/to/script
выполняет роль своеобразной песочницы для выполняемого скрипта python. Так что такой запуск вполне беопасен для ОС.
Вывод работы скрипта:
$ sudo docker run -v /home/to/script:/root -w /root --rm python:3.13-rc-slim python3 test.py # sys.path= ['/root', '/usr/local/lib/python313.zip', '/usr/local/lib/python3.13', '/usr/local/lib/python3.13/lib-dynload', '/usr/local/lib/python3.13/site-packages'] # # ########### # sys.copyright => Copyright (c) 2001-2024 Python Software Foundation. # All Rights Reserved. # # Copyright (c) 2000 BeOpen.com. # All Rights Reserved. # # Copyright (c) 1995-2001 Corporation for National Research Initiatives. # All Rights Reserved. # # Copyright (c) 1991-1995 Stichting Mathematisch Centrum, Amsterdam. # All Rights Reserved. # # ########### # sys.version => 3.13.0b2 (main, Jul 2 2024, 03:33:35) [GCC 12.2.0] # # ########### # sys.api_version => 1013 # # ########### # sys.version_info => sys.version_info(major=3, minor=13, micro=0, releaselevel='beta', serial=2) # # ########### # sys.implementation => namespace(name='cpython', cache_tag='cpython-313', version=sys.version_info(major=3, minor=13, micro=0, releaselevel='beta', serial=2), hexversion=51183794, _multiarch='x86_64-linux-gnu')