Seite 1 von 1

Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 06:36
von plip
Servus,

ich versuche gerade nach einem Beispiel aus dem Netz einen File-Upload per
Python-CGI zu implementieren (momentan noch lokal). Der Transfer läuft durch und das Script
meldet einen erfolgreichen Upload - nur leider sind die Files (z.B.
jpeg-Bilder) danach viel kleiner und lassen sich nicht öffnen.

Server:

Code: Alles auswählen

import http.server
PORT = 8080
handler = http.server.CGIHTTPRequestHandler
httpd = http.server.HTTPServer(("", PORT), handler)
print("serving at port", PORT)
httpd.serve_forever()
Upload-Form:

Code: Alles auswählen

<div>
<form enctype="multipart/form-data" action="cgi-bin/upload.py" method="post">
    <p>File: <input type="file" name="file"></p>
      <input type="submit" value=" Start Upload ">
</form>
<div>
CGI:

Code: Alles auswählen

#!C:\Python33\python.exe 
#!/usr/bin/env python
import cgi, os
import cgitb; cgitb.enable()

try: # Windows needs stdio set for binary mode.
    import msvcrt
    msvcrt.setmode (0, os.O_BINARY) # stdin  = 0
    msvcrt.setmode (1, os.O_BINARY) # stdout = 1
except ImportError:
    pass

form = cgi.FieldStorage()

# A nested FieldStorage instance holds the file
fileitem = form['file']

# Test if the file was uploaded
if fileitem.filename:
   try:
      fn = os.path.basename(fileitem.filename)
      oFile = open('files\\' + fn, 'wb')
      data = fileitem.value
      oFile.write(data)
      oFile.close()
      message = '\nThe file "' + fn + '" was uploaded successfully'
   except Exception as e:
      message = 'Error wrting file "' + fn +'" : ' + str(e)   
else:
   message = 'No file was uploaded'
   
print("""\
Content-Type: text/html\n
<html><body>
<p>%s</p>
</body></html>
""" % (message,))
Schon der Aufruf

Code: Alles auswählen

fileitem.file.read()
liefert einen String, der viel kleiner ist als die Datei (etwa 40K von 3M, Größe jedes Mal ein bisschen anders).
Hat jemand eine Idee?

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 17:45
von Rigoletto
Passiert da bei allen Filetypen, text und binär?
Was ist wenn die Datei nur 10kb hat, fehlt dann auch was?

Ich glaub bei post ist die upload größe auf max. 32 oder 64 kb beschränkt und du musst auf get wecchseln.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 17:57
von /me
Rigoletto hat geschrieben:Ich glaub bei post ist die upload größe auf max. 32 oder 64 kb beschränkt und du musst auf get wecchseln.
Die erlaubte Größe ist nur durch den Server beschränkt und nicht durch die HTTP-Spezifikation.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 18:07
von Rigoletto
Die erlaubte Größe ist nur durch den Server beschränkt und nicht durch die HTTP-Spezifikation.
Richtig, aber bei "POST" afaik schiebt der Browser die Daten über die URL an den Server, und die browser haben da eine Größenbegrenzung.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 18:10
von Rigoletto
Aber probier mal die Größe manuell hochzusetzen:

Code: Alles auswählen

<input type="hidden" name="MAX_FILE_SIZE" value="1024000" />

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 19:09
von BlackJack
@Rigoletto: Bei POST sind die Daten gerade *nicht* in der URL kodiert. Und dieser <input>-Hack dürfte nicht funktionieren, das wäre nämlich eine Lücke die kein vernünftiger Admin zulassen würde das der Client einfach so Beschränkungen aushebeln kann die der Admin vorgibt.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 19:49
von Rigoletto
BlackJack hat geschrieben:@Rigoletto: Bei POST sind die Daten gerade *nicht* in der URL kodiert. Und dieser <input>-Hack dürfte nicht funktionieren, das wäre nämlich eine Lücke die kein vernünftiger Admin zulassen würde das der Client einfach so Beschränkungen aushebeln kann die der Admin vorgibt.
Ja, stimmt, POST codiert nicht in der url, sofern nutzt er richtig POST.
Aber das <input> ist kein hack sondern der Browser verhindert von vornherein das ich 10MByte Daten uploade wenn der Server auf 5MByte begrenzt ist, und ich das in der html angebe. Sonst lade ich umsonst 5MByte hoch und bekomme erst dann den abbruch vom server. Den Server interessiert die angabe nicht, nur den browser.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 21:02
von BlackJack
@Rigoletto: Das ist eine PHP-Umgebungsvariable, also für den Server, und das funktioniert nur wenn die Felddaten einfach so in die Umgebung übernommen werden, was eine Sicherheitslücke ist und deshalb von keinem ernstzunehmenden Admin mehr erlaubt wird. Das ist also komplett sinnfrei denn bei Python über CGI hat das gar keinen Effekt.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Montag 17. Februar 2014, 22:53
von plip
Ich hab jetzt mal ein 660K großes xml-File probiert. Angekommen sind 43K, die sind aber Ordnung...
Kann das eventuell auch mit dem Python-Server/Handler zusammenhängen. Hab schon überlegt es probehalber mal mit P2 statt P3 zu versuchen, weil die Beispiele alle in P2-Syntax waren. Oder ich versuchs mal auf meinem Raspberry-Pi mit lighttpd...

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Dienstag 18. Februar 2014, 06:17
von plip
Mit dem RPI funktionierts. Außerdem ist die Übertragung viel schneller als beim localhost, was etwas seltsam ist, oder?

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Dienstag 18. Februar 2014, 06:35
von Rigoletto
BlackJack hat geschrieben:@Rigoletto: Das ist eine PHP-Umgebungsvariable, also für den Server, und das funktioniert nur wenn die Felddaten einfach so in die Umgebung übernommen werden, was eine Sicherheitslücke ist und deshalb von keinem ernstzunehmenden Admin mehr erlaubt wird. Das ist also komplett sinnfrei denn bei Python über CGI hat das gar keinen Effekt.
Nicht nur, der Browser hat auch angaben die er verifiziert: http://www.tizag.com/htmlT/htmlupload.php

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Dienstag 18. Februar 2014, 08:02
von BlackJack
@Rigoletto: Das ist Unsinn, dem Browser ist dieses Feld vollkommen egal ausser das er es zum Server überträgt, und dort ist es wie gesagt, wenn überhaupt auch nur für PHP von Interesse. Entgegen der Angabe auf der Webseite ist die Angabe auch in Bytes und nicht in Kilobytes.

Diese Falschinformation scheint von der PHP-Dokumentation in die Netzwelt gesetzt worden zu sein. Hier der entsprechende Bug-Report: https://bugs.php.net/bug.php?id=40387

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Dienstag 18. Februar 2014, 08:14
von Rigoletto
BlackJack hat geschrieben:@Rigoletto: Das ist Unsinn, dem Browser ist dieses Feld vollkommen egal ausser das er es zum Server überträgt, und dort ist es wie gesagt, wenn überhaupt auch nur für PHP von Interesse. Entgegen der Angabe auf der Webseite ist die Angabe auch in Bytes und nicht in Kilobytes.

Diese Falschinformation scheint von der PHP-Dokumentation in die Netzwelt gesetzt worden zu sein. Hier der entsprechende Bug-Report: https://bugs.php.net/bug.php?id=40387
Hier nochmal in deutsch: http://de.selfhtml.org/html/formulare/d ... definieren
Und ich kann selber sagen das diese Angabe funktioniert, da selbst benutzt. Das hat mit PHP auch nichts zu tun, der Browser checkt das Feld genauso wie eine size-angabe bei einem normalem Texteingabefeld.

added: Ok, es ist nicht der Browser der es checkt sondern javascript.

Re: Html Upload mit Python-CGI - korrupte files

Verfasst: Dienstag 18. Februar 2014, 08:35
von BlackJack
@Rigoletto: Das steht ja auch ganz deutlich in dem von Dir verlinkten Abschnitt bei Erläuterungen, zweiter Absatz:
http://de.selfhtml.org/html/formulare/datei_upload.htm#definieren hat geschrieben:Das Attribut maxlength wurde in HTML 3.2 definiert als Hinweis an den Browser, nur Dateien bis zu einer Bytegröße dieser Angabe zur Auswahl zuzulassen. In HTML 4.01 wird auf diese Funktion nicht mehr eingegangen. Uns ist auch kein Browser bekannt, der diese Angabe in irgendeiner Weise einschränkend umsetzt.
Ausserdem bist Du hier mal eben so von einem <input>-Feld mit einem bestimmten Namen zu einem Attribut im Datei-<input>-Feld mit einem anderen Wert gesprungen.