Python3.0, CGI und der leidige UnicodeDecoreError

Sockets, TCP/IP, (XML-)RPC und ähnliche Themen gehören in dieses Forum
Antworten
kunatz
User
Beiträge: 5
Registriert: Freitag 20. Februar 2009, 14:22
Kontaktdaten:

Hallo,

ich versuche ein einfaches CGI Script zum Laufen zu bekommen, das einen Dateiupload handelt. Solange die Datei nix binäres ist, klappt das auch wunderbar. Wenn doch bekomme ich einen UnicodeDecodeError - klar, da Python3.0 den Datenstrom als Unicode behandelt.

Das ist das Script:

Code: Alles auswählen

#!/usr/bin/python3.0
import cgi, os
import cgitb; cgitb.enable()

form = cgi.FieldStorage()

# Generator to buffer file chunks
def fbuffer(f, chunk_size=10000):
   while True:
      chunk = f.read(chunk_size)
      if not chunk: break
      yield chunk
   
# A nested FieldStorage instance holds the file
fileitem = form['file']

# Test if the file was uploaded
if fileitem.filename:
   # strip leading path from file name to avoid directory traversal attacks
   fn = os.path.basename(fileitem.filename)
   with open('/tmp/' + fn, 'wb', 10000) as f:
      # Read the file in chunks
      for chunk in fbuffer(fileitem.file):
         f.write(chunk)

print('Content-Type: text/html')
print()
print("""
<html>
   <body>
      <p>{0} erforglreich hochgeladen!</p>
   </body>
</html>
""".format(fileitem.filename))
Ich vermutete das Problem in der Klasse cgi.FieldStorage(), also habe ich probiert direkt aus sys.stdin zu lesen. Aber natürlich klappt auch das nicht.

Nun meine Frage: Wie teile ich dem Interpreter mit, dass das was da kommt binär ist, und einfach bit für bit in eine Datei geschrieben werden soll? Wie würdet ihr dieses Problem lösen (und habt ihr Beispielcode zur Hand)?

Noch ein Hinweis: Ich bin kein Programmierer, und das was ich hier mache ist nur ein kleiner Test. Um mich in WSGI und ein Framework einzuarbeiten fehlt mir im Moment die Zeit, und ist für diesen Zweck wohl auch ein wenig Overkill.

Danke im Voraus für eure Antworten!
In a world without walls and fences, who needs Windows and Gates?
sma
User
Beiträge: 3018
Registriert: Montag 19. November 2007, 19:57
Wohnort: Kiel

Eine Minute gegoogelt und http://bugs.python.org/issue4953 gefunden. Sieht so aus, als wäre das in Python 3.0 kaputt.

Werden die ja hoffentlich reparieren, denn prinzipiell sollte es keine Probleme geben. Es ist mit nichten klar, dass Python den Datenstrom als Unicode behandelt, denn HTTP überträgt nur Bytes, keine Zeichen. Erst das ebenfalls übertragene Encoding sagt, wie die Bytes zu interpretieren sind.

Stefan
kunatz
User
Beiträge: 5
Registriert: Freitag 20. Februar 2009, 14:22
Kontaktdaten:

Danke für deine Antwort. Ich bin absoluter Anfänger in Python, und bin keinen einzigen Moment auf die Idee gekommen, dass es ein Bug sein könnte, sondern hab den Fehler die ganze Zeit bei mir gesucht ... nun bin ich wirklich erleichtert.
In a world without walls and fences, who needs Windows and Gates?
sma
User
Beiträge: 3018
Registriert: Montag 19. November 2007, 19:57
Wohnort: Kiel

Wenn du mit Python und Webprogrammierung anfangen willst, würde ich dir empfehlen, Python 2.x zu benutzen. Für 3.0 hat fast keiner Interesse, die notwendigen Bibliotheken zu portieren. Bis auf einfacheren Unicode-Support bietet 3.0 keine so gravierenden Vorteile.

Und wenn es ein bisschen mehr sein soll, als ein 20-Zeiler, würde ich ein ausgereiftes Webrahmenwerk empfehlen, damit du dich um solche low-level-Details wie das richtige Encoding von Eingabedateien nicht kümmern musst. Ich mag Django und habe die Erfahrung gemacht, dass Anfänger damit schnell loslegen können.

Stefan
Antworten