Pandas读取含非UTF-8字符CSV存入MongoDB的报错与解决需求
解决CSV非UTF-8字符解码错误及MongoDB存储问题
问题场景
使用以下Python代码读取Google Cloud Storage中的CSV文件并写入MongoDB时,因CSV包含非UTF-8字符触发解码错误:
bucket_name = "my-bucket" file_name = "input.csv" csv_data = pd.DataFrame(pd.read_csv('gs://' + bucket_name + '/' + file_name, encoding='utf-8')) csv_data = csv_data.to_dict(orient="records") db.task.insert_many(csv_data)
CSV文件内容:
ID,Name,Identity,Alignment,EyeColor,HairColor,Gender,Status,Appearances,FirstAppearance,Year,Universe 100001,Claude Potier (Earth-616),Secret,Neutral,Hazel,Brown,Male,Living,2,àå÷-00,2000,DC 100002,Elektra Natchios (Earth-616),Secret,Neutral,Blue,Black,Female,Living,280,éðå-81,1981,Marvel 100003,Thomas Williams (Earth-616),Secret,Neutral,Black,,Male,Living,1,àåâ-02,2002,DC 100004,Mogul (Earth-616),,,,Bald,,Living,,îàé-70,1970,DC
触发的错误:
File "pandas/_libs/parsers.pyx", line 1499, in pandas._libs.parsers._string_box_utf8
UnicodeDecodeError: 'utf-8' codec can't decode byte 0xe0 in position 0: invalid continuation byte
需求
- 将无效字符替换为“invalid”后继续处理并存入MongoDB;
- 是否可以将这些字符原样存入数据库?
解决方案
需求1:替换无效字符为"invalid"
通过先读取GCS文件内容、处理编码错误后再交给pandas解析的方式实现:
from google.cloud import storage import pandas as pd from io import StringIO # 初始化GCS客户端并获取文件 storage_client = storage.Client() bucket = storage_client.bucket("my-bucket") blob = bucket.blob("input.csv") # 读取文件时将无效UTF-8字符替换为Unicode替换符,再替换成指定字符串 content = blob.download_as_text(encoding='utf-8', errors='replace').replace('\ufffd', 'invalid') # 解析处理后的内容并写入MongoDB csv_data = pd.read_csv(StringIO(content)) csv_data = csv_data.to_dict(orient="records") db.task.insert_many(csv_data)
需求2:原样存入数据库
可以实现,但需先确定CSV文件的实际编码(如latin-1、cp1252等单字节编码):
步骤1:确认文件实际编码
# 读取原始字节并尝试用latin-1解码(兼容所有字节) raw_content = blob.download_as_bytes() test_content = raw_content.decode('latin-1') print(test_content)
如果输出字符与原文件一致,说明编码为latin-1或兼容编码。
步骤2:用正确编码读取并写入
# 用实际编码读取文件 content = blob.download_as_text(encoding='latin-1') csv_data = pd.read_csv(StringIO(content)) # 直接转换为字典写入MongoDB,字符会被原样保留 csv_data = csv_data.to_dict(orient="records") db.task.insert_many(csv_data)
解释:用对应编码读取后,pandas会将字符转为Unicode字符串,MongoDB支持存储这类UTF-8格式的字符串,不会出现乱码或丢失。
内容的提问来源于stack exchange,提问作者bionics parv
相关产品推荐
相关产品推荐

