求助:Linux下使用Pyodbc插入数据到MSSQL中文乱码

samsample 2016-01-10 09:24:08
先说ENV:
1. docker下: centos6.7-X64-minimal-en 和 直接虚拟机下: centos6.7-X64-minimal-cn 两个环境下均一样现象
2. 驱动接口 unixODBC2.2.14、FreeTDS-0.9.1
3. python-2.7
4. pyodbc-3.0.10
5. locale:en_US.UTF-8、zh_CN.UTF-8、zh_CN.GBK、zh_CN.GB18030、zh_CN.GB2312 全部试过
6. SQL Server 2008、SQL Server 2008 R2, 两种数据库均一样
7. 库排序规则:Chinese_PRC_CI_AS
8. 表字段 nvarchar 和 varchar 均试过


现象:
在CentOS下使用 pyodbc 通过 freetds 连接 MSSQL ,select 出来的内容 没有问题,是unicode字符,使用decode转换一下就是中文了。使用FreeTDS 自带的 tsql ,select 和 insert 结果都是正常显示中文,但是使用pyodbc,无论是直接在python命令行下,还是运行py脚步文件,insert都一定是乱码。
windows下无论怎么搞,只要符合unicode的规则,那么就能插入中文,没有任何问题,相同的源码,到centos下就不管用了。

配置及源码如下:
FreeTDS:
/usr/local/freetds0.91/etc/freetds.conf

……
[TestDB]
host = 10.0.0.100
port = 1433
tds version = 8.0
client charset = UTF-8 #这一行 试过三种情况:1. 去掉;2.UTF-8;3.GBK;结果一样


unixODBC:
/etc/odbcinst.ini

……
[SQL Server]
Description = FreeTDS ODBC driver for MSSQL
Driver = /usr/local/freetds0.91/lib/libtdsodbc.so
Setup = /usr/lib64/libtdsS.so
FileUsage = 1


SQL Server 字段:

CREATE TABLE t(NAME NVARCHAR(100))
CREATE TABLE t2(NAME VARCHAR(100))


Python脚本:
(罗嗦一句:脚本文件采用UTF-8进行报错,尝试使用iconv转换成GBK、GB18030没用,因为是使用SecureCRT cat > 进去的,所以尝试vi进去直接输入中文,执行,也是各种乱码;也尝试过更改CRT的字符编码为default、UTF-8、GB18030等,英文locale没法输入中文,中文的locale下只有对应字符编码才能输入中文,否则乱码没商量)

#-*- coding:UTF-8 -*-

import pyodbc
DBCONNECTSTR = 'DRIVER={SQL Server};SERVER=10.0.0.100;port=1433;DATABASE=TESTDB;UID=TESTDB;PWD=TESTDB;TDS_Version=8.0;' #连接串尝试过加上charset="utf-8",没有区别
conn=pyodbc.connect(DBCONNECTSTR)
#备注一下,以下18种情况均试过,实际代码没有最开头的数字和空格,#注释保留
# t 表和 t2 表均插入相同的内容试过,没有区别
1 conn.execute("insert into t values('%s')" % '测试') #命令行下:均可执行,均正常。脚本执行:均可执行,window乱码;CentOS正常
2 conn.execute("insert into t values('%s')" % '测试'.decode('utf-8')) #命令行下:windows报错;CentOS可执行。脚本执行:可执行,均正常
3 #conn.execute("insert into t values('%s')" % '测试'.encode('utf-8')) #命令行下:均报错。脚本执行:同命令行
4 conn.execute("insert into t values('%s')" % u'测试')
5 #conn.execute("insert into t values('%s')" % u'测试'.decode('utf-8')) #命令行下:均报错。脚本执行:均报错
6 conn.execute("insert into t values('%s')" % u'测试'.encode('utf-8')) #命令行下:均可执行,但是windows乱码;CentOS正常。脚本执行:同命令行

7 conn.execute("insert into t values('%s')" % '\u6d4b\u8bd5') #命令行下:均可执行,但其实均是一个字符串,实际结果为:'\\u6d4b\\u8bd5'
8 conn.execute("insert into t values('%s')" % '\u6d4b\u8bd5'.decode('utf-8')) #同7,因为decode针对的是字母和数字及\,结果肯定一样
9 conn.execute("insert into t values('%s')" % '\u6d4b\u8bd5'.encode('utf-8')) #同7
10 conn.execute("insert into t values('%s')" % u'\u6d4b\u8bd5')
11 #conn.execute("insert into t values('%s')" % u'\u6d4b\u8bd5'.decode('utf-8')) #同5
12 conn.execute("insert into t values('%s')" % u'\u6d4b\u8bd5'.encode('utf-8')) #同6

13 conn.execute("insert into t values('%s')" % '\xb2\xe2\xca\xd4') #命令行下:均可执行,windows下正常;CentOS下为不可见字符。脚本执行:同命令行
14 #conn.execute("insert into t values('%s')" % '\xb2\xe2\xca\xd4'.decode('utf-8')) #命令行下:均报错。脚本执行:同命令行
15 #conn.execute("insert into t values('%s')" % '\xb2\xe2\xca\xd4'.encode('utf-8')) #同3
16 #conn.execute("insert into t values('%s')" % u'\xb2\xe2\xca\xd4') #命令行下:windows下报错;CentOS下可执行但乱码。脚本执行:
17 #conn.execute("insert into t values('%s')" % u'\xb2\xe2\xca\xd4'.decode('utf-8')) #同5
18 conn.execute("insert into t values('%s')" % u'\xb2\xe2\xca\xd4'.encode('utf-8')) #命令行下:均可执行,但都是乱码。脚本执行:同命令行
conn.commit()
conn.close()


脚本的执行结果:
windows中:

2、4、10、13都insert了“测试”这两个字
CentOS中:

无论何时都不能insert中文

我真的要哭了,求帮助。
题外话:
其实我是用Django搭建web,站点的代码在windows下全部写好了,也能运行,没有中文神马的问题从来没有出现。
但是上两周开始想用docker部署,却发现运行时没有问题,通用的代码,但是当我要写入东西到数据库的时候,就悲剧了。
各位有过linux底下部署Django应用连接SQL Server的经验吗?求救。
...全文
593 4 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
samwang84 2016-02-13
  • 打赏
  • 举报
回复
嗯,其实解决方法很简单,就是使用pyodbc的问号表达式代替就行了。
samsample 2016-01-19
  • 打赏
  • 举报
回复
该问题已经自行解决了。 解决办法看我的博文: 解决使用Pyodbc向MSSQL插入unicode字符乱码的问题
pcboyxhy 2016-01-11
  • 打赏
  • 举报
回复
我是在linux下开发的,文件和字符串都是UTF-8,没乱码,不过不知道在windows下运行会不会乱码
samsample 2016-01-11
  • 打赏
  • 举报
回复
引用 1 楼 pcboyxhy的回复:
我是在linux下开发的,文件和字符串都是UTF-8,没乱码,不过不知道在windows下运行会不会乱码
你意思是在linux下直接用ide开发的?开发工具是啥?能说一下开发环境么?我照搬一下试试

37,743

社区成员

发帖
与我相关
我的任务
社区描述
JavaScript,VBScript,AngleScript,ActionScript,Shell,Perl,Ruby,Lua,Tcl,Scala,MaxScript 等脚本语言交流。
社区管理员
  • 脚本语言(Perl/Python)社区
  • WuKongSecurity@BOB
加入社区
  • 近7日
  • 近30日
  • 至今

试试用AI创作助手写篇文章吧