Ich habe eine Flask-Anwendung (Linux, Apache mit mod_wsgi, Python 3), die ein Shell-Skript mit einigen Argumenten aufruft. Wenn es irgendwelche Nicht-ASCII-Zeichen in den subprocess.run()
Befehlsargumente sind, Fehler folgende tritt in der Anwendung:subprocess.run() Argument Codierung
'ascii' codec can't encode characters in position 5-6: ordinal not in range(128)
ich viel Zeit damit verbracht, es zu beheben.
Kein solches Problem existiert in der Befehlszeile, nur in der Anwendung.
Die gesamte Anwendung Ausgabe ist in Unicode und es gibt keine Probleme damit. Nach einigen Recherchen kam ich zu dem Schluss, dass das Problem mit der "Dateisystem-Codierung" zu tun hat.
Ich habe einige Protokollanweisungen zu meinem run.wsgi
Skript hinzugefügt. Die FS-Codierung war tatsächlich 'ascii' (und 'utf-8' in der Befehlszeile).
Im nächsten Schritt fand ich diesen Artikel How to change file system encoding via python?
Der Server Apache wurde mit LANG=C
in seiner Umgebung gestartet. Ich habe es zu C.UTF-8
trotz Warnungen in /etc/sysconfig/httpd
geändert. Das half nicht, die FS-Codierung war immer noch 'ascii'. Ich habe dann sogar die sys.getfilesystemencoding()
zu lambda: 'utf-8'
monkey-gepatcht. Aber der Fehler ist immer noch da.
Ich habe den httpd-Dienst nach jeder Änderung ordnungsgemäß neu gestartet.
Ich bin am Ende meines Wissens.
- Ist mein Problem wirklich durch die FS-Codierung verursacht?
- Wenn ja, warum sind meine Versuche, es in utf-8 zu ändern, fehlgeschlagen?
- Am wichtigsten: Wie kann ich dieses Problem lösen?
UPDATE1:
Code-Schnipsel:
import subprocess as sub
cmdresult = sub.run(
[SCRIPT, tid, days, name],
stdin=sub.DEVNULL, stdout=sub.PIPE, stderr=sub.DEVNULL,
encoding='ascii', # 'utf-8' will not help, this affects stdin, stdout I/O only
check=True)
Rufen Sie mit 'shell = True' auf oder nicht? Übergeben Sie Argumente wie eine Zeichenfolge oder eine Liste? Bitte zeigen Sie den tatsächlichen Code, der das 'subprocess' Modul verwendet. –
Auf OS-Ebene ist es 'exec()' und Freunden egal, welche Kodierung Sie für die Argumente verwenden, die Sie an einen Unterprozess übergeben: POSIX erfordert nur, dass sie als C 'char *' - Zeichenfolge dargestellt werden können zum Subprozess, um sie zu dekodieren. –
@DanielPryden Code angehängt, 'shell = False' standardmäßig. – VPfB