2016-06-11 7 views
0

Wie verhindere ich, Sammlungen synchron während Aktualisierungen und Löschungen, wenn ich die folgenden Schemata definiert:Mongoose und Datenintegrität

var RestaurantSchema = mongoose.Schema({ 
    name: { 
     type: String, 
     required: true, 
    }, 
    menus: [{ 
     type: mongoose.Schema.Types.ObjectId, 
     ref: 'Menu' 
    }] 
}); 

var MenuSchema = mongoose.Schema({ 
    name: { 
     type: String, 
     required: true 
    }, 
    restaurant: { 
     type: mongoose.Schema.Types.ObjectId, 
     ref: 'Restaurant', 
     required: true 
    } 
}); 

erstelle ich ein Restaurant, indem Sie die folgenden Schritte aus:

Restaurant.create(restaurant, callback); 

I Erstellen Sie ein Menü und verknüpfen Sie es mit einem Restaurant, indem Sie folgendermaßen vorgehen:

Menu.create(menu, function(err, menu) { 
    if (err) { 
     callback(err, menu); 
    } 
    else { 
     restaurantController.addMenu(menu.restaurant, menu._id, 
      function(err, restaurant) { 
       callback(err, menu); 
      }); 
    } 
}); 

Erste Frage, gibt es eine bessere wa y Menüs zu Restaurants hinzufügen?

Zweite Frage, wie halte ich die Daten synchron, wenn ich ein Menü lösche oder wenn ich ein Restaurant lösche?

Dritte Frage, wie ich die Daten über Sammlungen hinweg synchronisieren, wenn ich ein Update mache, das die ID aus dem Referenzfeld entfernt. Zum Beispiel, wenn ich dies tun:

Restaurant.findOneAndUpdate({ _id: _id }, { $unset.menus }, options, callback); 

, dass die Menüs Array auf dem Restaurant-Dokument jedoch leer wird, würde die Menüs Dokument noch die Referenz auf das Restaurant.

Antwort

1

IMO Menu und Restaurant sollten eine eindeutige direktionale Beziehung haben. So kann eine Restaurant Einheit Menu (wenn Restaurant und Menü muss 1-1 sein) oder eine Sammlung von Menüs 1-n (Frühstück, Mittagessen, Abendessen etc ..).

Ein Menu muss nicht auf die Restaurant zurückverweisen, da dies zu einem zirkulären Referenzproblem führen könnte.

Auch die Datenintegrität könnte geschraubt werden. Zum Beispiel, was ist, wenn ein Restaurant-A einen Menu-A referenziert, aber Menu-A Referenzen Restaurant-B?

In Bezug auf Ihre Fragen: Erste Frage, gibt es eine bessere Möglichkeit, Menüs zu Restaurants hinzufügen?

  1. erstellen Menu, die _id Sie zurückkommen sollte.
  2. Diese Referenz zu RestaurantmyRestaurant.menuId = _id hinzufügen.
  3. Restaurant aktualisieren.

    PS: Sie können Ihre Struktur reduzieren, indem Sie stattdessen Versprechen verwenden.

Zweite Frage, wie verhindere ich, die Daten synchron, wenn ich ein Menü löschen oder wenn ich ein Restaurant löschen?

Sie betrachten 2 db Operationen (Menü löschen, entfernen Sie die Menü-Referenz aus Restaurant), die als eine Transaktion ausgeführt werden müssen. Checkout, wie Sie Multi-Dokument-Transaktionen durchführen können https://docs.mongodb.com/manual/tutorial/perform-two-phase-commits/

Meine obige Antwort könnte Ihre dritte Frage genügen.

Dadurch wird das Menü Array auf dem Restaurant-Dokument, aber die Menüs Dokument würde immer noch den Verweis auf das Restaurant haben.

Wenn Sie Ihr Schema als unidirektional neu verkabeln, müssen Sie sich keine Gedanken darüber machen.

Hoffe, das hilft.

+0

Ich denke, ein unidirektionales Schema ist der Weg zu gehen. Ich bin neu in all dem und von dem, was ich gelesen habe, scheint es, als ob der empfohlene/beste Praxisansatz mit MongoDB darin bestand, das gesamte Dokument in einen Datensatz zu bringen. Aber es unterstützt Dokumentverweise und mit Mongoose gibt es die populate Methode. Also dachte ich, ich sollte das Schema so erstellen, wie ich es beschrieben habe, denn dann kann ich einfach populate verwenden, um das gesamte Dokument aufzubauen, da die zugehörige ID in einer Array-Eigenschaft gespeichert ist. Was ist der Sinn der Populate-Methode, wenn Sie auf solche Probleme stoßen? –

+0

Vielleicht liegt es außerhalb des Geltungsbereichs der OP-Frage; Aber könnten Sie ein Beispiel dafür zeigen, was Sie mit "Sie können Ihre Struktur mit Hilfe von Versprechen abflachen" gemeint haben, das heißt, wenn Sie auf der Controller-Ebene etwas anderes als async/abwarten wollten. Ich bin ein Neuling bei Node/Mungo. – mrClean