编码导致 "'ascii' 编解码器无法编码字符 … 序号不在范围内(128)

16 投票
3 回答
34476 浏览
提问于 2025-04-15 20:50

我正在做一个Django的RSS阅读器项目,具体内容可以在这里找到。

这个RSS源的内容大概是“俄克拉荷马城(美联社)——詹姆斯·哈登让”。它的编码是“UTF-8”,所以我认为我在下面的代码片段中把utf-8传给了markdown。问题出在那个长破折号上。

我遇到了Django的错误信息:“'ascii' codec can't encode character u'\u2014' in position 109: ordinal not in range(128)”,这是一种Unicode编码错误。在传递的变量中,我看到“俄克拉荷马城(美联社) \u2014 詹姆斯·哈登”。出问题的代码行是:

content = content.encode(parsed_feed.encoding, "xmlcharrefreplace")

我使用的是markdown 2.0,django 1.1和python 2.4。

我需要做什么编码和解码的“魔法”才能让这个正常工作呢?


(这是对Prometheus请求的回应。我同意格式化确实有帮助)

所以在视图中,我在解析的feed编码行上方添加了一行smart_unicode...

content = smart_unicode(content, encoding='utf-8', strings_only=False, errors='strict')
content = content = content.encode(parsed_feed.encoding, "xmlcharrefreplace") 

这把问题推到了我的models.py文件里,我在这里有:

def save(self, force_insert=False, force_update=False): 
     if self.excerpt: 
         self.excerpt_html = markdown(self.excerpt) 
         # super save after this 

如果我把保存方法改成...

def save(self, force_insert=False, force_update=False): 
     if self.excerpt: 
         encoded_excerpt_html = (self.excerpt).encode('utf-8') 
         self.excerpt_html = markdown(encoded_excerpt_html)

我又遇到了错误“'ascii' codec can't decode byte 0xe2 in position 141: ordinal not in range(128)”,因为现在它读取的是“\xe2\x80\x94”,而那个长破折号就是在这里。

3 个回答

0

我在写一个zip文件的时候遇到了这个错误。下面的代码没有成功

ZipFile.write(root+'/%s'%file, newRoot + '/%s'%file)

而下面的代码成功了

ZipFile.write(str(root+'/%s'%file), str(newRoot + '/%s'%file))
14

如果你收到的数据确实是用UTF-8编码的,那么它应该是一串字节,也就是在Python 2.X中称为' str '对象。

你可以用一个断言来验证这一点:

assert isinstance(content, str)

一旦你确认了这一点,就可以进行实际的编码了。Python不支持直接从UTF-8转换到ASCII,比如说。你需要先把这串字节转换成一个Unicode字符串,也就是通过解码来实现:

unicode_content = content.decode('utf-8')

(如果你可以相信parsed_feed.encoding的值,那就用它,而不是直接写'utf-8'。无论如何,都要做好处理错误的准备。)

然后你可以把这个字符串编码成ASCII,并用它们的XML实体替换掉高位字符:

xml_content = unicode_content.encode('ascii', 'xmlcharrefreplace')

所以,完整的方法大概是这样的:

try:
    content = content.decode(parsed_feed.encoding).encode('ascii', 'xmlcharrefreplace')
except UnicodeDecodeError:
    # Couldn't decode the incoming string -- possibly not encoded in utf-8
    # Do something here to report the error

撰写回答