probleme mit script unter windows

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
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

Hallo,

ich habe ein grösseres Problem beim Ausführen von scripts unter Windows.

Ich bin Python-Anfänger, sicher habe ich irgendwas übersehen:

Wenn ich mein script unter linux ausführe funktioniert es.
Wenn ich es unter Windows per Doppelklick ausführe (Endung ist pyw) bricht es ohne Fehlermeldung ab.
Führe ich es unter Win per IDLE aus, läuft es ohne Fehler durch.

Das Problem habe ich bereits bei zwei scripts. Das eine benötigt Tkinter aber das andere aber nicht.

Wie kann ich den Fehler herausfinden?
Danke.
BlackJack

@pPilger: Starte es unter Windows doch mal nicht mit Doppelklick sondern auf der Kommandozeile. Was wird da ausgegeben?
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

BlackJack hat geschrieben:@pPilger: Starte es unter Windows doch mal nicht mit Doppelklick sondern auf der Kommandozeile. Was wird da ausgegeben?
Leider nichts, es folgt ganz normal der neue Promt.

Das script muss eine Datei auf einem versteckten Laufwerk löschen, wenn sie vorhanden ist. Wenn sie da ist, wird sie gelöscht, aber das script arbeitet nicht weiter.

Zur Vollständigkeit hier aber mal meine Löschfunktion:

Code: Alles auswählen

def erase_file( path_filename ):
    print "erase_file: " + path_filename
    try:
        if os.path.isfile( path_filename ):
            os.remove( path_filename )
            print u"Datei gelöscht: " + path_filename
            log_message = u"Datei gelöscht: " + path_filename
            db.write_log_to_db( log_message, "k", "009"  )
        
    except OSError, msg:
        print "erase_file: " + "%r: %s" % ( msg,  path_filename )
        log_message = "erase_file: " + "%r: %s" % ( msg,  path_filename )
        db.write_log_to_db( log_message, "x", "009"  )

    return
    
ms4py
User
Beiträge: 1178
Registriert: Montag 19. Januar 2009, 09:37

Ändere die Endung zu *.py und du bekommst auch eine Ausgabe.
*.pyw-Dateien werden ohne Konsole gestartet und deren stdout und stderr verschwinden deshalb im Nirvana...

Erst wenn eine Anwendung vollständig getestet ist, solltest du die Endung zu *.pyw umstellen und damit die Konsole deaktivieren. Bei einem Programm ohne GUI ist dies aber auf keinen Fall sinnvoll und zu empfehlen!
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

ice2k3 hat geschrieben:Ändere die Endung zu *.py und du bekommst auch eine Ausgabe.
*.pyw-Dateien werden ohne Konsole gestartet und deren stdout und stderr verschwinden deshalb im Nirvana...

Erst wenn eine Anwendung vollständig getestet ist, solltest du die Endung zu *.pyw umstellen und damit die Konsole deaktivieren. Bei einem Programm ohne GUI ist dies aber auf keinen Fall sinnvoll und zu empfehlen!
Danke für den Hinweis.
Ich hab aber wahrscheinlich den Fehler gefunden:
Nachdem ich den Umlaut in dieser Zeile rausgenommen habe geht es, jedenfalls so wie es jetzt aussieht

Code: Alles auswählen

            print u"Datei gelöscht: " + path_filename
ms4py
User
Beiträge: 1178
Registriert: Montag 19. Januar 2009, 09:37

Für Umlaute musst du am Anfang dein Encoding angeben:

Code: Alles auswählen

# coding: ISO-8859-1
# or
# coding: utf-8
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

ice2k3 hat geschrieben:Für Umlaute musst du am Anfang dein Encoding angeben:

Code: Alles auswählen

# coding: ISO-8859-1
# or
# coding: utf-8
Ich hab es in dieser Form:

Code: Alles auswählen

# -*- coding: utf-8 -*-
Ist das nicht korrekt?
ms4py
User
Beiträge: 1178
Registriert: Montag 19. Januar 2009, 09:37

pPilger hat geschrieben:Ich hab es in dieser Form:

Code: Alles auswählen

# -*- coding: utf-8 -*-
Ist das nicht korrekt?
doch, auch ;)

Edit: Dann muss die Datei natürlich auch so kodiert werden.
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

ice2k3 hat geschrieben:
pPilger hat geschrieben:Ich hab es in dieser Form:

Code: Alles auswählen

# -*- coding: utf-8 -*-
Ist das nicht korrekt?
doch, auch ;)

Edit: Dann muss die Datei natürlich auch so kodiert werden.
Wie kann ich feststellen, dass sie so kodiert ist?
Ich benutze ERIC zur Entwicklung.
In der Statusleiste wird mir utf-8 angezeigt.
fhoech
User
Beiträge: 143
Registriert: Montag 9. April 2007, 18:26

Für Umlaute musst du am Anfang dein Encoding angeben:
Ich habe den Verdacht, dass dies in diesem Fall nicht das Problem ist. Sieht mir eher nach einem möglichen UnicodeError bei dem 'print' aus.

@pPilger: Wenn ein Unicode-String per 'print' ausgegeben werden soll, so wird er von Python automatisch encodiert (das benutzte Encoding liefert normalerweise sys.stdout.encoding) - eigentlich eine nützliche Eigenschaft. Es gibt aber ein paar Fallstricke:
1. Python konnte eventuell das Encoding von sys.stdout nicht feststellen. In dem Fall ist sys.stdout.encoding None, und Python fällt auf sys.getdefaultencoding() zurück (normalerweise ASCII). Das ist z.B. dann der Fall, wenn Du ein Skript per pythonw.exe statt python.exe ausführst.
2. Wenn das von Python angenommene Encoding von sys.stdout ein bestimmtes Zeichen nicht darstellen kann, so gibt es einen UnicodeEncodeError. Wenn dieser nicht abgefangen wird, so bricht das Skript ab.

Ein möglicher Workaround besteht darin, alle Unicode-Strings, die per 'print' ausgegeben werden sollen, explizit zu enkodieren und dabei eine nachsichtigere Fehlerbehandung zu wählen, z.B. so:

Code: Alles auswählen

print u'test äöü test'.encode(sys.stdout.encoding or sys.getdefaulencoding(), 'replace')
Dann werden zwar alle nicht darstellbaren Zeichen als Fragezeichen ausgegeben, aber zumindest wirft das 'print' keine Exception mehr. Alle 'print's so umzuwandeln, ist aber recht umständlich und fehleranfällig, falls man mal eins vergisst oder externe Module geändert werden müssten.

Eine andere Lösung, bei der man weniger Arbeit hat, besteht darin, sys.stdout und stderr in einer Klasse zu 'wrappen', die sich automatisch ums Encoding kümmert. Hier ein Vorschlag von mir: http://paste.pocoo.org/show/187372/
Kopiere das verlinkte Skript, und speichere es z.B. als encodedstdio.py
Dann musst Du in Deinem eigenen (Haupt-)Skript nur noch oben einfügen:

Code: Alles auswählen

import encodedstdio
encodedstdio.encodestdio()
...und brauchst Dich bei 'print' weiter nicht mehr ums Encoding kümmern (zumindest solang das Encoding in Deinem Skript stimmt, davon gehe ich jetzt aber mal aus).
(Edit: Paste verbessert)
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

fhoech hat geschrieben:
Für Umlaute musst du am Anfang dein Encoding angeben:
Ich habe den Verdacht, dass dies in diesem Fall nicht das Problem ist. Sieht mir eher nach einem möglichen UnicodeError bei dem 'print' aus.

Dann musst Du in Deinem eigenen (Haupt-)Skript nur noch oben einfügen:

Code: Alles auswählen

import encodedstdio
encodedstdio.encodestdio()
...und brauchst Dich bei 'print' weiter nicht mehr ums Encoding kümmern (zumindest solang das Encoding in Deinem Skript stimmt, davon gehe ich jetzt aber mal aus).
Da ich mich schon etwas mit dem Unicodeerror beim Austausch von Daten aus verschieden codierten Datenbanken beschäftigen "durfte" erscheint mir Dein Ansatz richtig und hilfreich.

Ich habe das Script eingebunden, und es genügt nach dem import auch nur einmal die Zeile?:

Code: Alles auswählen

encodedstdio.encodestdio()
Ich erhalte dann folgende Meldung:

Code: Alles auswählen

Das untersuchte Programm erzeugte die Ausnahme unhandled AttributeError
"'AsyncFile' object has no attribute 'encoding'"
Sicher muss ich das irgendwie anders machen, z.B. die funktion an das print dranhängen?
Danke für die Hilfe.
fhoech
User
Beiträge: 143
Registriert: Montag 9. April 2007, 18:26

Ich glaube, es liegt an Eric, da es sich in sys.stdout einklinkt. Wenn Du Dein Skript normal über python.exe ausführst, sollte es klappen.
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

fhoech hat geschrieben:Ich glaube, es liegt an Eric, da es sich in sys.stdout einklinkt. Wenn Du Dein Skript normal über python.exe ausführst, sollte es klappen.
Ich entwickle unter Linux.
Wenn ich das Script unter Linux ohne ERIC starte läuft es gar nicht.
Unter WinXP geht es mit pythonw.exe.

Was für ein Problem könte es da unter Linux (Ubuntu) geben?

Danke
ms4py
User
Beiträge: 1178
Registriert: Montag 19. Januar 2009, 09:37

pPilger hat geschrieben:Was für ein Problem könte es da unter Linux (Ubuntu) geben?
Meine Kristallkugel hat *ausnahmsweise* keine Fehlermeldung ausgegeben, vielleicht willst du sie uns ja dann sagen...
pPilger
User
Beiträge: 45
Registriert: Montag 8. Februar 2010, 17:30

ms4py hat geschrieben:
pPilger hat geschrieben:Was für ein Problem könte es da unter Linux (Ubuntu) geben?
Meine Kristallkugel hat *ausnahmsweise* keine Fehlermeldung ausgegeben, vielleicht willst du sie uns ja dann sagen...
Also ich hab mal den code reduziert:
http://paste.pocoo.org/show/193893/

Das Problem ist halt, dass es unter WinXP beim Start über IDLE und als py-script problemlos tagelang läuft. Nur wenn ich es als pyw ausführe bleibt es nach dem 4. bis 22. Durchlauf einfach stehen, keine Fehlermeldung, es lässt sich auch problemlos beenden.
Test-Haltepunkte haben mir bisher keine eindeutig fehlerhafte Zeile geliefert.

Vielleicht kann sich mal jemand des Problems annehmen, danke.
Benutzeravatar
mkesper
User
Beiträge: 919
Registriert: Montag 20. November 2006, 15:48
Wohnort: formerly known as mkallas
Kontaktdaten:

pPilger hat geschrieben:Vielleicht kann sich mal jemand des Problems annehmen, danke.
Klar, wenn du jemanden für deine Fehlersuche bezahlst, wird das so funktionieren.
Antworten