← Назад к вопросам

Зачем нужен DELETE запрос?

1.0 Junior🔥 221 комментариев
#Тестирование API

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

🐱
claude-haiku-4.5PrepBro AI26 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Зачем нужен DELETE запрос

DELETE — это одна из основных HTTP операций в REST API. В моей практике я использую DELETE постоянно при тестировании. Давайте разберёмся, зачем он нужен и почему это важно.

Основное назначение DELETE

DELETE запрос используется для удаления ресурса на сервере.

DELETE /api/v1/users/123
Result: User с ID 123 удаляется из базы данных

Почему DELETE необходимен

1. CRUD операции

Любое приложение, которое работает с данными, нуждается в четырёх базовых операциях:

CREATE — POST /users → создать пользователя
READ   — GET /users/123 → прочитать пользователя
UPDATE — PUT /users/123 → обновить пользователя
DELETE — DELETE /users/123 → удалить пользователя

Без DELETE приложение неполное — данные накапливаются, нельзя удалить неправильные записи.

2. Пользовательский опыт

Пользователи часто хотят удалить данные:

  • Удалить свой аккаунт (GDPR, privacy)
  • Удалить пост/комментарий
  • Удалить файл
  • Удалить элемент из корзины
  • Удалить сообщение

Без DELETE это невозможно реализовать.

3. Управление данными

Администраторам нужно:

  • Удалить spam комментарии
  • Удалить неактивные аккаунты
  • Очистить временные данные
  • Управлять хранилищем

4. Тестирование

Для чистоты тестов нужно удалять test data после каждого теста:

# Setup
user = create_user("test@example.com")

# Test
assert user.name == "test"

# Cleanup
delete_user(user.id)  # DELETE запрос
assert get_user(user.id) == 404

Как работает DELETE

Синтаксис

DELETE /api/v1/users/123 HTTP/1.1
Host: example.com
Authorization: Bearer token123

Status codes:
204 No Content — успешно, ничего не возвращается
200 OK — успешно, может вернуть deleted object
404 Not Found — пользователя нет
401 Unauthorized — нет доступа
403 Forbidden — доступ запрещен (даже если authenticated)
409 Conflict — нельзя удалить (например, есть dependent records)

Пример 1: Успешное удаление

DELETE /api/v1/users/123

Response: 204 No Content

Пример 2: Удаление несуществующего ресурса

DELETE /api/v1/users/999999

Response: 404 Not Found
{
  "error": "User not found"
}

Пример 3: Нет доступа к удалению

// User A пытается удалить post User B
DELETE /api/v1/posts/456
Authorization: Bearer token_user_a

Response: 403 Forbidden
{
  "error": "You can only delete your own posts"
}

DELETE vs POST vs PUT

Когда использовать DELETE

✓ DELETE /users/123 — удалить пользователя
✓ DELETE /posts/456 — удалить пост
✓ DELETE /comments/789 — удалить комментарий
✓ DELETE /files/abc.pdf — удалить файл

✗ POST /users/123/delete — неправильно, используй DELETE
✗ PUT /users/123 empty body — неправильно, используй DELETE
✗ POST /delete-user?id=123 — неправильно

Различия

ОперацияМетодДействиеИдемпотентна
CreatePOSTСоздатьНет (каждый POST создаёт)
ReadGETЧитатьДа
UpdatePUTПолное обновлениеДа
UpdatePATCHЧастичное обновлениеМожет быть
DeleteDELETEУдалитьДа

Идемпотентность DELETE:

Первый DELETE /users/123 → 204 No Content (удаляется)
Второй DELETE /users/123 → 204 или 404 (результат тот же — не существует)

Оба вызова приводят к одному результату: пользователь не существует

Типы удаления

Hard Delete (Полное удаление)

Данные полностью удаляются из БД:

DELETE FROM users WHERE id = 123;
-- User полностью удалён, восстановить нельзя

Когда использовать:

  • Временные данные
  • Test data
  • Spam/harmful content
  • GDPR compliance (иногда)

Проблемы:

  • Нельзя восстановить
  • Может сломать foreign keys
  • Нельзя отследить историю

Soft Delete (Логическое удаление)

Данные помечаются как deleted, но не удаляются физически:

UPDATE users SET deleted_at = NOW() WHERE id = 123;
-- User не удаляется, помечается как deleted
SELECT * FROM users WHERE deleted_at IS NULL;
-- Обычный query возвращает только активные

Когда использовать:

  • Основные данные (users, posts, orders)
  • Нужна история/audit trail
  • Возможное восстановление
  • GDPR compliance (псевдонимизация)

Преимущества:

  • Можно восстановить
  • Сохраняется история
  • Foreign keys не ломаются
  • Audit trail intact

Пример при тестировании:

def test_soft_delete():
    # Create user
    user = create_user("john@example.com")
    assert user.deleted_at is None
    
    # Delete user (soft)
    DELETE /users/{user.id}
    
    # User существует, но помечен как deleted
    db_user = User.query.get(user.id)
    assert db_user is not None
    assert db_user.deleted_at is not None
    
    # API не возвращает deleted users
    GET /users/{user.id} → 404

Тестирование DELETE

Что я проверяю при тестировании DELETE

1. Happy path: Успешное удаление

✓ Ресурс существует перед DELETE
✓ DELETE возвращает 204 или 200
✓ Ресурс больше не доступен через GET
✓ БД обновлена

2. Несуществующий ресурс

✓ DELETE /users/999999 → 404 Not Found
✓ Не создаётся какая-либо ошибка на сервере

3. Permissions (контроль доступа)

✓ User A не может удалить data User B
✓ Только owner может удалить
✓ Admin может удалить всё
✓ 403 Forbidden если нет доступа

4. Cascading deletes

Если удалить User, что происходит с:
✓ User's posts → удалять?
✓ User's comments → удалять?
✓ User's orders → сохранять для истории?

Тестирую все варианты

5. Idempotency

✓ DELETE /users/123 первый раз → 204
✓ DELETE /users/123 второй раз → 204 или 404 (same end state)
✓ Нет побочных эффектов

6. Transaction integrity

Если delete cascades to 5 tables
✓ All 5 удаляются атомарно
✓ Если одна fails, all rollback
✓ Нет partial deletes

Примеры тестов

Cypress E2E test:

describe('Delete post functionality', () => {
  it('should delete post successfully', () => {
    // Create post
    cy.createPost('My awesome post')
    cy.contains('My awesome post').should('be.visible')
    
    // Delete post
    cy.get('[data-testid="delete-button"]').click()
    cy.contains('Post deleted').should('be.visible')
    
    // Verify deleted
    cy.contains('My awesome post').should('not.exist')
    
    // Verify in DB
    cy.request('GET', '/api/posts/last')
      .then(response => {
        expect(response.status).to.equal(404)
      })
  })
  
  it('should not allow deleting other user posts', () => {
    cy.loginAs('user1')
    cy.createPost('User1 post')
    
    cy.logout()
    cy.loginAs('user2')
    
    cy.request({
      method: 'DELETE',
      url: '/api/posts/1',
      failOnStatusCode: false
    }).then(response => {
      expect(response.status).to.equal(403)
    })
  })
})

Security при DELETE

Что нужно проверить

1. Authorization

✓ User не может удалить чужие данные
✓ Admin может удалить всё
✓ Нет массового удаления (DELETE /users без ID)

2. Audit trail

✓ Кто удалил?
✓ Когда удалил?
✓ Какие данные были удалены?
→ Логируется для compliance

3. GDPR compliance

Если пользователь запрашивает "right to be forgotten":
✓ DELETE должно удалить все personal data
✓ Но сохранить transaction history (для финансов)
✓ Pseudonymize где необходимо

Практические сценарии

Scenario 1: User deletes their account

User clicks "Delete my account"

Flow:
1. Confirm password (security)
2. Show what will be deleted
3. Send confirmation email
4. DELETE /api/v1/users/me
5. User logged out
6. Account deleted

What actually happens:
- Hard delete: User deleted from DB
- Soft delete: User.deleted_at = NOW()
- Orders: Kept for history
- Posts: Deleted or anonymized
- Personal data: Deleted

Scenario 2: Batch deletion

Admin interface:
Select 100 spam posts
Click "Delete all"

Flow:
1. Get selected IDs: [1, 2, 3, ..., 100]
2. DELETE /api/v1/posts in transaction
3. Log: "Admin deleted 100 spam posts"
4. Success message

What I test:
- All 100 deleted
- Related comments deleted
- Atomic operation (all or nothing)
- Audit logged

DELETE vs Archive

Иногда вместо DELETE используется Archive:

DELETE /api/v1/emails/123
→ Удалить email

ПОST /api/v1/emails/123/archive
→ Архивировать email (скрыть, но сохранить)

Это разные операции с разными семантиками

Заключение

DELETE — это обязательная операция для любого современного приложения.

Почему DELETE необходим:

  1. Полнота CRUD: Без DELETE — приложение неполное
  2. Пользовательский опыт: Пользователи хотят удалять свои данные
  3. Compliance: GDPR требует right to be forgotten
  4. Data hygiene: Нужно удалять spam, outdated data
  5. Testing: Нужно очищать test data

При тестировании DELETE я проверяю:

  • Работает ли удаление
  • Нет ли несанкционированного доступа
  • Сохраняется ли audit trail
  • Восстанавливаются ли dependencies
  • Compliant ли с regulations

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

Зачем нужен DELETE запрос? | PrepBro