Sails.js Modell - einfügen oder aktualisieren von Datensätzen
Schon ausprobieren Sails.js und ich Schreibe eine app, die importiert Daten aus einer Drittanbieter-API und speichert Sie in einer MySQL-Tabelle. Grundsätzlich bin ich versucht zu synchronisieren, die Daten über meine app für weitere Analysen, die Aktualisierung meiner Unterlagen oder erstellen neue Datensätze, wie gebraucht.
Ist, habe ich mich durch Segel' API-und ich sehe, Methoden zu finden, erstellen und aktualisieren Sie Datensätze, aber keine integrierte Methode zum einfügen/aktualisieren von Datensätzen basierend auf der situation. Hab ich was übersehen, oder muss ich diese umsetzen mir?
Wenn ich diese umsetzen mir, kennt jemand ein gutes design pattern für insert/update?
Dies ist, was ich denke, es könnte so Aussehen...
_.each(importedRecords, function(record){
MyModel.find({id: record.id}).exec(function findCB(err, found){
if(found.length){
MyModel.update(record.id, task).exec(function(err, updated){
if(err) { //returns if an error has occured, ie id doesn't exist.
console.log(err);
} else {
console.log('Updated MyModel record '+updated[0].name);
}
});
}else{
MyModel.create(record).exec(function(err, created){
if(err) { //returns if an error has occured, ie invoice_id doesn't exist.
console.log(err);
} else {
console.log('Created client record '+created.name);
}
});
}
});
});
Bin ich unter der Leitung in die richtige Richtung, oder gibt es eine elegantere Lösung?
Außerdem bin ich den Umgang mit vielen verschiedenen Modellen in dieser app, was bedeuten würde, Neuerstellung dieser block von code, der auf jedes meiner Modelle. Gibt es eine Möglichkeit, kann ich das erweitern der Basis-Model-Objekts, um diese Funktionalität hinzuzufügen für alle Modelle.
Dank,
John
Du musst angemeldet sein, um einen Kommentar abzugeben.
Habe ich umgeschrieben, Kritische Mash-code, also seine Art und Weise weniger code und mehr Generika.
Rufen Sie nun updateOrCreate die gleiche Weise rufen Sie findOrCreate. Und es sieht so aus, dass:
So, dass die Art und Weise, die Sie schreiben können Kriterien auf die gleiche Weise. keine Notwendigkeit, die Arbeit auf die Taste, und der code ist so viel einfacher.
module.exports.models = {
Es hat nicht funktioniert es. Habe die Methode undefiniert Fehler als ich es von meinem controller. Also ich habe es als eine Methode auf dem Modell war ich versucht, es zu benutzen und es funktionierte dort. Also +1, große Antwort. Weiß nicht, warum es nicht funktioniert in den Modellen-Datei, wie Sie vorgeschlagen.Segel 0.10 hat
findOrCreate(criteria, attributes, callback)
finden Sie Segel Docs.criteria
ist die Suche nach Kriterien für die "finden" - bit (gleiche syntax wie find()).attributes
ist die Daten verwendet werden, wenn es nicht für die "erstellen" - bit (gleiche syntax wie create()).Hier ein Beispiel:
MyModel.findOrCreate({name:'Walter'},{name:'Jessie'}, function (err, record){
console.log('What\'s cookin\' '+record.name+'?');
Beachten Sie auch, dass es andere composite query-Methoden dokumentiert, die in der Wasserlinie-repository (siehe tests für Beispiele) und Wasserlinie Dokumentation:
Als Blick auf etwas, gut, es ist draußen, aber es ist nicht in der Haupt-Segel-Dokumentation ist doch so, die Antwort ist ja und Nein, also keine Sorge 🙂
upsert
undfindOrCreate
Methoden, die eine Gegenwartnext()
Methode für die go-ahead zuinsert
odercreate
bzw.Ihre Lösung richtig ist. Es gibt keinen anderen Weg, dies zu tun mit der Wasserlinie (die ORM von sails.js).
Aber mehrere Datenbanken Funktionen für diesen Fall:
MySQL
REPLACE INTO table SET id = 42, foo = 'bar';
(mit primary-oder unique-Schlüssel. Ziemlich beschissen, wenn Sie auto_increment 😉
In der Wasserlinie können Sie das Modell.query()-Funktion ausführen direkten SQL (siehe: http://sailsjs.org/#/documentation/reference/waterline/models/query.html)
MongoDB
Den upsert Flagge bedeutet: Wenn Sie nicht aktualisieren Sie es, weil Sie nicht finden, alles, was mit der Abfrage erstellen, die dieses element!
In der Wasserlinie können Sie das Modell.native()-Funktion ausführen direkten mongoDB-Befehle (siehe: http://sailsjs.org/#/documentation/reference/waterline/models/native.html)
Abschluss
Müssen Sie schnelle Ausführung (und von corse, wenn Sie haben viele viele Anfrage), würde ich vorschlagen, die Verwendung der Muttersprache/sql-Funktionen. Aber im Allgemeinen bin ich wirklich ein fan von der Flexibilität der ein ORM-System und jedes mal, wenn Sie die Verwendung von Datenbank-spezifischen Funktionen ist es schwieriger zu handhaben.
Dank user3351722 ich lieber mit dem ORM-system als gut. Ich habe nur versucht, die Umsetzung der oben genannten Lösung als ein Allgemeines Modell, Methode. (Basierend auf Erben Attribute und lifecycle-Funktionen Sails.js Modelle).
Bearbeitete ich config/models.js und wurde eine neue Funktion Hinzugefügt
insertOrUpdate
nimmt, dass der name des Indexes Spalte, die Daten, die ich will, um insert-oder update-und eine callback-Funktion.Funktioniert dies nur mit Tabellen/Auflistungen, die über einen index. Ich weiß nicht, wie die Introspektion der name des Schlüssels von einem Modell in der Wasserlinie, so dass ich übergeben, in die der name des Feldes als string.
Hier ist, wie könnten Sie die Methode in einem controller...
Ich habe versucht, diese Methode mit drei verschiedenen Modellen und, so weit, so gut. Sie sind alle MySQL-Tabellen und die Modelle haben alle einen definierten index. Ihr milage kann sich sehr, wenn Sie mit einem anderen datastore.
Wenn jemand sieht, ein Weg zu verbessern, bitte lassen Sie es uns wissen.
Dies ist, wie ich es mache: ich bringe das config/models.js um die Funktionalität und es prüft, um zu sehen, ob der adapter hat den richtigen Methoden. Sie können es nennen, wie ein Versprechen oder normal.
Race
Zustand, da der Datensatz erstellt werden konnte, nachdem die lookup. Dies gilt für alle Datenbanken unterstützen Transaktionen. Technisch gesehen, ist es am besten, rufen Sie dascreate
Funktion und hören für einen Fehler, das würde wiederum sagen, Sie zu aktualisieren, statt.