2016-10-23 1 views
0

私はAzureでホストされているSQLサーバデータベースを持っています。私はスマート引用符( '"テスト"')でデータベースに文字列を入れました。私は私のMac(MacOSの10.11.6やPython 3.4.4、2.1.3 pymssql)にこのクエリを実行すると、私は、文字列を取り戻すpymssqlはAzure/Windows上でMacと比べて異なる文字セットを返します

import pymssql 
import json 

conn = pymssql.connect(
    server='coconut.database.windows.net', 
    user='[email protected]', 
    password='********', 
    database='coconut', 
    charset='UTF-8', 
) 

sql = """ 
SELECT * FROM messages WHERE id = '548a72cc-f584-7e21-2725-fe4dd594982f' 
""" 
cursor = conn.cursor() 
cursor.execute(sql) 
row = cursor.fetchone() 
json.dumps(row[3]) 

:私はそれに接続して簡単なクエリを実行することができます

"\u201ctest\u201d" 

これはスマート引用符として正しく解釈され、正しく表示されます。

私はAzureのWebデプロイメント(Pythonの3.4、Azureのアプリケーションサービス)上でこのクエリを実行すると、私は戻って、同じ文字列で異なる(誤った)エンコーディングを取得:

"\u0093test\u0094" 

私は 'と文字セットを指定UTF-8 'をpymssql接続に追加します。なぜWindows/Azure環境が別の文字セットを返すのですか?

(注:私はAzureの私のプロジェクトレポのホイールハウスにあらかじめ構築されたバイナリpymssql-2.1.3-cp34-none-win32.whlを入れました。これはpymssqlのプリビルドバイナリpymssqlと同じです-2.1.3-cp34-cp34m-win32.whl for PyPIのみpipをインストールするように 'cp34m'を 'none'に変更しなければなりませんでした)

答えて

2

あなたの説明によると、 Azure上のSQLデータベースのデフォルトのcharsetエンコーディングによって問題が発生しました。私の考えを検証するために、私はPython 3でいくつかのテストを行った。

AzureのSQLデータベースのデフォルトの文字コードエンコードはWindows-1252 (CP-1252)です。

SQL Server Collation Support
のMicrosoftのAzure SQLデータベースで使用されるデフォルトのデータベースの照合順序は、CP1は、コードページ1252 LATIN1_GENERALは、英語(米国)で順序SQL_Latin1_General_CP1_CI_AS、あるされ、CIは大文字と小文字を区別しないで、そしてASはaccent-です感受性が高い。 V12データベースの照合順序を変更することはできません。照合順序を設定する方法の詳細については、「COLLATE(Transact-SQL)」を参照してください。図示上記コードとして

>>> u"\u201c".encode('cp1252') 
b'\x93' 
>>> u"\u201d".encode('cp1252') 
b'\x94' 

\u0093 & \u0094をエンコード\u201c & \u201d介して得ことができます。

そして、

>>> u"\u0093".encode('utf-8') 
b'\xc2\x93' 
>>> u"\u0093".encode('utf-8').decode('cp1252')[1] 
'“'  # It's `\u201c` 
>>> u"\u201c" == u"\u0093".encode('utf-8').decode('cp1252')[1] 
True 

だから私は、あなたが以下の図は、デフォルトのプロパティCollation上として、SQLデータベースを作成したときにデータストレージのためのあなたの現在のSQLデータベースの文字セットエンコーディングは、Latin-1、ないUTF-8だと思いますAzureのポータルはSQL_Latin1_General_CP1_CI_ASです。他の照合サポートUTF-8をデフォルトの照合サポートの代わりに使用してください。

enter image description here

+0

興味深い。私はSQL_Latin1_General_CP1_CI_ASのデフォルト照合を使用しています。私が "sys"を実行すると、私のMacでは "stdin.encoding"を "utf-8"に、Azureで "cp1252"を取得します。デフォルトのpython文字エンコーディングが使用されているUnicode文字を判別しているのだろうかと思います。 Pythonを起動する前にAzureで "65001"を入力してください。 – Wheat

1

私はVARCHARからNVARCHARに列の型を作り直すことになりました。これは私の問題を解決し、文字はプラットフォームに関係なく正しく解釈されます。

+0

素晴らしい。共有してくれてありがとう。 –

関連する問題