Datenbankstruktur Sinnvoll?

Hallo Habo, ich möchte mir gerade ein kleines Portal zu Übungszwecken der Scriptsprache Php schreiben. Bevor es überhaupt los geht mache ich mir gerade Gedanken über die Datenbanstruktur.

Dabei soll das Portal folgende Ziele erreichen :

Userlogin
Userseite einrichten
User Nachrichten senden

(Wirklich sehr simpel alles)

Zur Zeit habe ich folgendes Ergebnis der Datenbankstruktur (siehe Anhang).

Mit der Tabelle portal_nachrichten bin ich mir schon im klaren, wie eine Abfrage aussehen könnte.
Code:
 Select nachricht, ip, timestamp From portal_nachrichten from portal_nachrichten Where user_id = x
Problem an der Sache :

Ich muss ja erstmal aus der portal_user auslesen, welche Id der User gerade in der Tabelle hat und dann suchen - das kann nicht die feine Lösung sein ;-)

Ich hab schon mal mit Inner Joins gearbeiter, frage muss ich hier einen Inner Join machen? Finde die nämlich ziemlich lästig

Ist meine DB Struktur überhaupt sinnvoll?

LG, Weau :)
 
Zuletzt bearbeitet:
Sonderlich schlüssig wirkt mir das noch nicht.

User:
Die hier enthaltenen Daten passen einigermaßen. "details" könnte man ggf. noch aufsplitten, kommt drauf an, was du in diesem Feld ablegen willst. Die Nachrichten-ID hat in dieser Tabelle nix zu suchen, das Passwortfeld beinhaltet hoffentlich auch nur einen Hash, und nicht das PW im Klartext.

Login:
Sollte vielleicht in "Session" umgetauft werden, denn das ist es eigentlich, was du dort ablegen willst. Das Passwort hat hier nix zu suchen, dafür sollte sort sicherlich noch die Session-ID eine Spalte bekommen.

Nachrichten:
Eine Nachricht braucht mindestens 2 User-IDs als Fremdschlüssel, nämlich Absender und Empfänger. Ansonsten könnte die Tabelle ggf. noch ergänzt werden um einen Nachrichtenbetreff.


Zu den Abfragen: Um JOINs kommst du ab einer gewissen Komplexität der Anwendung sowieso nicht herum, ich sehe da aber auch kein Problem drin.
 
Warum vergibst du überhaupt so viele "doppelte" ids an Felder?
Was soll z.B: "portaluser.nachrichten_id"? Nimm zur Zuordnung doch einfach die eigentliche User-ID (als Foreign Key). Und was bezweckst du damit, Username und Passwort in zwei Tabellen redundant zu Speichern.
Ich kann verstehen, dass du Login und Profil trennen willst. Aber da reicht doch die User-ID zu Zuordnung von Datensätzen zwischen der Tabellen.
Also ich würde es etwas anders aufziehen:
Code:
table portal_user
===========
userid (Primary Key, auto_incr.)
name [Angezeigter Name, z.B: "metax."]
email
datails
bild

table portal_login
===========
userid [korrelliert zu portal_user.userid]
loginname [kann ja != angezeigter Name sein ...]
passwort
timestamp
ip

table portal_nachricht
==============
nachrichtenid
senderid
empfaengerid
timestamp
text
Wenn du jetzt mehrere Informationen auf einmal brauchst, kannst du die Daten einfach von mehreren Tabellen fetchen:
Code:
z.B:
SELECT portal_user.userid as senderid,
portal_user.name as sendername,
portal_nachricht.timestamp as datum,
portal_nachricht.text as text
FROM portal_user, portal_nachricht
WHERE  portal_nachricht.senderid = portal_user.userid
AND portal_nachricht.empfaengerid = $userid
ORDER BY portal_nachricht.timestamp DESC;
Für genaueres siehe die Dokumentation von MySQL bzw. der SQL allgemein.

mfg, metax.
 
Da es einen Lernzweck hat, würde ich vielleicht erstmal Entity-Relationsship Entwurf empfehlen: http://de.wikipedia.org/wiki/Entity-Relationship-Modell
dann setzt du den Entwurf in ein relationales Schema um:
http://www-lehre.informatik.uni-osnabrueck.de/~dbs/2001/skript/node41.html
verfeinerst das:
http://www-lehre.informatik.uni-osnabrueck.de/~dbs/2001/skript/node42.html
führst eine Normalisierung durch:
http://de.wikipedia.org/wiki/Normalisierung_(Datenbank)
und erst dann fängst du an zu programmieren :D
Ich weiß, dass es etwas viel auf einmal ist, die Links sind übrigens nur als Beispiele für weitere Suche.

Auch ist es ganz nett, einen blick auf http://de.wikipedia.org/wiki/Referenzielle_Integrität zu werfen (nicht vom Namen abschrecken lassen). Damit lässt sich z.B sicherstellen, dass nur "sinnvolle" Daten existieren und die Datenbank nicht zugemüllt wird. D.h z.B dass wenn ein User Eintrag aus der Usertabelle gelöscht wird, alle von ihm abhängigen Einträge (z.B in der PM_Tabelle) auch mit entferent werden (durch CASCADE Definition). Das gilt auch für Änderungen in der "Masteratabelle". Umgekehrt lässt sich z.B ein "falscher" Datensatz gar nicht einfügen - z.B eine Nachricht in die PM_Tabelle, wenn die zugehörige User_ID nicht existiert.

Es gibt auch die Klausel "check" (nunja, noch nicht bei MySQL)
Code:
create domain Gebiete varchar(20)
default ?Informatik? check (
value in ( ?Informatik?, ?Mathematik?,
?Physik?, ?Chemie?, ?Biologie?) )
...
create table Vorlesungen (
V Bezeichnung varchar(80) not null,
primary key,
SWS smallint check(SWS ≥ 0),
Semester smallint check(
Semester between 1 and 9),
Studiengang Gebiete )
... oder...
create table Buch Versionen (
ISBN char(10),
Auflage smallint check(Auflage > 0),
Jahr integer check
(Jahr between 1800 and 2020),
Seiten integer check(Seiten > 0),
Preis decimal(8,2) check(Preis ≤ 250),
primary key (ISBN, Auflage),
foreign key (ISBN) references B¨ucher (ISBN),
check
( (select sum(Preis) from Buch Versionen) <
(select sum(Budget) from Lehrst¨uhle) ) )
Auch wenn man auf den ersten Blick sagen würde "Wer braucht das Zeug, ich kanns ja mit PHP umsetzen und alles sicherstellen?!" - die Votreile zeigen sich, wenn man das z.B dynamisch erweiterbar macht, mehrere Programmierer daran arbeiten lässt oder einfach paar Monate später an an dem Code werkelt. Dann hat man keine (oder eher weniger ;) ) Möglichkeiten, irgendwelche "fatalen" Fehler zu machen, nur weil man nseine eigene Definition nicht mehr so genau im Kopf hat oder weil der "Mitstreiter" etwas an der Struktur missvestanden hat.
 
Zurück
Oben