Поднимите UnicodeEncodeError в logging.StreamHandler - PullRequest
0 голосов
/ 07 ноября 2019

Я перенес свой код Python с хоста Win10 на WS2012R2. Удивительно, но он перестает работать правильно и теперь показывает предупреждающее сообщение: «UnicodeEncodeError: кодек« charmap »не может кодировать символы в позиции 0-2: символы отображаются на»

Я пытался выполнить команду:

set PYTHONLEGACYWINDOWSSTDIO=yes

Мой код:

import logging
import sys

def get_console_handler():
    console_handler = logging.StreamHandler(sys.stdout)
    return console_handler


def get_logger():
    logger = logging.getLogger()
    logger.setLevel(logging.DEBUG)
    logger.addHandler(get_console_handler())
    return logger


my_logger = get_logger()
my_logger.debug("Это отладочное сообщение".encode("cp1252"))

Что мне сделать, чтобы избавиться от этого предупреждения?

Обновление КоллегиПрошу прощения, что ввел вас в заблуждение! Я, очевидно, устал после долгих часов отслеживания ошибок) Проблема не связана с вызовом "* .encode ()" как таковым, она связана с кодировкой python по умолчанию во время работы консоли IO (я так полагаю)! Исходный код делает некоторые запросы из БД в кодировке cp1251, но проблема возникает, когда python пытается преобразовать его в cp1252.

Вот еще один пример того, как вызвать ошибку.

  1. Создайте простой текстовый файл, т.е. test.txt с текстом «Это отладочное сообщение» и сохраните его cp1252.
  2. Запустите консоль Python и введите: f = open("test.txt") f.read()

Вывод:

f = open("test.txt")
f.read()
Traceback (most recent call last):   File "<stdin>", line 1, in <module>
File "c:\project\venv\lib\encodings\cp1252.py", line 23, in decode return codecs.charmap_decode(input,self.errors,decoding_table)[0]
UnicodeDecodeError: 'charmap' codec can't decode byte 0x81 in position 29: character maps to <undefined>

Ответы [ 3 ]

2 голосов
/ 08 ноября 2019

Проблема в том, как logging.StreamHandler выполняет вывод на консоль, а именно из-за того, что вы не можете изменить кодировку по умолчанию в отличие от FileHandler. Если системная кодировка по умолчанию не соответствует необходимой, вы можете столкнуться с проблемой.

Для моего примера. Я хотел вывести строки cp1251, в то время как системная кодировка по умолчанию была:

import locale
locale.getpreferredencoding()

'cp1252'

Этот вопрос был решен путем изменения языкового стандарта системы (см. https://stackoverflow.com/a/11234956/9851754). Выберите «Изменить системный язык ...» для программ, не поддерживающих Юникод. Никаких изменений кода не требуется.

import locale
locale.getpreferredencoding()

'cp1251'

0 голосов
/ 07 ноября 2019

Я проверил ваш код с Python 3.6.8, и он работал для меня (я ничего не менял).

Python 3.6.8:

>>> python3 -V
Python 3.6.8
>>> python3 test.py 
Это отладочное сообщение

Но когда я проверил его с Python 2.7.15+, я получил ошибку, похожую на вас.

Python 2.7.15+ с вашей реализацией:

>>> python2 -V
Python 2.7.15+
>>> python2 test.py 
  File "test.py", line 17
SyntaxError: Non-ASCII character '\xd0' in file test.py on line 17, but no encoding declared; see http://python.org/dev/peps/pep-0263/ for details

Затем я поместил следующую строку в первую строку, где он работал для меня.

Запрос кода:

# -*- coding: utf-8 -*-
import logging
import sys
...

Выход с Python 2.7.15+ и с измененным кодом:

>>> python2 -V
Python 2.7.15+
>>> python2 test.py 
Это отладочное сообщение
0 голосов
/ 07 ноября 2019

Использовать кодирование ("utf-8"). Вот список кодировок Python: https://docs.python.org/2.4/lib/standard-encodings.html

my_logger.debug("Это отладочное сообщение".encode("utf-8"))

, затем используйте .decode ("utf-8"), чтобы увидеть значение для печати вашей строки

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...