Doppelwerte in Tabelle verhindern

Installation und Anwendung von Datenbankschnittstellen wie SQLite, PostgreSQL, MariaDB/MySQL, der DB-API 2.0 und sonstigen Datenbanksystemen.
Antworten
Caldar
User
Beiträge: 46
Registriert: Sonntag 17. Mai 2009, 18:20

Ich benutze Python 2.5 und Mysql(aktuelle Version) zum Anlegen einer Wasserwert-Datenbanktabelle.

Dabei werden csv-Files mit Timestamps und den entsprechenden Wasserwerten (pH-Wert, Nitrit usw) "angeliefert" und durch ein Python-Skript eingepflegt.
So weit so gut. Nur kann es vorkommen, dass ich z.B. eine Datei erhalte, die meinetwegen Daten einer bestimmten Woche enthält. Am Ende des Jahres bekomme ich dann eine csv-Datei mit allen aufgezeichneten Werten. Nun will ich aber doppelte Werte vermeiden, da ja in der Jahres-csv-Datei diese 1 Woche schon vorher eingepflegt wurde.
Nun kann ich durch

ALTER IGNORE TABLE qual ADD UNIQUE INDEX(`Id`,`UnixTimestamp`)

verhindern, dass Doppelwerte reinkommen, aber das Problem ist nun:
Wenn versucht wird, einen Wert einzutragen, der schon in der Tabelle vorhanden ist , wirft mir MySQL natürlich einen
_mysql_exceptions.IntegrityError, der sieht dann z.B. so aus: (1062, "Duplicate entry '91-1167720000' for key Id_2'")
und mein Python-Skript terminiert dann.
Wie verhindere ich einerseits, dass Doppelwerte in der Tabelle stehen und andererseits die MySQL-Exception abgefangen wird und die restlichen Werte, die noch nicht in der Tabelle sind, dort hineingeschreiben werden?
Bin für jede Hilfe dankbar
Leonidas
Python-Forum Veteran
Beiträge: 16025
Registriert: Freitag 20. Juni 2003, 16:30
Kontaktdaten:

Caldar hat geschrieben:Wie verhindere ich einerseits, dass Doppelwerte in der Tabelle stehen und andererseits die MySQL-Exception abgefangen wird und die restlichen Werte, die noch nicht in der Tabelle sind, dort hineingeschreiben werden?
Mit try-except.
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
Caldar
User
Beiträge: 46
Registriert: Sonntag 17. Mai 2009, 18:20

Das habe ich, aber das Programm hält trotzdem an:
Wie bringe ich es soweit, dass es nach der Exception weiterläuft?

Code: Alles auswählen

try:
    curs.execute(sql)

except MySQLdb.Error, e:
        print "Doppelwert"
        print e[1]

Leonidas
Python-Forum Veteran
Beiträge: 16025
Registriert: Freitag 20. Juni 2003, 16:30
Kontaktdaten:

Na die Queries solange ausführen lassen bis alles importiert wurde, dafür gibt es Schleifen.
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
Caldar
User
Beiträge: 46
Registriert: Sonntag 17. Mai 2009, 18:20

Das probiere ich ja gerade, aber ohne Erfolg:

Code: Alles auswählen

try:
    sql = """INSERT INTO TABLE `ww` (`ph`,`UnixTimestamp`, `id`) VALUES '%s'""" % val
    curs.execute(sql)

except MySQLdb.Error, e:
        print "Doppelwert"
        curs.execute(sql)

Anmerkung: val ist eine Liste, die die Werte enthält. Das 1. Einlesen in die DB funktioniert ohne Probleme, ist klar, aber wenn ich die Werte ein 2.Mal einlesen lassen will, darf er das ja gerade nicht machen. Deshalb habe ich die Spalten UnixTimestamp und Id auch Unique gekennzeichnet.
MySQLdb wirft also dann die Exception, bringt mir in der Konsole "Doppelwert", aber er weigert sich, die restlichen Werte (sind ja nicht alle doppelt vorhanden) einzupflegen. Es könnten ja neue Werte dabei sein, die noch nicht in der Tabelle sind. Stattdessen bricht er beim 1. Doppelwert ab, geht in die Exception, in der ich ja die sql-Anweisung weiterführen will, aber er bricht schon vorher ab.
Benutzeravatar
jbs
User
Beiträge: 953
Registriert: Mittwoch 24. Juni 2009, 13:13
Wohnort: Postdam

Irgendwie kann das nicht klappen, wenn du das was schiefgeht im except wiederholst.
[url=http://wiki.python-forum.de/PEP%208%20%28%C3%9Cbersetzung%29]PEP 8[/url] - Quak!
[url=http://tutorial.pocoo.org/index.html]Tutorial in Deutsch[/url]
Caldar
User
Beiträge: 46
Registriert: Sonntag 17. Mai 2009, 18:20

Stimmt, fällt mir auch grad auf.
kann man ihn nicht dazu bringen, alle schon vorhandenen Werte zu skippen und nur die nichtvorhandenen einzufügen?
BlackJack

@Caldar: Dazu braucht man niemanden bringen -- wenn die Ausnahme ausgelöst wird, dann werden die Daten ja nicht eingetragen.
ms4py
User
Beiträge: 1178
Registriert: Montag 19. Januar 2009, 09:37

BTW: Schau dir mal das Kapitel [wiki=Parametrisierte_SQL-Queries]Parameterisierte Queries[/wiki] an.
Benutzeravatar
noisefloor
User
Beiträge: 3856
Registriert: Mittwoch 17. Oktober 2007, 21:40
Wohnort: WW
Kontaktdaten:

Hallo,

Alternative: wenn du die Daten mit LOAD DATA INFILE einfügst ignoriert MySQL IMHO automatisch doppelte Einträge, ohne einen Fehler zu werfen.

Müßtest du im Zweifelsfall aber nochmal prüfen. :-)

Gruß, noisefloor
Benutzeravatar
jens
Python-Forum Veteran
Beiträge: 8502
Registriert: Dienstag 10. August 2004, 09:40
Wohnort: duisburg
Kontaktdaten:

Evtl. auch interessant: [wiki]DB-Transaktionen[/wiki]

GitHub | Open HUB | Xing | Linked in
Bitcoins to: 1JEgSQepxGjdprNedC9tXQWLpS424AL8cd
Antworten