我试图通过python pyodbc调用以下短脚本(这是我的sql文件中的内容):
SELECT distinct ShipmentId, shipmentstatus
FROM log_shipmentstatus
我首先创建了一个通用的sql reader函数:
def sql_reader_single(qry_file, server_name, database):
server = db.connect(str('DRIVER={SQL Server};
SERVER='+server_name+';
DATABASE='+database+';'))
qry = open(qry_file, 'r').read()
data = pd.read_sql(qry, server)
return data
然后我尝试调用上面的函数来读取我的sql脚本:
dir = 'C:/Users/Documents/qry'
QryFile = os.path.join(dir, 'qry clean no comment.sql')
Data = sp.sql_reader_single(qry_file=QryFile, server_name='server1', database='db2')
当我调用read.sql()函数时,我总是会收到以下错误:
pandas.io.sql.DatabaseError: Execution failed on sql 'ÿþS E L E C T d i s t i n c t S h i p m e n t I d , s h i p m e n t s t a t u s
F R O M l o g _ s h i p m e n t s t a t u s
': ('42000', "[42000] [Microsoft][ODBC SQL Server Driver][SQL Server]Incorrect syntax near 'L'. (102) (SQLExecDirectW)")
注意我的查询开头是如何添加两个随机的无字母数字字符。我该怎样摆脱它们?
我已检查过默认的系统编码类型:
print(sys.getdefaultencoding())
我得到了" utf-8"。
从我在谷歌上阅读,我应该使用utf-8。正确?我现在很无能......
答案 0 :(得分:1)
它们不是随机字符。 0xFF 0xFE是UTF16编码数据的byte order mark。这些字节的存在表示文件/流的编码和字节顺序,在这种情况下,它是小端UTF16。字符之间的附加“空格”也是一个提示:这些实际上是NUL字符(0x00),它们已在错误消息中呈现为空格。
解决方案是将SQL脚本文件重新编码为UTF8,ASCII或其他支持的编码。您可以使用转换工具(例如iconv
)对文件本身执行此操作,或者在编辑器中打开文件并将其另存为UTF8。
或者,您可以在代码中处理编码。问题的本质表明您正在使用Python 2:
import codecs
def sql_reader_single(qry_file, encoding='utf16', server_name, database):
server = db.connect(str('DRIVER={SQL Server};
SERVER='+server_name+';
DATABASE='+database+';'))
with codecs.open(qry_file, encoding=encoding) as qf:
data = pd.read_sql(qf.read(), server)