Ответ
Опыт включает тестирование REST API как вручную, так и с помощью автоматизации. Основной стек: Postman (для ручных проверок и коллекций), Python с библиотеками Requests и Pytest (для автотестов).
Типичные проверки в интеграционных тестах API:
- Корректность HTTP-статусов:
200 OK,201 Created,400 Bad Request,401 Unauthorized,404 Not Found,500 Internal Server Error. - Валидация структуры и данных ответа:
- Соответствие JSON-схеме (используется библиотека
jsonschema). - Проверка типов данных, обязательных полей, форматов значений (например,
date-time).
- Соответствие JSON-схеме (используется библиотека
- Проверка бизнес-логики: Корректность вычислений, состояние данных после выполнения запроса.
- Проверка заголовков (headers):
Content-Type,Authorization(JWT, OAuth2). - Обработка граничных случаев и ошибок: Передача невалидных данных, проверка валидационных сообщений.
Пример автотеста для цепочки запросов (создание -> чтение -> удаление ресурса):
import requests
import pytest
BASE_URL = "https://api.example.com/v1"
@pytest.fixture
def auth_headers():
# Получение токена для авторизации
auth_resp = requests.post(f"{BASE_URL}/auth", json={"login": "user", "pass": "pass"})
token = auth_resp.json()["access_token"]
return {"Authorization": f"Bearer {token}"}
def test_user_crud_lifecycle(auth_headers):
# 1. CREATE (POST)
new_user = {"name": "John Doe", "email": "john@example.com"}
create_resp = requests.post(f"{BASE_URL}/users", json=new_user, headers=auth_headers)
assert create_resp.status_code == 201
user_id = create_resp.json()["id"]
# 2. READ (GET) - проверяем, что пользователь создан
get_resp = requests.get(f"{BASE_URL}/users/{user_id}", headers=auth_headers)
assert get_resp.status_code == 200
assert get_resp.json()["name"] == new_user["name"]
# 3. DELETE (DELETE) - очистка тестовых данных
delete_resp = requests.delete(f"{BASE_URL}/users/{user_id}", headers=auth_headers)
assert delete_resp.status_code == 204
# 4. Проверяем, что пользователь удален
get_resp_after = requests.get(f"{BASE_URL}/users/{user_id}", headers=auth_headers)
assert get_resp_after.status_code == 404 Ответ 18+ 🔞
А, вот это я понимаю — тестирование API! Ты знаешь, это как пытаться объяснить глухонемому Герасиму, что его Муму не срет на крыше, блядь. Только вместо собаки у тебя — эти ебучие эндпоинты, которые то работают, то отдают 500-й статус просто потому что луна в Водолее, ёпта.
Так вот, смотри. Опыт у меня — овердохуища. И руками в Postman'е полапать могу, когда надо быстро проверить, не сломал ли чего фронтенд-разработчик, пока кофе пил. И на автомате, когда уже всё приелось и хочется, чтобы скрипты сами всё проверили, пока ты смотришь видосики про котиков.
Основной мой инструментарий — это Postman, конечно. Для коллекций, для ручных прогонов, когда надо понять, где именно система начинает истерить. А для серьёзных, долгих проверок — Python, библиотеки Requests да Pytest. Красота, блядь!
И что я там обычно проверяю, спросишь? Да всё, на что хватит терпения, а терпения, я тебе скажу, ноль ебать после пятого бага в одном и том же методе.
- Статусы HTTP, мать их. Это святое. Должен 200 — получи 200. Должен 404 — на, получи свою «не найдено», сука. 401, когда токен протух — это вообще отдельная песня. А 500-й... Ну, 500-й — это когда разработчики совсем уже, в рот меня чих-пых, накосячили.
- А ответ-то что внутри? JSON? А он правильный? Все поля на месте?
id— integer, а не строка?created_at— дата, а не число? Вот для этогоjsonschema— лучший друг. Засунул схему — и пусть библиотека сама орёт, если что не так. - Логика бизнес-. Ну вот создал ты заказ. А сумма-то правильно посчиталась? Скидка применилась? Вот это всё. Чтобы не вышло как в том анекдоте: «заказали один, а пришло сто, потому что в цикле ошибка».
- Заголовки, блядь (headers). Особенно
Authorization. Тыкаешься с этим Bearer токеном, с OAuth2... Иногда кажется, что проще самому стать сервером и всем ответы писать, чем разобраться в ихней системе прав. - И самое весёлое — обработка ошибок. Вот смотри: ты передаёшь в поле
emailстроку «абвгд». Ну и? Сервер должен тебе вежливо сказать: «Чувак, это не имейл». А не падать с 500-й ошибкой и молча умирать в логах. Проверяем, что валидационные сообщения адекватные, а не «Internal server error», ёбта.
А вот тебе пример, как это выглядит в коде. Цепочка: создали юзера, проверили, что создался, потом удалили и убедились, что его нет. Чисто, аккуратно.
import requests
import pytest
BASE_URL = "https://api.example.com/v1"
@pytest.fixture
def auth_headers():
# Тут мы получаем токен, чтобы нас не послали нахуй с первого же запроса
auth_resp = requests.post(f"{BASE_URL}/auth", json={"login": "user", "pass": "pass"})
token = auth_resp.json()["access_token"]
return {"Authorization": f"Bearer {token}"}
def test_user_crud_lifecycle(auth_headers):
# 1. СОЗДАЁМ (POST) — типа, давайте нового человека в систему
new_user = {"name": "John Doe", "email": "john@example.com"}
create_resp = requests.post(f"{BASE_URL}/users", json=new_user, headers=auth_headers)
assert create_resp.status_code == 201 # Должен сказать «Создано!»
user_id = create_resp.json()["id"] # Вытаскиваем ID, он нам ещё пригодится
# 2. ЧИТАЕМ (GET) — а правда создался? Проверим-ка
get_resp = requests.get(f"{BASE_URL}/users/{user_id}", headers=auth_headers)
assert get_resp.status_code == 200 # Всё ок, пользователь есть
assert get_resp.json()["name"] == new_user["name"] # И имя совпадает, красота
# 3. УДАЛЯЕМ (DELETE) — чтобы не засорять базу тестовым хламом
delete_resp = requests.delete(f"{BASE_URL}/users/{user_id}", headers=auth_headers)
assert delete_resp.status_code == 204 # «Нет содержимого», всё удалено
# 4. ФИНАЛЬНАЯ ПРОВЕРКА (GET) — а теперь его точно нет?
get_resp_after = requests.get(f"{BASE_URL}/users/{user_id}", headers=auth_headers)
assert get_resp_after.status_code == 404 # Вот теперь «Не найдено». Идеально.
Вот так-то, друг. Кажется, просто, да? А попробуй это на продакшене, где ползапроса в секунду, и смотри, как твои тесты падают из-за таймаутов. Но это уже совсем другая история, блядь.