Ich arbeite an einem Editor, der seinen Benutzern ermöglicht, "Objekt" -Definitionen in Echtzeit zu erstellen. Eine Definition kann null oder mehr Eigenschaften enthalten. Eine Eigenschaft hat einen Namen und einen Typ. Sobald eine Definition erstellt wurde, kann ein Benutzer ein Objekt dieser Definition erstellen und die Eigenschaftswerte dieses Objekts festlegen.Schema zur Unterstützung dynamischer Eigenschaften
Also per Mausklick sollte der Benutzer zB. in der Lage sein, eine neue Definition namens "Bicycle" zu erstellen und die Eigenschaft "Size" vom Typ "Numeric" hinzuzufügen. Dann eine andere Eigenschaft namens "Name" vom Typ "Text" und dann eine andere Eigenschaft namens "Preis" vom Typ "Numerisch". Sobald dies erledigt ist, sollte der Benutzer in der Lage sein, ein paar "Fahrrad" -Objekte zu erstellen und die Eigenschaftswerte "Name" und "Preis" jedes Fahrrads einzugeben.
Jetzt habe ich diese Funktion in mehreren Softwareprodukten gesehen, also muss es ein bekanntes Konzept sein. Mein Problem begann, als ich mich hinsetzte und versuchte, ein DB-Schema zu erstellen, um diese Datenstruktur zu unterstützen, weil ich die Eigenschaftswerte mit den entsprechenden Spaltentypen speichern möchte. Ie. Ein numerischer Eigenschaftswert wird beispielsweise als INT in der Datenbank gespeichert, und ein Texteigenschaftswert wird als VARCHAR gespeichert.
Zuerst muss ich eine Tabelle, die alle meine Objektdefinitionen halten:
Table obj_defs
id | name |
----------------
1 | "Bicycle" |
2 | "Book" |
Dann brauche ich einen Tisch zum Halten, welche Art von Eigenschaften jeder Objektdefinition haben sollte:
Table prop_defs
id | obj_def_id | name | type |
------------------------------------
1 | 1 | "Size" | ? |
2 | 1 | "Name" | ? |
3 | 1 | "Price" | ? |
4 | 2 | "Title" | ? |
5 | 2 | "Author" | ? |
6 | 2 | "ISBN" | ? |
I würde auch eine Tabelle, die jedes Objekt enthält:
Table objects
id | created | updated |
------------------------------
1 | 2011-05-14 | 2011-06-15 |
2 | 2011-05-14 | 2011-06-15 |
3 | 2011-05-14 | 2011-06-15 |
Schließlich brauche ich eine Tabelle, die wi ll die tatsächlichen Eigenschaftswerte der einzelnen Objekte halten, und eine Lösung ist für diese Tabelle eine Spalte für jeden möglichen Wert Typ aufweisen, wie dies:
Table prop_vals
id | prop_def_id | object_id | numeric | textual | boolean |
------------------------------------------------------------
1 | 1 | 1 | 27 | | |
2 | 2 | 1 | | "Trek" | |
3 | 3 | 1 | 1249 | | |
4 | 1 | 2 | 26 | | |
5 | 2 | 2 | | "GT" | |
6 | 3 | 2 | 159 | | |
7 | 4 | 3 | | "It" | |
8 | 5 | 3 | | "King" | |
9 | 6 | 4 | 9 | | |
Wenn ich dieses Schema implementiert, was wäre die „Art“ Spalte der Tabelle prop_defs halten? Ganzzahlen, die jeweils einem Spaltennamen zugeordnet sind, varchars, die einfach den Spaltennamen enthalten? Irgendwelche anderen Möglichkeiten? Würde mir eine gespeicherte Prozedur irgendwie helfen? Und wie würde die SQL zum Abrufen der "name" -Eigenschaft von Objekt 2 aussehen?
Ausgezeichnete Antwort! Vielen Dank :) –
Was wäre dann eine bessere Lösung für den Fall, dass EAV etwas ist, das zu vermeiden ist, wenn die Notwendigkeit, Objekte zu verschachteln, sich darstellt? – ChrisR
Jetzt mit NoSQL-Lösungen wie MongoDB können EAVs schließlich sterben. –