'ascii' codec can't encode character u'\xe4

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
audacity363
User
Beiträge: 83
Registriert: Dienstag 6. August 2013, 18:59

Guten Abend,
Bin gerade dabei einen kleinen Server für eine Android App zu schreiben, der SQL Querry für sie ausführt und die Ergebnisse zurückgibt.
Jetzt befinden sich aber in der Datenbank Umlaute und diese sollen natürlich auch mit übertragen werden.
Ausgeben über Print ist das auch kein Problem, aber sobald ich die Daten aufbereite kommt der Fehler:
UnicodeEncodeError: 'ascii' codec can't encode character u'\xe4' in position 1: ordinal not in range(128)
Ich bereite die Daten wie folgt für die App auf:

Code: Alles auswählen

c.execute("select * from allgemeine_infos where vorname = %s and nachname = %s order by allgemeine_infos.id", (vorname, nachname,))
db_tmp = c.fetchall()
antwort = ""
for i in db_tmp:
        antwort += str(i["id"]) + ","
        antwort += None2Str(i["vorname"]) + ","
        antwort += None2Str(i["nachname"]) + ","
        antwort += None2Str(i["geschlecht"]) + ","
        antwort += None2Str(i["geburtstag"]) + ","
        antwort += None2Str(i["geburts_jahr"]) + "."
conn.send(antwort)
Leider ist beim kopieren die Formatierung flöten gegangen. Habe versucht sie so gut wie möglich wieder hinzubekommen.
None2Str gibt einfach ein Leerzeichen zurück wenn der Inhalt None ist.

Rufe die Datenbank auch schon mit "charset=''utf8" auf:

Code: Alles auswählen

db = MySQLdb.connect(host='blablabla.de',
                     db='datenbank',
                     user='user',
                     passwd='12345',
                     charset='utf8',
                     cursorclass=MySQLdb.cursors.DictCursor
                     )
Habe es auch schon mit:

Code: Alles auswählen

.decode("UTF-8")
und
.decode("iso-8859-1")
versucht und der Header " # -*- coding: utf-8 -*- " ist natürlich auch vorhanden.
BlackJack

@audacity363: Versuchen reicht nicht, Du musst heraus finden wo die Ausnahme auftritt und verstehen *warum*.

Was denkst Du hat `antwort` in Zeile 11 für einen Wert und Typ, und was *müsste* der Wert dort für einen Typ haben?
Sirius3
User
Beiträge: 17750
Registriert: Sonntag 21. Oktober 2012, 17:20

@audacity363: Warum erfindest Du ein Datenformat, wenn es schon fertige gibt? Was passiert, wenn in einem Feld ein Punkt oder Komma steht?
audacity363
User
Beiträge: 83
Registriert: Dienstag 6. August 2013, 18:59

Sirius3 hat geschrieben:@audacity363: Warum erfindest Du ein Datenformat, wenn es schon fertige gibt? Was passiert, wenn in einem Feld ein Punkt oder Komma steht?
Was meinst du mit erfndest? Fasse doch nur die Ergebniss zusammen und trenne die einzelnen Felder mit "," und ein Ende des Datensatzes wird mit einem "." makiert.
Beim Insert wird aufgepasst, dass soetwas nicht pasiert.
BlackJack hat geschrieben:Was denkst Du hat `antwort` in Zeile 11 für einen Wert und Typ, und was *müsste* der Wert dort für einen Typ haben?
Wert: Es stehen alle gefunden Datenwerte drinnen und jeder Datensatz ist mit einem "." getrennt.
Typ: Str
Sollte: Str
Sirius3
User
Beiträge: 17750
Registriert: Sonntag 21. Oktober 2012, 17:20

Den Typ 'Str' gibt es nicht, und wäre er 'str' gäbe es den Fehler nicht.
Du definierst Dir einen Feldtrenner und ein Datensatzendezeichen. Damit hast Du ein Datenformat erfunden. Und Deine App muß dann das Gegenteil vom Server machen, Datensätze nach Datensatzendezeichen und Felder nach Feldtrenner trennen.
Alles Arbeit, die man nicht hätte, wenn man eine Bibliothek für ein übliches Datenformat verwenden würde.
audacity363
User
Beiträge: 83
Registriert: Dienstag 6. August 2013, 18:59

Sirius3 hat geschrieben:Den Typ 'Str' gibt es nicht, und wäre er 'str' gäbe es den Fehler nicht.
Du definierst Dir einen Feldtrenner und ein Datensatzendezeichen. Damit hast Du ein Datenformat erfunden. Und Deine App muß dann das Gegenteil vom Server machen, Datensätze nach Datensatzendezeichen und Felder nach Feldtrenner trennen.
Alles Arbeit, die man nicht hätte, wenn man eine Bibliothek für ein übliches Datenformat verwenden würde.
Ja sicher das mit dem Trennen war er Plan. Was soll ich denn deiner Meinung nach verwenden?
Sirius3
User
Beiträge: 17750
Registriert: Sonntag 21. Oktober 2012, 17:20

JSON wird gerne genommen, weil es schon in der Standardbibliothek integriert ist:

Code: Alles auswählen

c.execute("select * from allgemeine_infos where vorname = %s and nachname = %s order by allgemeine_infos.id", (vorname, nachname,))
conn.sendall(json.dumps(c.fetchall()))
BlackJack

@audacity363: Tja, muss und sollte sind falsch geraten. In welcher Weise falsch hängt davon ab ob Du Python 2 oder 3 einsetzt. Wenn es 2 ist hast Du `unicode` und solltest `str` haben, und bei 3 hast Du `str` und solltest `bytes` haben.
audacity363
User
Beiträge: 83
Registriert: Dienstag 6. August 2013, 18:59

@Sirius3
Danke er überträgt es nun, nur kann Java nichts mit dem Tuple von Python anfangen. Für Java ist es nun ein plain String.

@BlackJack
Na ja okey aber soweit komme ich ja Nichtmal. Das Problem ist ja weiter oben.
Sirius3
User
Beiträge: 17750
Registriert: Sonntag 21. Oktober 2012, 17:20

@audacity363: das Problem ist genau die `send`-Zeile, denn dort mußt Du festlegen, wie Zeichen übertragen werden.

Auch für Java gibt es Pakete, die JSON dekodieren können: JSONTokener
Benutzeravatar
Hyperion
Moderator
Beiträge: 7478
Registriert: Freitag 4. August 2006, 14:56
Wohnort: Hamburg
Kontaktdaten:

Sirius3 hat geschrieben: Auch für Java gibt es Pakete, die JSON dekodieren können: JSONTokener
Gibts auch für XStream :-)
encoding_kapiert = all(verstehen(lesen(info)) for info in (Leonidas Folien, Blog, Folien & Text inkl. Python3, utf-8 everywhere))
assert encoding_kapiert
BlackJack

@audacity363: Wieso ist das Problem weiter oben? Der Traceback sollte von der `send()`-Zeile ausgelöst werden und nicht weiter oben. Ansonsten müsstest Du mal den Quelltext und den kompletten Traceback zeigen.
Antworten