🐛 Типичные ошибки

← К оглавлению урока

⚡ Топ-5 ошибок курса

  1. Используют @allure.step без {param} — параметры не видны в отчёте
  2. Генерируют отчёт без --clean — старые результаты смешиваются с новыми
  3. resp.text вместо resp.json() — нельзя обратиться к полям как к словарю
  4. Не закрывают драйвер (driver.quit()) — процессы браузера остаются в памяти
  5. Хардкодят URL в каждом тесте вместо BASE_URL или класса-обёртки

Ошибка 1: @allure.step без параметров (из лекции)

Из лекции: без параметров в названии шага непонятно, с какими данными работал метод.

Неправильно:
# company_table.py
@allure.step("БД. Удалить организацию")
def delete(self, id):
    ...
# В отчёте: "БД. Удалить организацию" — непонятно, какой id удалили
Правильно:
# company_table.py
@allure.step("БД. Удалить организацию по {id}")
def delete(self, id):
    ...
# В отчёте: "БД. Удалить организацию по 42" — сразу видно

Ошибка 2: генерация отчёта без --clean (из лекции)

Неправильно:
# Старые результаты остаются и смешиваются с новыми
allure generate allure-results -o allure-report
# Статистика неверная — учитываются прошлые прогоны
Правильно:
# --clean очищает директорию перед генерацией
allure generate allure-results -o allure-report --clean

Ошибка 3: resp.text вместо resp.json()

Неправильно:
# test_api.py
resp = requests.get(url + "/company")
data = resp.text          # data — это строка!
print(data[0]["name"])    # TypeError: string indices must be integers
Правильно:
# test_api.py
resp = requests.get(url + "/company")
data = resp.json()        # data — это list
print(data[0]["name"])    # Работает корректно

Ошибка 4: @allure.id путают с ID в отчёте

Из лекции: @allure.id не отображается в Allure-интерфейсе. Это частая причина путаницы.

Заблуждение:
# Ожидают увидеть "ITCH-1" в интерфейсе Allure — его там нет
@allure.id("ITCH-1")
def test_get_companies(self):
    ...
Реальность (из лекции): @allure.id используется только для удобства навигации в коде. В Allure-отчёте видны только @allure.title, @allure.feature, @allure.story и т.д.

Ошибка 5: не закрывать драйвер

Неправильно:
# test_selenium.py
def test_login():
    driver = webdriver.Chrome()
    driver.get("https://example.com")
    driver.find_element(By.ID, "username").send_keys("user")
    # driver.quit() забыли — браузер остаётся открытым
    assert "Welcome" in driver.title
Правильно — через фикстуру:
# conftest.py
import pytest
from selenium import webdriver

@pytest.fixture(scope="class")
def driver(request):
    d = webdriver.Chrome()
    request.cls.driver = d
    yield d
    d.quit()  # teardown — закрывается всегда, даже при ошибке

Ошибка 6: хардкод URL в каждом тесте

Неправильно:
# test_companies.py — URL размазан по всем тестам
def test_get_companies():
    resp = requests.get("https://x-clients-be.onrender.com/company")
    ...

def test_create_company():
    resp = requests.post("https://x-clients-be.onrender.com/company", json={...})
    ...
# При смене URL — менять везде
Правильно — одна константа или класс:
# test_companies.py
BASE_URL = "https://x-clients-be.onrender.com"
api = CompanyApi(BASE_URL)  # или просто используем константу

def test_get_companies():
    resp = requests.get(BASE_URL + "/company")
    ...

Ошибка 7: смешивание allure.step-декоратора и контекстного менеджера

Неправильно:
# Дублирование: метод уже размечен @allure.step,
# но тест снова оборачивает его в with allure.step()
class CompanyApi:
    @allure.step("api. Получить список компаний")
    def get_company_list(self):
        ...

def test_get_companies():
    with allure.step("Получить список через API"):  # лишний шаг!
        result = api.get_company_list()             # создаст вложенный дубль
Правильно (из лекции): Если метод уже размечен @allure.step, в тестах отдельный with allure.step() не нужен.
def test_get_companies():
    result = api.get_company_list()  # автоматически шаг в отчёте
    db_result = db.get_companies()
    assert len(result) == len(db_result)

Ошибка 8: не проверять status_code перед json()

Неправильно:
# test_api.py
resp = requests.get(url + "/company/99999")
data = resp.json()         # Если 404, json() может бросить исключение
assert data["name"] == "X" # Или вернуть {"detail": "Not found"}
Правильно:
# test_api.py
resp = requests.get(url + "/company/99999")
assert resp.status_code == 200, f"Ожидался 200, получен {resp.status_code}"
data = resp.json()
assert data["name"] == "X"