Рассмотрим пример с редактированием и удалением объектов модели на примере модели Person:
from django.db import models class Person(models.Model): name = models.CharField(max_length=20) age = models.IntegerField()
Для обновления объекта также применяется метод save():
bob = Person.objects.get(id=2) bob.name = "Bob" bob.save()
В этом случае Django полностью обновляет объект, все его свойства, даже если мы их не изменяли. Чтобы указать, что нам надо обновить только
определенные поля, следует использовать параметр update_fields
:
from .models import Person bob = Person.objects.get(id=1) bob.name = "Robert" bob.save(update_fields=["name"])
Это позволит повысить производительность.
Другой способ обновления объектов представляет метод update() (и его асинхронная версия aupdate()) в сочетании с методом filter, которые вместе выполняют один запрос к базе данных:
from .models import Person number = Person.objects.filter(id=1).update(name="Mike") print(number) # количество обновленных строк
В данном случае у объектов с id = 1 устанавливаем для поля name значение "Mike". Метод возвращает количество обновленных строк.
Если нам не надо получать обновляемый объект, то данный способ позволит нам увеличить производительность взаимодействия с бд.
Также можно установить и большое количество полей:
Person.objects.filter(id=1).update(name="Mike", age = 33)
Иногда бывает необходимо изменить значение столбца в бд на основании уже имеющегося значения. В этом случае мы можем использовать функцию F():
from .models import Person from django.db.models import F Person.objects.all(id=2).update(age = F("age") + 1)
В данном случае полю age присваивается уже имеющееся значение, увеличенное на единицу.
При этом важно учитывать, что метод update обновляет все записи в таблице, которые соответствуют условию.
Если надо обновить вообще все записи, вне зависимости от условия, то необходимо комбинировать метод update с методом all()
:
from .models import Person from django.db.models import F Person.objects.all().update(name="Mike") Person.objects.all().update(age = F("age") + 1)
Метод update_or_create (и его асинхронная версия aupdate_or_create()) обновляет запись, а если ее нет, то добавляет ее в таблицу:
values_for_update={"name":"Bob", "age": 31} bob, created = Person.objects.update_or_create(id=2, defaults = values_for_update)
Метод update_or_create()
принимает два параметра. Первый параметр представляет критерий выборки объектов, которые будут обновляться.
Второй параметр представляет объект со значениями, которые получат выбранные объекты.
Если критерию не соответствует никаких объектов, то в таблицу добавляется новый объект, а переменная created будет равна True.
Метод bulk_update() (и его асинхронная версия abulk_update()) позволяет обновить за один раз набор объектов.
bulk_update(objs, fields, batch_size=None)
Первый параметр - obj
указывает на обновляемые объекты, а второй параметр - fields
представляет обновляемые поля с новыми значениями.
Последний параметр - batch_size
указывает, сколько объектов обновляется в одном запросе (по умолчанию обновляются все объекты)
from .models import Person first_person = Person.objects.get(id=1) first_person.name = "Tomas" second_person = Person.objects.get(id=2) second_person.age = 29 number = Person.objects.bulk_update([first_person, second_person], ["name", "age"]) print(number) # 2
В данном случае у первого объекта обновляется значение поля "name", а у второго - значение поля "age". Поэтому в качестве второго параметра передается список с данными полями. Результатом метода является количество обновленных объектов.
Данный метод имеет некоторые ограничения. В частности, мы не можем обновить значение первичного ключа. Также если в обновляемом наборе есть дубли, то только первое вхождение объекта будет использоваться для обновления.
Для удаления мы можем вызвать метод delete() (либо его асинхронную версию adelete()) у удаляемого объекта:
person = Person.objects.get(id=2) person.delete()
Если не требуется получение отдельного объекта из базы данных, тогда можно удалить объект с помощью комбинации методов filter()
и delete()
:
Person.objects.filter(id=4).delete()
Удаление всех данных из таблицы:
Person.objects.all().delete()