Удаление в MongoDB
Как удалять документы из MongoDB в Python с помощью delete_one() и delete_many() PyMongo: фильтры, обработка ошибок и безопасные шаблоны.
PyMongo предоставляет два метода для удаления документов из коллекции: delete_one() удаляет первый подходящий документ, а delete_many() удаляет все совпадающие документы. Оба метода работают с фильтрами — вы точно указываете, какие документы нужно удалить, используя тот же синтаксис запросов, что и в find().
В этой главе рассматривается:
delete_one()— удаление одного документаdelete_many()— удаление нескольких документов (в том числе всех)- Чтение объекта
DeleteResult - Операторы фильтров для точного удаления
- Обработка ошибок и безопасные практики
- Когда удалять документы, а когда удалять всю коллекцию
Предварительные требования: Python 3.8+, установленный PyMongo (
pip install pymongo) и работающий сервер MongoDB. Инструкции по настройке см. в разделе MongoDB Get Started, а о том, как документы попадают в коллекцию, — в разделе MongoDB Insert.
Подключение и выбор коллекции
Для любой операции удаления необходимы MongoClient, база данных и коллекция:
import pymongo
client = pymongo.MongoClient("mongodb://localhost:27017/")
db = client["mydatabase"]
col = db["customers"]Во всех примерах ниже предполагается, что col определён именно так.
Удаление одного документа с помощью delete_one()
delete_one(filter) находит первый документ, соответствующий фильтру, и удаляет его. Если фильтру соответствует несколько документов, удаляется только один (MongoDB определяет его по естественному порядку).
result = col.delete_one({"name": "Alice"})
print(result.deleted_count) # 1 if a match was found, 0 if notdelete_one() не вызывает ошибку, если подходящий документ не найден — метод возвращает DeleteResult со значением deleted_count = 0.
Поиск по конкретному значению поля
# Delete the customer whose name is "Bob"
result = col.delete_one({"name": "Bob"})
if result.deleted_count == 1:
print("Document deleted.")
else:
print("No matching document found.")Поиск по вложенному полю
Для обращения к полям во вложенных документах используйте точечную нотацию:
# Delete the first customer whose city is "London"
result = col.delete_one({"address.city": "London"})
print(result.deleted_count) # 1 or 0Удаление нескольких документов с помощью delete_many()
delete_many(filter) удаляет все документы, соответствующие фильтру. Используйте его, когда нужно очистить набор записей за один вызов.
# Delete all customers whose address starts with "S"
result = col.delete_many({"address": {"$regex": "^S"}})
print(result.deleted_count, "documents deleted")Удаление всех документов в коллекции
Передайте пустой фильтр {}, чтобы удалить все документы. Сама коллекция и её индексы при этом сохраняются — исчезают только документы:
result = col.delete_many({})
print(result.deleted_count, "documents deleted")Предупреждение:
delete_many({})на рабочей коллекции необратимо. Всегда тщательно проверяйте фильтр и делайте резервную копию перед массовым удалением. Если нужно удалить коллекцию целиком (документы и индексы), используйтеcol.drop()— подробнее в разделе MongoDB Drop Collection.
Объект DeleteResult
Оба метода возвращают объект DeleteResult. Чаще всего вам потребуются два его свойства:
| Свойство | Тип | Описание |
|---|---|---|
deleted_count | int | Количество фактически удалённых документов |
acknowledged | bool | True, если сервер подтвердил запись; False для неподтверждённых записей |
result = col.delete_many({"status": "inactive"})
print(f"Deleted: {result.deleted_count}")
print(f"Acknowledged: {result.acknowledged}")Операторы фильтров для точного удаления
Те же операторы запросов, что используются в find(), работают и в фильтрах удаления.
Удаление по условию сравнения
# Delete all orders with a quantity less than 10
col.delete_many({"qty": {"$lt": 10}})
# Delete all orders with a quantity greater than or equal to 100
col.delete_many({"qty": {"$gte": 100}})Удаление по регулярному выражению
# Delete all customers whose name starts with "A" (case-sensitive)
col.delete_many({"name": {"$regex": "^A"}})Удаление по наличию поля
# Delete all documents that have no "email" field
col.delete_many({"email": {"$exists": False}})Удаление по значению из списка
# Delete all documents whose status is either "cancelled" or "expired"
col.delete_many({"status": {"$in": ["cancelled", "expired"]}})Обработка ошибок
Оборачивайте операции удаления в блок try/except, чтобы обрабатывать два наиболее распространённых типа ошибок:
pymongo.errors.OperationFailure— сервер отклонил операцию (например, у подключённого пользователя нет правremoveна коллекцию).pymongo.errors.ConnectionFailure— соединение с MongoDB было разорвано.
import pymongo
client = pymongo.MongoClient("mongodb://localhost:27017/")
col = client["mydatabase"]["customers"]
try:
result = col.delete_many({"status": "inactive"})
print(f"{result.deleted_count} documents deleted.")
except pymongo.errors.OperationFailure as e:
print(f"Server error: {e}")
except pymongo.errors.ConnectionFailure as e:
print(f"Connection error: {e}")Практический пример: полный рабочий процесс
Этот пример наполняет коллекцию данными, выполняет точечные удаления и проверяет результат:
import pymongo
client = pymongo.MongoClient("mongodb://localhost:27017/")
col = client["mydatabase"]["customers"]
# 1. Start clean
col.drop()
# 2. Insert sample documents
col.insert_many([
{"name": "Alice", "city": "Oslo", "active": True},
{"name": "Bob", "city": "Sydney", "active": False},
{"name": "Carol", "city": "Seattle","active": False},
{"name": "Dave", "city": "Sofia", "active": True},
])
print("Inserted:", col.count_documents({})) # 4
# 3. Delete the one inactive customer named "Bob"
r1 = col.delete_one({"name": "Bob", "active": False})
print("delete_one:", r1.deleted_count) # 1
# 4. Delete all customers in cities that start with "S"
r2 = col.delete_many({"city": {"$regex": "^S"}})
print("delete_many (city ^S):", r2.deleted_count) # 2 (Carol/Seattle, Dave/Sofia)
# 5. Check what remains
remaining = list(col.find({}, {"_id": 0}))
print("Remaining:", remaining) # [{'name': 'Alice', 'city': 'Oslo', 'active': True}]Ожидаемый вывод:
Inserted: 4
delete_one: 1
delete_many (city ^S): 2
Remaining: [{'name': 'Alice', 'city': 'Oslo', 'active': True}]Удаление документов и удаление коллекции
Эти две операции часто путают:
| Операция | Документы удалены | Коллекция удалена | Индексы удалены | Скорость |
|---|---|---|---|---|
col.delete_many({}) | Все | Нет | Нет | Медленнее на больших наборах |
col.drop() | Все | Да | Да | Очень быстро |
Выбирайте delete_many({}), когда нужно очистить коллекцию, но сохранить индексы и валидаторы схемы. Выбирайте col.drop(), когда нужен полностью чистый результат — например, между тестовыми запусками или при миграции схемы. Подробнее о drop() — в разделе MongoDB Drop Collection.
Резюме
delete_one(filter)удаляет первый совпадающий документ;delete_many(filter)удаляет все совпадающие документы.- Оба метода возвращают
DeleteResult— проверяйтеdeleted_count, чтобы убедиться в результате. - Пустой фильтр
{}вdelete_many()удаляет все документы из коллекции. - Используйте операторы запросов MongoDB (
$regex,$lt,$in,$exists, …) для построения точных фильтров. - Оборачивайте операции в
try/exceptдля обработкиOperationFailureиConnectionFailure. - Чтобы удалить саму коллекцию, используйте
col.drop().
Связанные главы:
- MongoDB Insert — вставка документов с помощью
insert_one()иinsert_many() - MongoDB Update — изменение существующих документов с помощью
update_one()иupdate_many() - MongoDB Drop Collection — удаление коллекции целиком вместе с индексами
- MongoDB Query — построение фильтров с операторами запросов
- MongoDB Get Started — установка PyMongo и подключение к MongoDB