Введение

В мире разработки программного обеспечения автоматизация тестирования играет ключевую роль, помогая улучшить качество кода, ускорить процесс разработки и гарантировать надежность приложений. Python, с его богатым набором библиотек, предоставляет отличную платформу для создания современных фреймворков автоматизации. В данной статье мы рассмотрим подробный план создания фреймворка автоматизации на Python, используя популярные библиотеки, такие как Pytest, Selene, WebDriver‑Manager, Selenium, Requests, Allure, Pydantic, SQLAlchemy, Mimesis, Black, Isort и Flake8.

Зачем нам нужен фреймворк автоматизации?

Автоматизация тестирования предоставляет несколько ключевых преимуществ в процессе разработки:

  1. Ускорение Разработки: Автоматические тесты могут быстро выполняться, что уменьшает временные затраты на проверку работоспособности кода.

  2. Повышение Надежности: Автоматизация исключает человеческий фактор, связанный с ручным тестированием, и позволяет создавать стабильные и надежные тесты.

  3. Оценка Качества Кода: Автоматические тесты могут служить индикаторами качества кода, предупреждая о возможных проблемах и соблюдении стандартов.

  4. Быстрая Обратная Связь: Отчеты от автоматизированных тестов предоставляют быструю обратную связь о состоянии приложения, что помогает оперативно выявлять и устранять ошибки.

  5. Экономия Ресурсов: За счет автоматизации можно эффективно использовать ресурсы, освобождая команду от монотонных и рутинных задач.

Шаг 1: Установка зависимостей

Первый шаг в построении фреймворка автоматизации — это установка необходимых библиотек и инструментов. В нашем случае мы будем использовать следующие библиотеки:

  • Pytest: мощный фреймворк для написания и организации тестов.

  • Selene: обертка над Selenium для упрощения взаимодействия с веб‑элементами.

  • WebDriver‑Manager: автоматическое управление веб‑драйверами.

  • Selenium: библиотека для автоматизации веб‑браузеров.

  • Requests: библиотека для работы с HTTP‑запросами.

  • Allure: инструмент для создания красочных отчетов о тестировании.

  • Pydantic: библиотека для валидации данных и конфигураций.

  • SQLAlchemy: ORM (Object‑Relational Mapping) для работы с базой данных.

  • Mimesis: библиотека для генерации тестовых данных.

  • Black: автоматический форматтер кода.

  • Isort: инструмент для сортировки импортов в коде.

  • Flake8: линтер кода для выявления потенциальных проблем.

Пример установки зависимостей:

pip install pytest selene webdriver-manager selenium requests allure-pytest pydantic sqlalchemy mimesis black isort flake8

Пояснение:

  1. Pytest: Фреймворк для написания и запуска тестов. Он предоставляет удобный синтаксис и разнообразные возможности для тестирования.

  2. Selene: Обертка над Selenium, облегчающая написание тестов и взаимодействие с веб‑элементами.

  3. WebDriver‑Manager: Управление веб‑драйверами, обеспечивая автоматическую установку и обновление.

  4. Selenium: Библиотека для автоматизации веб‑браузеров.

  5. Requests: Используется для отправки HTTP‑запросов, что полезно при тестировании API.

  6. Allure: Инструмент для создания красочных отчетов о тестировании с поддержкой различных языков программирования.

  7. Pydantic: Позволяет определять и валидировать данные при помощи структурного описания.

  8. SQLAlchemy: ORM для работы с базой данных. Удобен для взаимодействия с базой данных в тестах.

  9. Mimesis: Библиотека для генерации тестовых данных, таких как имена, адреса, почтовые ящики и т. д.

  10. Black: Автоматический форматтер кода, способствующий поддержанию единообразного стиля.

  11. Isort: Инструмент для автоматической сортировки импортов в коде.

  12. Flake8: Линтер кода, который помогает выявить потенциальные проблемы и несоответствия стандартам.

Эти библиотеки предоставляют набор инструментов для создания мощного и эффективного фреймворка автоматизации тестирования на Python. В следующих шагах мы рассмотрим, как эти инструменты могут быть использованы для построения структуры фреймворка и написания тестов.

Шаг 2: Структура проекта

Правильная структура проекта является фундаментом успешного развертывания и поддержки фреймворка автоматизации. В данном разделе мы рассмотрим оптимальную структуру проекта и объясним, почему каждая часть важна.

1. Каталог tests

В этом каталоге мы будем хранить все наши тесты. Каждый файл в этом каталоге представляет собой отдельный тестовый сценарий или группу связанных тестов.

automation_framework/
|-- tests/
|   |-- test_login.py
|   |-- test_registration.py

Пояснение:

  • test_login.py: Файл с тестами для функционала входа в систему.

  • test_registration.py: Файл с тестами для функционала регистрации.

2. Каталог pages

В этом каталоге мы будем хранить классы, представляющие страницы веб‑приложения. Каждая страница должна содержать методы для взаимодействия с элементами на странице.

automation_framework/
|-- pages/
|   |-- base_page.py
|   |-- login_page.py
|   |-- registration_page.py

Пояснение:

  • base_page.py: Базовый класс для всех страниц, содержащий общие методы, такие как открытие URL и поиск элементов.

  • login_page.py: Класс, представляющий страницу входа в систему, с методами для ввода логина и пароля, а также выполнения входа.

  • registration_page.py: Класс, представляющий страницу регистрации, с методами для ввода данных и выполнения регистрации.

3. Каталог utilities

В этом каталоге мы будем хранить вспомогательные утилиты, которые могут быть использованы в тестах.

automation_framework/
|-- utilities/
|   |-- config.py
|   |-- webdriver_manager.py
|   |-- api_client.py
|   |-- data_generator.py

Пояснение:

  • config.py: Файл с конфигурационными данными, такими как URL приложения и учетные данные.

  • webdriver_manager.py: Утилита для управления веб‑драйвером.

  • api_client.py: Утилита для взаимодействия с API приложения.

  • data_generator.py: Утилита для генерации тестовых данных.

4. Каталог models

В этом каталоге мы будем хранить модели данных, которые могут быть использованы для валидации и передачи данных в тестах.

automation_framework/
|-- models/
|   |-- user.py

Пояснение:

  • user.py: Модель данных для представления пользователя, содержащая поля, такие как логин и пароль.

5. Файл main.py

Этот файл может служить точкой входа для запуска тестов, объединяя их в единый тестовый набор.

automation_framework/
|-- main.py

Пояснение:

  • main.py: Файл, содержащий код для запуска тестов или тестовых наборов.

Эта структура проекта обеспечивает логичное разделение ответственности и позволяет удобно организовывать и добавлять новые тесты, страницы и утилиты. В следующих шагах мы будем дополнять эту структуру кодом, чтобы создать полноценный фреймворк автоматизации.

Шаг 3: Настройка конфигурации

Настройка конфигурации важна для централизованного хранения данных, таких как URL приложения, учетные данные и другие параметры, которые могут изменяться в процессе разработки или в зависимости от среды выполнения тестов. Создание отдельного модуля для управления конфигурацией упрощает поддержку кода и делает его более гибким.

1. Создание файла config.py

В этом файле мы будем определять класс Config, который будет содержать переменные для различных параметров конфигурации.

# automation_framework/utilities/config.py

class Config:
    BASE_URL = "https://example.com"
    API_BASE_URL = "https://api.example.com"
    USERNAME = "your_username"
    PASSWORD = "your_password"

Пояснение:

  • BASE_URL: Адрес веб-приложения, с которым будут взаимодействовать тесты.

  • API_BASE_URL: Адрес API приложения, если оно предоставляет такую возможность.

  • USERNAME и PASSWORD: Учетные данные, которые могут использоваться для входа в систему или других операций.

2. Использование конфигурации в тестах и утилитах

Теперь мы можем использовать значения из конфигурации в наших тестах и утилитах.

# automation_framework/tests/test_login.py

from utilities.config import Config

def test_login_successful():
    username = Config.USERNAME
    password = Config.PASSWORD

    # Теперь можно использовать username и password в тесте
    # ...
# automation_framework/utilities/api_client.py

from utilities.config import Config

class APIClient:
    @staticmethod
    def login():
        url = f"{Config.API_BASE_URL}/login"
        data = {"username": Config.USERNAME, "password": Config.PASSWORD}
        # Отправка запроса с использованием данных из конфигурации
        # ...

Этот подход упрощает обновление учетных данных или URL при изменении среды выполнения тестов (например, переход с тестового сервера на продакшн).

Настройка конфигурации важна для поддержания чистоты кода и обеспечения его гибкости в условиях изменяющихся требований. В следующих шагах мы продолжим наше развитие, используя созданный конфигурационный файл в других частях фреймворка.

Шаг 4: Управление веб-драйвером

Управление веб‑драйвером является важной частью фреймворка для автоматизации тестирования веб‑приложений. Здесь мы рассмотрим, как использовать библиотеку webdriver-manager для автоматического управления установкой и обновлением веб‑драйверов, а также создадим утилиту для управления самим веб‑драйвером.

1. Создание утилиты для управления веб-драйвером

# automation_framework/utilities/webdriver_manager.py

from selenium import webdriver
from webdriver_manager.chrome import ChromeDriverManager

class WebDriverManager:
    @staticmethod
    def get_driver():
        driver = webdriver.Chrome(ChromeDriverManager().install())
        driver.maximize_window()
        return driver

Пояснение:

  • get_driver: Метод, который создает и возвращает экземпляр веб-драйвера. В данном случае используется ChromeDriver, но вы можете легко адаптировать этот код для других браузеров.

2. Использование утилиты в тестах

Теперь мы можем использовать эту утилиту в наших тестах для получения экземпляра веб-драйвера.

# automation_framework/tests/test_login.py

from utilities.webdriver_manager import WebDriverManager

def test_login_successful():
    driver = WebDriverManager.get_driver()

    # Теперь можно использовать driver для взаимодействия с браузером
    # ...

    # Не забудьте закрыть браузер после завершения теста
    driver.quit()

Этот подход обеспечивает автоматическую установку и обновление веб‑драйвера при каждом запуске теста, что упрощает поддержку кода и предотвращает проблемы с несоответствием версий.

Управление веб‑драйвером — это важный шаг для создания стабильного и легко поддерживаемого фреймворка. В следующих шагах мы будем использовать созданный веб‑драйвер в наших тестах для взаимодействия с веб‑приложением.

Шаг 5: Базовая страница

Базовая страница — это класс, который содержит общие методы и функциональность для всех страниц вашего веб‑приложения. Создание базовой страницы помогает уменьшить дублирование кода и обеспечивает удобство в поддержке.

1. Создание базовой страницы

# automation_framework/pages/base_page.py

from selene.support.jquery_style_selectors import s

class BasePage:
    def open_url(self, url):
        s.open(url)

    def find_element(self, selector):
        return s(selector)

Пояснение:

  • open_url: Метод для открытия заданного URL в браузере.

  • find_element: Метод для поиска элемента на странице по селектору.

2. Использование базовой страницы в других страницах

# automation_framework/pages/login_page.py

from base_page import BasePage
from utilities.config import Config
from selene.support.jquery_style_selectors import s

class LoginPage(BasePage):
    def login(self, username, password):
        self.open_url(Config.BASE_URL)
        self.find_element('#username').type(username)
        self.find_element('#password').type(password)
        self.find_element('[type="submit"]').click()

Пояснение:

  • LoginPage: Класс, который наследуется от BasePage. Содержит специфичные для страницы методы.

3. Использование базовой страницы в тестах

# automation_framework/tests/test_login.py

from pages.login_page import LoginPage

def test_login_successful():
    login_page = LoginPage()
    login_page.login("your_username", "your_password")

    # Добавьте проверки успешного входа
    # ...

Пояснение:

  • test_login_successful: Тест, который создает экземпляр LoginPage и использует его методы для взаимодействия с веб-приложением.

Создание базовой страницы упрощает создание новых страниц, так как вам не нужно повторять общие методы на каждой странице. Это также способствует поддерживаемости кода и его легкости в расширении. В следующих шагах мы будем дополнять функциональность страниц и использовать их в тестах.

Шаг 6: Страницы приложения

Страницы приложения представляют собой классы, содержащие методы для взаимодействия с элементами веб‑страниц. Каждый класс страницы соответствует определенной странице вашего веб‑приложения, и содержит методы для выполнения действий на этой странице.

1. Создание страницы входа (Login Page)

# automation_framework/pages/login_page.py

from base_page import BasePage
from utilities.config import Config
from selene.support.jquery_style_selectors import s

class LoginPage(BasePage):
    def login(self, username, password):
        self.open_url(Config.BASE_URL)
        self.find_element('#username').type(username)
        self.find_element('#password').type(password)
        self.find_element('[type="submit"]').click()

Пояснение:

  • LoginPage: Класс, представляющий страницу входа в систему.

  • login: Метод, выполняющий вход в систему с заданным именем пользователя и паролем.

2. Создание страницы регистрации (Registration Page)

# automation_framework/pages/registration_page.py

from base_page import BasePage
from utilities.config import Config
from selene.support.jquery_style_selectors import s

class RegistrationPage(BasePage):
    def register(self, username, password, email):
        self.open_url(Config.BASE_URL)
        self.find_element('#username').type(username)
        self.find_element('#password').type(password)
        self.find_element('#email').type(email)
        self.find_element('[type="submit"]').click()

Пояснение:

  • RegistrationPage: Класс, представляющий страницу регистрации.

  • register: Метод, выполняющий регистрацию с заданными данными пользователя.

3. Использование страниц в тестах

# automation_framework/tests/test_login.py

from pages.login_page import LoginPage
from pages.registration_page import RegistrationPage

def test_login_successful():
    login_page = LoginPage()
    login_page.login("your_username", "your_password")

    # Добавьте проверки успешного входа
    # ...

def test_registration_successful():
    registration_page = RegistrationPage()
    registration_page.register("new_user", "new_password", "new_user@example.com")

    # Добавьте проверки успешной регистрации
    # ...

Пояснение:

  • test_login_successful: Тест, который использует метод login из LoginPage для выполнения входа.

  • test_registration_successful: Тест, который использует метод register из RegistrationPage для выполнения регистрации.

Создание отдельных классов страниц позволяет абстрагироваться от деталей реализации и делает тесты более понятными и легко поддерживаемыми. В следующих шагах мы добавим дополнительную функциональность к страницам и использование их методов в тестах.

Шаг 7: API Клиент

API клиент представляет собой утилиту для взаимодействия с API вашего веб‑приложения. В этом шаге мы создадим простой API клиент, который может отправлять HTTP‑запросы, такие как POST для регистрации пользователя.

1. Создание API клиента

# automation_framework/utilities/api_client.py

import requests
from utilities.config import Config

class APIClient:
    @staticmethod
    def register_user(username, password, email):
        url = f"{Config.API_BASE_URL}/register"
        data = {"username": username, "password": password, "email": email}
        response = requests.post(url, json=data)
        return response.json()

Пояснение:

  • register_user: Статический метод, отправляющий POST-запрос для регистрации нового пользователя. Возвращает ответ в формате JSON.

2. Использование API клиента в тестах

# automation_framework/tests/test_registration.py

from utilities.api_client import APIClient

def test_registration_successful():
    username = "new_user"
    password = "new_password"
    email = "new_user@example.com"

    # Отправка запроса на регистрацию пользователя
    response = APIClient.register_user(username, password, email)

    # Проверки успешной регистрации
    assert response["status"] == "success"
    assert response["message"] == "User registered successfully"

    # Дополнительные проверки, если необходимо
    # ...

Пояснение:

  • test_registration_successful: Тест, который использует метод register_user из APIClient для регистрации нового пользователя через API. Затем проверяет ответ API на успешную регистрацию.

API клиент позволяет вам интегрировать тестирование ваших API в общий фреймворк автоматизации. В следующих шагах мы будем комбинировать тестирование веб‑приложения и API, чтобы создать более комплексные тесты.

Шаг 8: Генерация Тестовых Данных

Генерация тестовых данных — важный аспект автоматизации тестирования, особенно при регистрации новых пользователей или заполнении форм. В этом шаге мы создадим утилиту для генерации тестовых данных, используя библиотеку mimesis.

1. Создание утилиты для генерации тестовых данных

# automation_framework/utilities/data_generator.py

from mimesis import Generic

class DataGenerator:
    @staticmethod
    def generate_username():
        return Generic().person.username()

    @staticmethod
    def generate_password():
        return Generic().person.password()

    @staticmethod
    def generate_email():
        return Generic().person.email()

Пояснение:

  • generate_username, generate_password, generate_email: Статические методы, использующие библиотеку mimesis для генерации уникальных значений для имени пользователя, пароля и электронной почты.

2. Использование утилиты в тестах

# automation_framework/tests/test_registration.py

from utilities.data_generator import DataGenerator
from utilities.api_client import APIClient

def test_registration_successful():
    # Генерация уникальных тестовых данных
    username = DataGenerator.generate_username()
    password = DataGenerator.generate_password()
    email = DataGenerator.generate_email()

    # Отправка запроса на регистрацию пользователя с сгенерированными данными
    response = APIClient.register_user(username, password, email)

    # Проверки успешной регистрации
    assert response["status"] == "success"
    assert response["message"] == "User registered successfully"

    # Дополнительные проверки, если необходимо
    # ...

Пояснение:

  • test_registration_successful: Тест, который использует методы DataGenerator для генерации уникальных тестовых данных при каждом запуске теста. Затем эти данные используются для регистрации нового пользователя через API.

Генерация тестовых данных с помощью библиотеки mimesis позволяет создавать разнообразные и уникальные значения для тестов, что повышает их реалистичность. В следующих шагах мы будем использовать созданные утилиты для генерации данных в наших тестах.

Шаг 9: Модель данных

Использование моделей данных в автоматизированных тестах помогает структурировать информацию и упрощает валидацию ожидаемых результатов. В этом шаге мы создадим простую модель данных для представления пользователя.

1. Создание модели данных

# automation_framework/models/user.py

from pydantic import BaseModel

class User(BaseModel):
    username: str
    password: str
    email: str

Пояснение:

  • User: Класс-модель данных, созданный с использованием библиотеки pydantic. Он определяет поля, которые могут принимать значения строкового типа.

2. Использование модели данных в тестах

# automation_framework/tests/test_registration.py

from utilities.data_generator import DataGenerator
from utilities.api_client import APIClient
from models.user import User

def test_registration_successful():
    # Генерация уникальных тестовых данных
    user_data = User(
        username=DataGenerator.generate_username(),
        password=DataGenerator.generate_password(),
        email=DataGenerator.generate_email()
    )

    # Отправка запроса на регистрацию пользователя с использованием модели данных
    response = APIClient.register_user(user_data.username, user_data.password, user_data.email)

    # Проверки успешной регистрации
    assert response["status"] == "success"
    assert response["message"] == "User registered successfully"

    # Дополнительные проверки, если необходимо
    # ...

Пояснение:

  • test_registration_successful: Тест, который использует модель данных User для структурирования тестовых данных. Это делает код более читаемым и обеспечивает типизацию данных при использовании в тестах.

Использование моделей данных, таких как User, может значительно улучшить читаемость и поддерживаемость вашего кода. Кроме того, библиотека pydantic предоставляет встроенную валидацию данных, что обеспечивает дополнительный уровень надежности ваших тестов. В следующих шагах мы продолжим использовать эту модель в различных частях фреймворка.

Шаг 10: Тесты с использованием Pytest

Pytest — мощный фреймворк для написания и запуска тестов в Python. В этом шаге мы рассмотрим, как написать тесты с использованием Pytest, а также как использовать различные возможности этого фреймворка.

1. Написание простого теста

# automation_framework/tests/test_example.py

def test_example():
    assert 1 + 1 == 2

Пояснение:

  • test_example: Пример простого теста. Pytest автоматически обнаруживает функции, начинающиеся с test_, и считает их тестами.

2. Использование Pytest с фикстурами

# automation_framework/tests/test_fixture.py

import pytest

# Фикстура для подготовки данных перед тестом
@pytest.fixture
def prepare_data():
    data = {'key': 'value'}
    return data

# Тест, использующий фикстуру
def test_using_fixture(prepare_data):
    assert 'key' in prepare_data
    assert prepare_data['key'] == 'value'

Пояснение:

  • prepare_data: Фикстура, которая возвращает подготовленные данные. Фикстуры - это способ предварительной настройки данных или ресурсов перед выполнением тестов.

  • test_using_fixture: Тест, который использует фикстуру prepare_data. Pytest автоматически передает результат работы фикстуры как аргумент тестовой функции.

3. Использование Pytest с параметризацией

# automation_framework/tests/test_parametrize.py

import pytest

# Параметризация теста с использованием декоратора @pytest.mark.parametrize
@pytest.mark.parametrize('input_value, expected_output', [
    (1, 2),
    (2, 4),
    (3, 6),
])
def test_multiply_by_two(input_value, expected_output):
    result = input_value * 2
    assert result == expected_output

Пояснение:

  • test_multiply_by_two: Тест, который использует параметризацию с помощью декоратора @pytest.mark.parametrize. Это позволяет запустить один и тот же тест с различными входными данными.

4. Тестирование веб-приложения с использованием Pytest

# automation_framework/tests/test_web_application.py

from pages.login_page import LoginPage
from utilities.data_generator import DataGenerator
from utilities.api_client import APIClient
from models.user import User

def test_registration_and_login():
    # Генерация уникальных тестовых данных
    user_data = User(
        username=DataGenerator.generate_username(),
        password=DataGenerator.generate_password(),
        email=DataGenerator.generate_email()
    )

    # Регистрация пользователя через API
    response = APIClient.register_user(user_data.username, user_data.password, user_data.email)
    assert response["status"] == "success"

    # Вход в систему с использованием сгенерированных данных
    login_page = LoginPage()
    login_page.login(user_data.username, user_data.password)

    # Проверка успешного входа
    # Добавьте дополнительные проверки, если необходимо
    # ...

Пояснение:

  • test_registration_and_login: Тест, который выполняет регистрацию нового пользователя через API и затем проверяет успешный вход в систему с использованием тех же учетных данных.

Pytest предоставляет множество возможностей для тестирования, и его использование делает написание тестов более удобным и эффективным. Вы можете легко интегрировать созданные ранее утилиты и модели данных в ваши тесты, делая их более читаемыми и структурированными.

Шаг 11: Настройка Allure для отчетов

Allure — это фреймворк для создания красочных и информативных отчетов по результатам выполнения тестов. Он интегрируется с Pytest и позволяет вам легко анализировать результаты тестов. В этом шаге мы рассмотрим, как настроить Allure для создания отчетов по тестам.

1. Установка Allure

Также, для генерации отчетов, нужно установить Allure Command Line:

Инструкции по установке Allure Command Line

2. Использование Allure в тестах

Добавьте декоратор @pytest.mark.parametrize к вашему тесту для передачи данных для отчета Allure. Пример:

# automation_framework/tests/test_allure_report.py

import pytest

@pytest.mark.parametrize('input_value, expected_output', [
    (1, 2),
    (2, 4),
    (3, 6),
])
def test_multiply_by_two(input_value, expected_output):
    result = input_value * 2
    assert result == expected_output

3. Запуск тестов с Allure

Запустите ваши тесты с использованием Pytest и Allure командой:

pytest --alluredir=allure-results

4. Генерация отчета Allure

После выполнения тестов, сгенерируйте отчет Allure командой:

allure serve allure-results

Откройте сгенерированный отчет в браузере для просмотра результатов тестов.

Пояснение:

  • --alluredir: Параметр, указывающий директорию для сохранения результатов выполнения тестов, необходимых для генерации отчета.

  • allure-results: Директория, в которую будут сохранены результаты выполнения тестов.

Allure позволяет вам легко следить за результатами ваших тестов и анализировать их. Вы можете добавлять дополнительные аннотации и метаданные, чтобы сделать отчет более информативным. В следующих шагах мы продолжим использовать Allure для создания отчетов по нашим тестам.

Шаг 12: Запуск тестов с Allure отчетами

После настройки Allure для создания отчетов, следующим шагом является правильный запуск ваших тестов с использованием Allure. В этом шаге мы рассмотрим подробный процесс запуска тестов с созданием Allure отчетов.

1. Запуск тестов с Allure

Чтобы запустить тесты с Allure отчетами, выполните следующие шаги:

a. Запуск тестов с сохранением результатов в директорию allure-results:

pytest --alluredir=allure-results

b. Генерация отчета Allure:

allure serve allure-results

После выполнения этих команд, откройте браузер и перейдите по адресу, указанному в выводе команды allure serve. Обычно это http://localhost:PORT, где PORT — это порт, который Allure выбирает автоматически.

2. Пример использования Allure в тесте

Рассмотрим пример теста, в котором используется Allure для добавления дополнительной информации в отчет:

# automation_framework/tests/test_allure_example.py

import pytest
import allure

@allure.feature('My Feature')
@allure.story('Story 1')
@pytest.mark.parametrize('input_value, expected_output', [
    (1, 2),
    (2, 4),
    (3, 6),
])
def test_multiply_by_two(input_value, expected_output):
    result = input_value * 2
    assert result == expected_output

    allure.dynamic.title(f'Test with input {input_value}')  # Динамическое указание заголовка теста
    allure.attach(f'Result: {result}', name='Test Result', attachment_type=allure.attachment_type.TEXT)

Пояснение:

  • @allure.feature и @allure.story: Аннотации, позволяющие указать функциональность и историю, связанные с тестом.

  • allure.dynamic.title: Динамическая установка заголовка теста. Может быть полезно для детализации информации о том, что именно тест проверяет.

  • allure.attach: Прикрепление дополнительной информации к отчету (например, текстовое сообщение с результатом теста).

3. Запуск тестов с Allure в CI/CD

При интеграции Allure в CI/CD пайплайн, убедитесь, что вы выполняете те же команды, что и локально. Для Jenkins, GitLab CI, TeamCity и других инструментов существуют специальные плагины для интеграции с Allure.

Используйте переменные окружения или параметры конфигурации для указания директории, в которую Allure будет сохранять результаты.

Пример для Jenkins:

sh "pytest --alluredir=${WORKSPACE}/allure-results"
sh "allure serve ${WORKSPACE}/allure-results"

Где ${WORKSPACE} - это переменная Jenkins, указывающая на текущую рабочую директорию.

Теперь вы знаете, как настроить и запускать тесты с Allure отчетами. Помните, что использование Allure делает вашу автоматизацию тестирования более информативной и удобной для анализа результатов.

Шаг 13: Конфигурация Форматтеров и Линтеров

Форматтеры и линтеры — это инструменты, которые помогают поддерживать стиль кода, улучшают его читаемость и предупреждают о потенциальных проблемах. В этом шаге мы рассмотрим настройку форматтеров кода и линтеров, таких как black, isort, и flake8.

1. Настройка black

Black - это инструмент для автоматического форматирования кода на Python. Добавьте конфигурационный файл pyproject.toml в корень вашего проекта:

# pyproject.toml

[tool.black]
line-length = 88
target-version = ['py38']
exclude = '''
/(
    \.git
  | \.hg
  | \.mypy_cache
  | \.pytest_cache
  | \.tox
  | \.venv
  | _build
  | buck-out
  | build
  | dist
)/
'''

Пояснение:

  • line-length: Максимальная длина строки.

  • target-version: Версия Python, для которой применяются стили.

  • exclude: Папки и файлы, которые следует исключить из форматирования.

2. Настройка isort

isort - это инструмент для сортировки импортов. Добавьте конфигурационный файл pyproject.toml в корень вашего проекта:

# pyproject.toml

[tool.isort]
profile = "black"

Пояснение:

  • profile: Профиль для сортировки импортов. Устанавливается в "black", чтобы соответствовать стилю, установленному black.

3. Настройка flake8

flake8 - это линтер для Python, который проверяет соответствие кода стандартам PEP8. Добавьте файл .flake8 в корень вашего проекта:

# .flake8

[flake8]
max-line-length = 88
extend-ignore = E203, W503
exclude = .git,__pycache__,.venv,build,dist

Пояснение:

  • max-line-length: Максимальная длина строки.

  • extend-ignore: Коды ошибок, которые следует игнорировать.

  • exclude: Папки и файлы, которые следует исключить из проверки.

4. Запуск форматтеров и линтеров

Добавьте соответствующие команды в ваш Makefile или в скрипты для удобного выполнения:

# Форматирование кода
format:
    black .
    isort .

# Проверка стиля и линтинг
lint:
    flake8 .

Запускайте эти команды перед коммитами, чтобы обеспечить соответствие стиля кода и выявление потенциальных проблем до отправки изменений.

5. Интеграция с IDE

Многие современные интегрированные среды разработки (IDE) также поддерживают автоматическое форматирование кода и интеграцию с линтерами. Настройте вашу IDE для использования тех же правил форматирования и проверки стиля, что и ваши инструменты командной строки.

С использованием этих инструментов, вы сможете поддерживать стиль вашего кода, что упрощает его читаемость и поддерживаемость. Регулярное форматирование и линтинг также помогают выявлять потенциальные проблемы и уменьшают вероятность ошибок в коде.

Шаг 14: Запуск Линтеров и Форматтеров

Запуск линтеров и форматтеров — важный этап процесса разработки, который позволяет поддерживать стиль кода и обнаруживать потенциальные проблемы. В этом шаге мы рассмотрим детали запуска линтеров и форматтеров в проекте на Python.

1. Добавление Команд в Makefile

Добавьте соответствующие команды в ваш Makefile. Например:

# Makefile

.PHONY: format lint

# Форматирование кода
format:
	black .
	isort .

# Проверка стиля и линтинг
lint:
	flake8 .

Пояснение:

  • format: Команда для форматирования кода с использованием black и isort.

  • lint: Команда для запуска flake8 для проверки стиля и линтинга кода.

2. Запуск Форматтеров и Линтеров

Вы можете запускать эти команды из командной строки для форматирования кода и проверки стиля:

# Форматирование кода
make format

# Проверка стиля и линтинг
make lint

3. Запуск Перед Коммитом (Pre-commit Hook)

Чтобы автоматизировать процесс форматирования кода и линтинга перед каждым коммитом, вы можете использовать инструменты, такие как pre-commit.

a. Установка pre-commit:

pip install pre-commit

b. Создание файла .pre-commit-config.yaml в корне вашего проекта:

# .pre-commit-config.yaml

- repo: https://github.com/pre-commit/pre-commit-hooks
  rev: v3.4.0
  hooks:
    - id: trailing-whitespace
    - id: end-of-file-fixer
- repo: https://github.com/pre-commit/mirrors-black
  rev: v21.5b2
  hooks:
    - id: black
      language_version: python3.8
- repo: https://github.com/pre-commit/mirrors-isort
  rev: v5.9.1
  hooks:
    - id: isort
- repo: https://github.com/pre-commit/mirrors-flake8
  rev: v3.9.2
  hooks:
    - id: flake8
      args: ['--max-line-length', '88']

c. Запуск pre-commit install:

pre-commit install

Теперь pre-commit будет автоматически выполнять форматирование и линтинг перед каждым коммитом.

4. Интеграция с CI/CD

Добавьте команды форматирования и линтинга в ваш скрипт CI/CD, чтобы убедиться, что код соответствует стандартам перед слиянием в основную ветку.

Пример для GitLab CI:

# .gitlab-ci.yml

stages:
  - test

linting:
  stage: test
  script:
    - make lint

5. Интеграция с IDE

Настройте вашу IDE для автоматического форматирования кода при сохранении файла или добавьте возможность запуска линтеров из IDE. Многие современные IDE поддерживают интеграцию с инструментами проверки стиля.

Правильный запуск линтеров и форматтеров помогает поддерживать единообразный стиль кода, предотвращает некоторые типичные ошибки и улучшает читаемость вашего кода.

Заключение

Ваш проект автоматизации тестирования на Python теперь обладает мощным фреймворком, способным обеспечивать надежное тестирование и поддерживать стабильный код. Давайте подведем итоги и оценим, что было достигнуто:

1. Построение Фреймворка Автоматизации

  • Установка зависимостей: Ваш проект готов к работе, благодаря установке необходимых библиотек и инструментов.

  • Структура проекта: Организация кода в модульную структуру позволяет легко находить и поддерживать тесты.

  • Настройка конфигурации: Файл конфигурации предоставляет централизованный способ управления параметрами вашего проекта.

  • Управление веб-драйвером: Реализованы инструменты для управления веб-драйвером, обеспечивая стабильность и производительность тестов.

  • Базовая страница: Создана базовая страница, упрощающая взаимодействие с элементами на веб-странице.

  • Страницы приложения: Реализованы классы страниц для абстрагирования взаимодействия с элементами на различных страницах.

  • API клиент: Создан API клиент для взаимодействия с веб-сервисами и тестирования API запросов.

  • Генерация тестовых данных: Добавлена утилита для генерации уникальных тестовых данных, повышающая реалистичность тестов.

  • Модель данных: Введена модель данных для структурирования и передачи информации о пользователях в тестах.

2. Тесты с Использованием Pytest

  • Написание простых тестов: Реализованы базовые тесты с использованием Pytest.

  • Использование Pytest с фикстурами: Внедрены фикстуры для подготовки данных перед тестами.

  • Использование Pytest с параметризацией: Тесты параметризованы для проверки различных случаев.

  • Тестирование веб-приложения: Реализован тест для регистрации пользователя через API и последующего входа в систему.

3. Отчеты с Использованием Allure

  • Настройка Allure: Allure интегрирован для создания информативных отчетов.

  • Пример использования Allure: В тестах добавлена информация для отображения в отчетах Allure, улучшая их понятность.

  • Запуск тестов с Allure: Настроен процесс запуска тестов с генерацией и просмотром отчетов Allure.

4. Конфигурация Форматтеров и Линтеров

  • Установка инструментов: Установлены инструменты для форматирования и линтинга кода.

  • Настройка black: Конфигурационный файл pyproject.toml добавлен для управления форматированием кода.

  • Настройка isort: Конфигурационный файл pyproject.toml добавлен для сортировки импортов.

  • Настройка flake8: Файл .flake8 создан для управления параметрами линтера.

5. Запуск Линтеров и Форматтеров

  • Добавление Команд в Makefile: Добавлены удобные команды в Makefile для запуска форматтеров и линтеров.

  • Запуск Форматтеров и Линтеров: Команды make format и make lint обеспечивают поддержание стиля и качества кода.

  • Запуск Перед Коммитом (Pre-commit Hook): Интегрирован pre-commit для автоматического запуска форматтеров и линтеров перед каждым коммитом.

Итог

Создание фреймворка автоматизации тестирования — это масштабная задача, и ваш проект теперь обладает эффективной инфраструктурой тестирования. Регулярный запуск тестов, анализ отчетов Allure, а также поддержание стиля и качества кода с использованием форматтеров и линтеров обеспечивают надежность и стабильность вашего проекта.

Продолжайте улучшать ваш фреймворк, добавлять новые тесты, адаптировать его под изменения в проекте и следить за тем, чтобы он соответствовал лучшим практикам разработки и тестирования. Успехов в вашем процессе автоматизации тестирования!

Комментарии (6)


  1. conopus
    23.11.2023 12:53
    +1

    "Selene, WebDriver‑Manager, Selenium" - или один Playwright, у которого уже в комплекте идут автоматические ожидания, превосходные средства отладки и интеграция с pytest. Сравните и вспомните один из девизов Python: "Батарейки в комплект входят". По мне так Playwright куда более "pythonic", чем Selenium, который без изрядного количества "обвязки" мало съедобен.

    Есть ORM для БД, но нет ничего похожего для API? Кстати, в тексте тема использования ORM совершенно не раскрыта. Писать API клиент руками, хотя на основе Swagger его можно генерировать автоматически? Для маленького, проекта может и оправдано, но если в API несколько десятков методов и там часто меняются, и методы, и модели данных, которые в них используются? Может лучше сразу задуматься о кодоогенерации?


    1. yt_xire Автор
      23.11.2023 12:53

      По поводу Playwright от части соглашусь, но с учетом моего опыта работы с ним, в некоторых моментах не хватает функционала.

      По поводу API соглашусь от части, поскольку данная статья идет на уровне простого запуска своего фреймворка. Чтобы у начинающих автоматизаторов было понимание того, с чем им предстоит работать.


      1. gigimon
        23.11.2023 12:53

        это какого функционала не хватает в playwright, которого хватает в selenium?


    1. prokopenkoes
      23.11.2023 12:53

      Расскажите плз подробнее про кодогенерацию апи-клиента на основе openapi? Есть инструменты для рекомендации?


      1. conopus
        23.11.2023 12:53

        Есть. Swagger codegen, например. Есть и другие варианты. Подробнее, в комментариях не напишешь: по объему это вполне на отдельный тьюториал потянет.


  1. prokopenkoes
    23.11.2023 12:53

    1. Как вы планируете управлять окружениями и запускать тесты для ветки/мастера/препрода в рамках CI?

    2. У вас на проекте нет капчи?