- •Об авторе
- •О группе редакторов
- •Предисловие
- •Введение
- •Как использовать эту книгу
- •Загрузка исходного кода CPython
- •Что в исходном коде?
- •Настройка среды разработки
- •IDE или редактор?
- •Настройка Visual Studio
- •Настройка Visual Studio Code
- •Настройка Vim
- •Выводы
- •Компиляция CPython
- •Компиляция CPython на macOS
- •Компиляция CPython на Linux
- •Установка специализированной версии
- •Знакомство с Make
- •Make-цели CPython
- •Компиляция CPython на Windows
- •Профильная оптимизация
- •Выводы
- •Грамматика и язык Python
- •Спецификация языка Python
- •Генератор парсеров
- •Повторное генерирование грамматики
- •Выводы
- •Конфигурация и ввод
- •Конфигурация состояния
- •Структура данных конфигурации среды выполнения
- •Конфигурация сборки
- •Сборка модуля из входных данных
- •Выводы
- •Генерирование конкретного синтаксического дерева
- •Парсер/токенизатор CPython
- •Абстрактные синтаксические деревья
- •Важные термины
- •Пример: добавление оператора «почти равно»
- •Выводы
- •Компилятор
- •Исходные файлы
- •Важные термины
- •Создание экземпляра компилятора
- •Флаги будущей функциональности и флаги компилятора
- •Таблицы символических имен
- •Основная компиляция
- •Ассемблер
- •Создание объекта кода
- •Использование Instaviz для вывода объекта кода
- •Пример: реализация оператора «почти равно»
- •Выводы
- •Цикл вычисления
- •Исходные файлы
- •Важные термины
- •Построение состояния потока
- •Построение объектов кадров
- •Выполнение кадра
- •Стек значений
- •Пример: добавление элемента в список
- •Выводы
- •Управление памятью
- •Выделение памяти в C
- •Проектирование системы управления памятью Python
- •Аллокаторы памяти CPython
- •Область выделения объектной памяти и PyMem
- •Область выделения сырой памяти
- •Нестандартные области выделения памяти
- •Санитайзеры выделенной памяти
- •Арена памяти PyArena
- •Подсчет ссылок
- •Сборка мусора
- •Выводы
- •Параллелизм и конкурентность
- •Модели параллелизма и конкурентности
- •Структура процесса
- •Многопроцессорный параллелизм
- •Многопоточность
- •Асинхронное программирование
- •Генераторы
- •Сопрограммы
- •Асинхронные генераторы
- •Субинтерпретаторы
- •Выводы
- •Объекты и типы
- •Примеры этой главы
- •Встроенные типы
- •Типы объектов
- •Тип type
- •Типы bool и long
- •Тип строки Юникода
- •Словари
- •Выводы
- •Стандартная библиотека
- •Модули Python
- •Модули Python и C
- •Набор тестов
- •Запуск набора тестов в Windows
- •Запуск набора тестов в Linux или macOS
- •Флаги тестирования
- •Запуск конкретных тестов
- •Модули тестирования
- •Вспомогательные средства тестирования
- •Выводы
- •Отладка
- •Обработчик сбоев
- •Компиляция поддержки отладки
- •LLDB для macOS
- •Отладчик Visual Studio
- •Отладчик CLion
- •Выводы
- •Бенчмаркинг, профилирование и трассировка
- •Использование timeit для микробенчмарка
- •Использование набора тестов производительности Python
- •Профилирование кода Python с использованием cProfile
- •Выводы
- •Что дальше?
- •Создание расширений C для CPython
- •Улучшение приложений Python
- •Участие в проекте CPython
- •Дальнейшее обучение
- •Препроцессор C
- •Базовый синтаксис C
- •Выводы
- •Благодарности
Вспомогательные средства тестирования 297
Перед вами фрагмент класса UnicodeTest:
class UnicodeTest(string_tests.CommonTest, string_tests.MixinStrUnicodeUserStringTest, string_tests.MixinStrUnicodeTest, unittest.TestCase):
...
def test_casefold(self): self.assertEqual('hello'.casefold(), 'hello') self.assertEqual('hELlo'.casefold(), 'hello') self.assertEqual('ß'.casefold(), 'ss') self.assertEqual('fi'.casefold(), 'fi')
Оператор «почти равно», реализованный нами для строк Юникода в предыдущих главах, можно расширить и добавить новый тестовый метод в класс
UnicodeTest:
def test_almost_equals(self): self.assertTrue('hello' ~= 'hello') self.assertTrue('hELlo' ~= 'hello') self.assertFalse('hELlo!' ~= 'hello')
Этот конкретный модуль тестирования можно запустить на Windows:
> rt.bat -q -d -x64 test_unicode
Также можно выполнить его на macOS или Linux:
$ ./python -m test test_unicode -v
ВСПОМОГАТЕЛЬНЫЕ СРЕДСТВА ТЕСТИРОВАНИЯ
Импортируя модуль test.support.script_helper, вы получаете доступ к некоторым вспомогательным функциям для тестирования среды выполнения Python:
zz Функция assert_python_ok(*args, **env_vars) выполняет процесс Python с заданными аргументами и возвращает кортеж (код возврата, stdout, stderr).
zz Функция assert_python_failure(*args, **env_vars) похожа на assert_ python_ok(), но проверяет, завершилось ли выполнение неудачей.
zz Функция make_script(script_dir, script_basename, source) создает в script_dir скрипт с именем script_basename и исходным кодом source,
Книги для программистов: https://t.me/booksforits
298 Набор тестов
после чего возвращает путь к этому скрипту. Ее удобно использовать в сочетании с assert_python_ok() или assert_python_failure().
Если вы хотите создать тест, который будет пропускаться, если модуль не был построен, можно воспользоваться вспомогательной функцией test. support.import_module(). Она поднимет исключение SkipTest и даст сигнал программе запуска тестов пропустить этот пакет. Пример:
import test.support
_multiprocessing = test.support.import_module('_multiprocessing')
# Ваши тесты...
ВЫВОДЫ
История средств регрессионного тестирования Python насчитывает более двух десятилетий разработки тестов для необычных, редких случаев, а также для исправления ошибок и введения новой функциональности. За ее пределами остается большая часть стандартной библиотеки CPython с минимумом тестов или вообще без них. Если вы хотите поучаствовать в проекте CPython, то написание или расширение юнит-тестов может стать отличным началом.
Если вы захотите изменить любую часть CPython или добавить функцио нальность, то в качестве обновления вы можете написать свои тесты или расширить существующие.
Книги для программистов: https://t.me/booksforits