Toon posts:

Generieke gegevens in een DB met een flexible schema

Pagina: 1
Acties:

Verwijderd

Topicstarter
Ik onderzoek momenteel of ik een relationele database dusdanig kan ontwerpen dat je er alle alle gegevens in op kunt slaan, zonder dat het schema voor één soort gegevens is bedoeld. Dus je tabellen beschrijven niet direct de gegevens (tabel Product met kolommen productcode en naam) maar beschrijven wát je opslaat en wat het onderliggende type data is.

Het probleem is, misschien is hier een term voor, maar die weet ik niet. En zodoende heb ik nogal wat moeite om hierover informatie en voorbeelden te vinden. Weet iemand hier wat ik bedoel en of hier een eenduidige term voor is?

  • Daos
  • Registratie: Oktober 2004
  • Niet online
In Java hebben ze het altijd over Properties. Twee kolommen: String key en String value.

Zoiets is handig voor een aantal op zichzelf staande constanten, maar niet voor alle data.


Je zal er niet veel over kunnen vinden, want het is niet de bedoeling van een relationele database dat je alle data zo opslaat.

[edit]
Wat jij wilt, past dan gewoon in 1 tabel met 4 kolommen. De key van hierboven bestaat dan uit de kolommen type, code en veldnaam.

[edit2]
voorbeeldje:
ProductCode = PC1, Beschrijving = Mooie PC, Prijs = E 2000,00.

TypeCodeFieldValue
ProductPC1BeschrijvingMooie PC
ProductPC1PrijsE 2000,00

[ Voor 57% gewijzigd door Daos op 10-04-2006 15:06 ]


Verwijderd

Topicstarter
Ja, voorbeeld is in de richting, alleen probeer je wel optimaal gebruik te maken van je database. Dus ik zou strings en bedragen niet in dezelfde kolom opslaan.

Maar het gaat me nu niet om een specifieke implementatie, maar ik ben opzoek naar een term die dit idee omschrijft, zodat ik er meer informatie over kan vinden.

  • Gabberhead
  • Registratie: Mei 2002
  • Laatst online: 07-12-2020

Gabberhead

Pluizig en blauw

De term die ik hier vaak voor hoor is 'Objectenstructuur', maar de officiële term is me ontschoten.
Leuk principe hoor. Een uitvoermogelijkheid hiervan is deze:

Een object wordt beschreven door objecttypes
Een object bevat parameters
Een parameter heeft waardes

Dat zijn dus 4 tabellen. In de waardes tabel kun je er dan voor kiezen om kolommen op te nemen met verschillende datatypes.
Overigens is dit nog lang niet compleet. Je kunt nu bijvoorbeeld nog niet opnemen wat de geldigheidsduur is van een bepaalde waarde of object.

Integratie ontwikkelaars hier melden! http://www.whitehorses.nl

"If everything seems under control, you're just not going fast enough."


  • Daos
  • Registratie: Oktober 2004
  • Niet online
Soms zie je ook "Key/Value Pairs" als naam. [google=Key Value Database]


Maar nogmaals: zoiets is alleen handig voor losse constanten. Bv "email van beheerder" ->"webmaster@mijnsite.xxx" en "lettergrootte" -> "12"

[ Voor 24% gewijzigd door Daos op 10-04-2006 15:46 ]


  • JHS
  • Registratie: Augustus 2003
  • Laatst online: 04-01 15:49

JHS

Splitting the thaum.

Ik denk dat het over het algemeen een stuk zinniger is om de structuur van je database je daadwerkelijke structuur van gegevens weer te laten geven, aangezien het anders als eerste nogal flink ten koste zou kunnen gaan van je performance, en relationele databases er niet voor bedoeld zijn, zoals * Daos al aangaf :) .

Als je een generieke manier wil ontwikkelen om te voorkomen dat je voor alle (typen) gegevens zelf nieuwe tabellen moet gaan zitten maken, denk ik dat je beter een stuk software kan ontwikkelen wat de database voor je in elkaar zit aan de hand van een relationeel / object georienteerde configuratiebestand :) .

Kan je anders aangeven wat je wil bereiken?

DM!


Verwijderd

Topicstarter
Key/value pairs lijkt de term te zijn die ik zocht.

De vraag ligt er als volgt: Kunnen we een applicatie ontwikkelen waar verschillende klanten hun gegevens in kwijt kunnen, op een dusdanige manier, dat we niet telkens een nieuwe database hoeven te ontwikkelen. Denk content management, maar niet document georienteerd, maar met 'business objecten'. De ene keer schoenen, de andere keer auto's. Het schema moet dus slechts 'objecten' en hun eigenschappen bevatten, en waarschijnlijk ook de relaties ertussen beschrijven.

Ik denk zelf dat het wel kan, maar zie nu al diverse buien hangen. Maar omdat het slechts om een verkenning van de mogelijkheden gaat, ga ik nu niets uitsluiten, maar wil ik eerst kijken of hierover meer geschreven is, of voorbeelden zijn van werkende systemen. Probleem: ik kan niets vinden, waarschijnlijk omdat ik niet goed zoek. Dat komt op z'n beurt weer omdat ik misschien een algemene term voor een dergelijke werkwijze over het hoofd zie?

Veel van m'n zoektochten kwamen uit op ORM, maar dat is dus niet wat ik zoek.

Mogelijke problemen
  1. Zie maar eens alle mogelijke constraints en relaties te vangen in een algemeen inzetbaar schema.
  2. Door in tabellen niet de 'echte' data op te slaan, maar juist de data te beschrijven kun je niet (haast niet?) gegevens op de traditionele manier met queries opvragen en mis je dus idd een belangrijk voordeel van RDB (zoals gezegd: hier is het niet voor bedoeld).
  3. Hoe ga je je BLL schrijven en presentatie lagen schrijven? Om echt winst te behalen zou je die ook generiek moeten houden, anders kun je net zo goed per klant een applicatie schrijven.

[ Voor 4% gewijzigd door Verwijderd op 10-04-2006 19:45 ]


  • djluc
  • Registratie: Oktober 2002
  • Laatst online: 20-02 15:44
Je probleem is al vaker besproken, o.a. in een topic wat ik gestart heb: [rml][ alg]database ontwerp voor personenbeheer[/rml]

Wat sowieso geen goede oplossing is: een relationale database (mis/ge)bruiken voor een object georienteerde opzet. Dit is gewoon inefficient, traag en onhandig. Er zijn databases die hier wel voor bedoeld zijn.

  • JHS
  • Registratie: Augustus 2003
  • Laatst online: 04-01 15:49

JHS

Splitting the thaum.

Krimszon: Nogmaals, ik denk dat je hier niet je database voor moet gaan gebruiken. Ik betwijfel ten zeerste of dat ook maar enigzins performant gaat zijn :) . Maar, wat denk je van de manier die ik in mijn tweede alinea hierboven schetste? Dat lijkt me een stuk zinniger oplossing. Aan de andere kant is het zoals je zelf zegt maar moeilijk om alle relaties en constraints aan te gaan geven in een dergelijk schema.

Eerlijkgezegd denk ik dat dit een geval 'over-generalisering' is :) . Met een goed framework en degelijke tools kóst het helemaal niet veel (tijd) om een specifieke implementatie voor een bepaald type business objecten, als je tenminste wilt dat die wat kunnen doen. Dat is dan ook (een deel van) de filosofie achter Ruby on Rails, en mij bevalt het eerlijkgezegd wel.

Maar wat bedoel je precies met het opslaan van business objecten? Ik begrijp het doel van de applicatie nog niet helemaal, kan je een concreet scenario schetsen?

Overigens zijn veel opmerkingen in het topic van * djluc interessant en zinnig :) .
djluc schreef op maandag 10 april 2006 @ 19:48:
Wat sowieso geen goede oplossing is: een relationale database (mis/ge)bruiken voor een object georienteerde opzet. Dit is gewoon inefficient, traag en onhandig. Er zijn databases die hier wel voor bedoeld zijn.
offtopic:
Met een fatsoenlijk O/R mapper zijn dat soort problemen grotendeels tot volledig op te vangen :) ?

DM!


  • JaQ
  • Registratie: Juni 2001
  • Laatst online: 20-02 23:48

JaQ

JHS schreef op maandag 10 april 2006 @ 20:05:
Krimszon: Nogmaals, ik denk dat je hier niet je database voor moet gaan gebruiken. Ik betwijfel ten zeerste of dat ook maar enigzins performant gaat zijn :) .
Ik weet wel zeker dat de performance uiteindelijk ruk is. Je queries worden namelijk onmogelijk ingewikkeld met ladingen (onnodige) joins.

Om een van de grote Oracle helden (Tom Kyte) te citeren:
Do not use Generic Data Models

Frequently I see applications built on a generic data model for "maximum
flexibility" or applications built in ways that prohibit performance. Many times
- these are one in the same thing! For example, it is well known you can
represent any object in a database using just four tables:

Create table objects ( oid int primary key, name varchar2(255) );

Create table attributes
( attrId int primary key, attrName varchar2(255),
datatype varchar2(25) );

Create table object_Attributes
( oid int, attrId int, value varchar2(4000),
primary key(oid,attrId) );

Create table Links ( oid1 int, oid2 int,
primary key (oid1, oid2) );


That's it - no more CREATE TABLE for me! I can fill the attributes table up with
rows like this:

insert into attributes values ( 1, 'DATE_OF_BIRTH', 'DATE' );
insert into attributes values ( 2, 'FIRST_NAME', 'STRING' );
insert into attributes values ( 3, 'LAST_NAME', 'STRING' );
commit;


And now I'm ready to create a PERSON record:

insert into objects values ( 1, 'PERSON' );
insert into object_Attributes values( 1, 1, '15-mar-1965' );
insert into object_Attributes values( 1, 2, 'Thomas' );
insert into object_Attributes values( 1, 3, 'Kyte' );
commit;

insert into objects values ( 2, 'PERSON' );
insert into object_Attributes values( 2, 1, '21-oct-1968' );
insert into object_Attributes values( 2, 2, 'John' );
insert into object_Attributes values( 2, 3, 'Smith' );
commit;

And since I'm good at SQL, I can even query this record up to get the FIRST_NAME
and LAST_NAME of all PERSON records:

ops$tkyte@ORA920> select
max( decode(attrName, 'FIRST_NAME', value, null )) first_name,
2 max( decode( attrName, 'LAST_NAME', value, null ) ) last_name
3 from objects, object_attributes, attributes
4 where attributes.attrName in ( 'FIRST_NAME', 'LAST_NAME' )
5 and object_attributes.attrId = attributes.attrId
6 and object_attributes.oid = objects.oid
7 and objects.name = 'PERSON'
8 group by objects.oid
9 /

FIRST_NAME LAST_NAME
-------------------- --------------------
Thomas Kyte
John Smith


Looks great, right? I mean, the developers don't have to create tables anymore,
we can add columns at the drop of a hat (just requires an insert into the
ATTRIBUTES table). The developers can do whatever they want and the DBA can't
stop them. This is ultimate "flexibility". I've seen people try to build entire
systems on this model.

But, how does it perform? Miserably, terribly, horribly. A simple "select
first_name, last_name from person" query is transformed into a 3-table join with
aggregates and all. Further, if the attributes are "NULLABLE" - that is, there
might not be a row in OBJECT_ATTRIBUTES for some attributes, you may have to
outer join instead of just joining which in some cases can remove more optimal
query plans from consideration.

Writing queries might look pretty straightforward, but it's impossible to do in
a performant fashion. For example, if we wanted to get everyone that was born in
MARCH or has a LAST_NAME = 'SMITH', we could simply take the query from above
and just wrap an inline view around that:


ops$tkyte@ORA920> select *
2 from (
3 select
max(decode(attrName, 'FIRST_NAME', value, null)) first_name,
4 max(decode(attrName, 'LAST_NAME', value, null)) last_name,
5 max(decode(attrName, 'DATE_OF_BIRTH', value, null))
date_of_birth
6 from objects, object_attributes, attributes
7 where attributes.attrName in ( 'FIRST_NAME',
'LAST_NAME', 'DATE_OF_BIRTH' )
8 and object_attributes.attrId = attributes.attrId
9 and object_attributes.oid = objects.oid
10 and objects.name = 'PERSON'
11 group by objects.oid
12 )
13 where last_name = 'Smith'
14 or date_of_birth like '%-mar-%'
15 /

FIRST_NAME LAST_NAME DATE_OF_BIRTH
-------------------- -------------------- --------------------
Thomas Kyte 15-mar-1965
John Smith 21-oct-1968

So, it looks "easy" to query, but think about the performance! If you had a
couple thousand OBJECT records, and a couple tens of thousands of
OBJECT_ATTRIBUTES - Oracle would have to process the entire inner group by query
first and then apply the WHERE clause.

This is not a made up data model, one that I crafted just to make a point. This
is an actual data model that I've seen people try to use. Their goal is ultimate
flexibility. They don't know what OBJECTS they need, they don't know what
ATTRIBUTES they will have. Well - that is what the database was written for in
the first place: Oracle implemented this thing called SQL to define OBJECTS and
ATTRIBUTES and lets you use SQL to query them. You are trying to put a generic
layer on top of a generic layer - and it fails each and every time except for
the most trivial of applications.
Voor meer over deze discussie, zie asktom.oracle.com

[ Voor 5% gewijzigd door JaQ op 11-04-2006 00:18 ]

Egoist: A person of low taste, more interested in themselves than in me


Verwijderd

Topicstarter
Bedankt! Vooral die quote van Tom 'Oracle' Kyte is precies wat ik bedoel, en geeft gelijk aan waarom het vooral niet te doen :P . Ik had gewoon moeite dit soort info te vinden (ben slecht om idee om te zetten naar goede zoekterm voor Google ofzo).

Nu dat ik allemaal bekeken heb ga ik het iig zeker niet doen. Het geheel vraagt gewoon om een nieuwe applicatie/database per nieuw project, niks aan te doen, en ook helemaal niet erg hoor, ook daar worden we voor betaald...

  • TukkerTweaker
  • Registratie: November 2001
  • Laatst online: 21-02 23:07
Verwijderd schreef op woensdag 12 april 2006 @ 13:01:
Bedankt! Vooral die quote van Tom 'Oracle' Kyte is precies wat ik bedoel, en geeft gelijk aan waarom het vooral niet te doen :P . Ik had gewoon moeite dit soort info te vinden (ben slecht om idee om te zetten naar goede zoekterm voor Google ofzo).

Nu dat ik allemaal bekeken heb ga ik het iig zeker niet doen. Het geheel vraagt gewoon om een nieuwe applicatie/database per nieuw project, niks aan te doen, en ook helemaal niet erg hoor, ook daar worden we voor betaald...
Wat je wel kunt doen is een basis schema ontwikkelen en hier uitbreidingen voor schrijven. In weet niet in welke omgeving je ontwikkeld maar als je bv. hibernate neemt kun je nog behoorlijk object georiënteerd te werk gaan. Schrijf een basischema voor bv. Product met alle atributen. Een extentie kan dan FoodProduct of NonFoodProduct zijn. Voor het ophalen van de gegevens krijg je 1 join per extentie dus als je niet te diep gaat hoeft je kwa performance niet te duur uit te zijn.
Pagina: 1