it-swarm.com.de

Erstelle Django Modell oder aktualisiere, falls vorhanden

Ich möchte ein Modellobjekt wie Person erstellen, wenn die ID der Person nicht vorhanden ist, oder ich erhalte dieses Personenobjekt.

Der Code zum Erstellen einer neuen Person lautet wie folgt:

class Person(models.Model):
    identifier = models.CharField(max_length = 10)
    name = models.CharField(max_length = 20)
    objects = PersonManager()

class PersonManager(models.Manager):
    def create_person(self, identifier):
        person = self.create(identifier = identifier)
        return person

Aber ich weiß nicht, wo ich das vorhandene Personenobjekt überprüfen und abrufen soll.

93
user1687717

Wenn Sie nach dem Anwendungsfall "Update, falls vorhanden, erstellen" suchen, lesen Sie bitte @ Zags ausgezeichnete Antwort


Django hat bereits ein get_or_create, https://docs.djangoproject.com/en/dev/ref/models/querysets/#get-or-create

Für Sie könnte es sein:

id = 'some identifier'
person, created = Person.objects.get_or_create(identifier=id)

if created:
   # means you have created a new person
else:
   # person just refers to the existing one
145
bakkal

Es ist unklar, ob Ihre Frage nach der get_or_create -Methode (verfügbar ab Django 1.3) oder der pdate_or_create -Methode (neu in =) fragt Django 1.7). Dies hängt davon ab, wie Sie das Benutzerobjekt aktualisieren möchten.

Beispielgebrauch ist wie folgt:

# In both cases, the call will get a person object with matching
# identifier or create one if none exists; if a person is created,
# it will be created with name equal to the value in `name`.

# In this case, if the Person already exists, its existing name is preserved
person, created = Person.objects.get_or_create(
        identifier=identifier, defaults={"name": name}
)

# In this case, if the Person already exists, its name is updated
person, created = Person.objects.update_or_create(
        identifier=identifier, defaults={"name": name}
)
147
Zags

Django hat Unterstützung dafür, check get_or_create

person, created = Person.objects.get_or_create(name='abc')
if created:
    # A new person object created
else:
    # person object already exists
9
Aamir Adnan

Ich dachte, ich würde eine Antwort hinzufügen, da Ihr Fragentitel so aussieht, als würde er fragen, wie er erstellt oder aktualisiert werden soll, anstatt wie im Fragenkörper beschrieben zu erhalten oder zu erstellen.

Wenn Sie ein Objekt erstellen oder aktualisieren möchten, hat die .save () -Methode dieses Verhalten bereits standardmäßig von the docs :

Django beschreibt die Notwendigkeit, INSERT- oder UPDATE-SQL-Anweisungen zu verwenden. Wenn Sie save () aufrufen, folgt Django diesem Algorithmus:

Wenn das Primärschlüsselattribut des Objekts auf einen Wert festgelegt ist, der True ergibt (dh einen anderen Wert als None oder die leere Zeichenfolge), führt Django ein UPDATE aus. Wenn das Primärschlüsselattribut des Objekts True lautet nicht gesetzt oder wenn das UPDATE nichts aktualisiert hat, führt Django ein INSERT aus.

Es ist erwähnenswert, dass, wenn sie sagen "Wenn das UPDATE nichts aktualisiert hat", sie sich im Wesentlichen auf den Fall beziehen, in dem die ID, die Sie dem Objekt gegeben haben, nicht bereits in der Datenbank vorhanden ist.

3
Tom Manterfield

Für nur eine kleine Anzahl von Objekten funktioniert das update_or_create gut, aber wenn Sie über eine große Sammlung verfügen, wird es nicht gut skaliert. update_or_create führt immer zuerst ein SELECT und danach ein UPDATE aus.

for the_bar in bars:
    updated_rows = SomeModel.objects.filter(bar=the_bar).update(foo=100)
        if not updated_rows:
            # if not exists, create new
            SomeModel.objects.create(bar=the_bar, foo=100)

Dies führt bestenfalls nur die erste Aktualisierungsabfrage aus, und nur, wenn sie mit Null übereinstimmt, führt es eine weitere INSERT-Abfrage aus. Dies erhöht Ihre Leistung erheblich, wenn Sie davon ausgehen, dass die meisten Zeilen tatsächlich vorhanden sind.

Alles hängt jedoch von Ihrem Anwendungsfall ab. Wenn Sie hauptsächlich Einfügungen erwarten, kann der Befehl bulk_create () eine Option sein.

1

Wenn eine der Eingaben beim Erstellen ein Primärschlüssel ist, reicht dies aus:

Person.objects.get_or_create(id=1)

Es wird automatisch aktualisiert, wenn vorhanden, da zwei Daten mit demselben Primärschlüssel nicht zulässig sind.

1
Aminah Nuraini