Como dice Mike, puede obtener la página de códigos del sistema en getfilesystemencoding
. Esta codificación se usa para convertir las cadenas Unicode nativas de Windows en bytes para todas las funciones de C stdio utilizadas por Python, incluidas las llamadas al sistema de archivos que usan rutas de archivos de cadena de bytes, y os.environ
.
Lo que esto significa es que usted podrá leer una cadena con caracteres que no sean ASCII desde os.environ
y utilizarla directamente como ruta de archivo sin ningún paso especial de codificación/decodificación.
Por desgracia, si la variable %APPDATA%
contiene caracteres Unicode que no están presentes en la página de códigos del sistema - por ejemplo, si en un alemán (CP1252) de instalación de Windows, su camino era C:\Documents and Settings\αβγ\Application Data
- entonces ya se habrán destrozado esos caracteres antes tener la oportunidad de usarlos La decodificación de la cadena de bytes que llega a Unicode usando el sistema de archivos no ayudará en ese caso.
Aquí hay una función que puede usar en las versiones recientes de Python que tienen la extensión ctypes
, para leer las variables de entorno Unicode nativas de Windows.
def getEnvironmentVariable(name):
name= unicode(name) # make sure string argument is unicode
n= ctypes.windll.kernel32.GetEnvironmentVariableW(name, None, 0)
if n==0:
return None
buf= ctypes.create_unicode_buffer(u'\0'*n)
ctypes.windll.kernel32.GetEnvironmentVariableW(name, buf, n)
return buf.value
En Python 3, el diccionario contiene os.environ
cadenas Unicode tomadas directamente desde Windows sin codificación de página de códigos, por lo que no tiene que preocuparse por este problema existe.
Hola, gracias bobince por su respuesta. De esta forma obtengo la ruta correcta de Appdata, pero no resuelve el problema con las diéresis. No puedo encontrar una manera de decodificar la cadena Unicode de buf.value de una manera correcta. – Heike
'buf.value' ya es una cadena Unicode. No es necesario decodificarlo. Puede usar cadenas Unicode directamente como nombres de archivo en Windows en Python 2.3 en adelante (PEP277). – bobince
pero os.path.exist (buf.value) devuelve falso ... si lo intento con un nombre sin diéresis está funcionando – Heike