2017-09-14 75 views
0

我有一個包含波斯語言字符串的變量,並且我無法正確地將該字符串保存到數據庫中。我正在使用REST API的燒瓶,並且我從客戶端獲取字符串。這是我的代碼:使用python將波斯語字符串保存到mysql數據庫中

@app.route('/getfile',methods=['POST']) 
def get_file(): 
    #check the validity of json format 
    if not request.json or not 'FileName' in request.json: 
     abort(400) 
    if not request.json or not 'FilePath' in request.json: 
     abort(400) 
    if not request.json or not 'Message' in request.json: 
     abort(400) 
    #retreive data from request 
    filename_=request.json['FileName'] 
    filepath_=request.json['FilePath'] 
    message_=request.json['Message'] 

    try: 
     conn = mysql.connector.connect(host=DBhost,database=DBname,user=DBusername,password=DBpassword) 
    except: 
     return jsonify({'Result':'Error, Could not connect to database.'}) 

    cursor_ = conn.cursor() 
    query_ = "INSERT INTO sms_excel_files VALUES(null,%s,%s,%s,0)" 
    data_ =(filename_,Dst_num_file,message_) 
    cursor_.execute(query_, data_) 
    last_row_id_=cursor_.lastrowid 
    conn.commit() 

有問題的變量是message_。我可以正確保存英文文本,但不能保存波斯文。我還在代碼頂部添加了# -*- coding: utf-8 -*-,但這並未解決問題。但是,如果我手動使用Persian字符串填充message_,它會正確保存到數據庫中。此外,如果我簡單地返回message_的值,則是正確的。

例如,這是被插入時message_包含字符串數據庫「سلام」:

سلام 

任何幫助表示讚賞。

回答

1

請注意,這是我第一次想讀阿拉伯語/波斯語字符,所以下面的信息可能是不正確的(我可以與波斯字符串比較我的測試輸出時犯了一個錯誤,你已經在你的問題中顯示)。此外,我從來沒有聽說過燒瓶。

說了:

1587 1604 1575 1605是代碼點,這代表你必須以Unicode顯示波斯串序列。現在,在HTML中,Unicode代碼點(十進制)可以編碼爲&#xxxx;形式的實體。所以字符串سلام該HTML字符串在HTML中表示形式的允許形式之一。

鑑於這種情況,有可能是錯誤行爲兩個可能的原因:

1)request.json [「消息」]已經包含/返回HTML(而不是自然文本)和(由於某種原因,我不t知道)包含/以HTML實體編碼形式返回問題字符串。所以這是你應該檢查的第一件事。 2)cursor_.execute(...)以某種方式將字符串編碼爲HTML,因此(出於某種原因,我不知道)將您的字符串編碼爲HTML實體編碼形式。也許你已經告訴數據庫驅動程序將message_中的非ASCII字符編碼爲HTML實體?

有關進一步分析,可以檢查request.json['Message']包含/僅返回ASCII字符的測試用例中發生了什麼。

如果ASCII字符也以HTML實體的形式寫入數據庫,那麼必須有一個基本問題,它可以將所有字符毫無例外地編碼爲HTML實體。否則,你最終還沒有告訴你的數據庫,你的數據庫驅動程序或你的文件系統驅動程序使用哪種編碼。在這種情況下,ASCII字符經常被正確處理,而奇怪的事情發生在非ASCII字符上。不過,在文件IO或數據庫操作期間自動將非ASCII字符編碼爲HTML實體將非常不尋常。但正如上面提到的,我不知道......燒瓶

請參考MySQL手冊,看看如何設置的字符編碼數據庫,表,列和連接,你的數據庫驅動程序文檔,看看哪些其他的事情你爲了正確處理這種編碼,必須做到這一點,你的解釋器和它的庫的手冊,看看如何正確設置文件IO的編碼(CGI通過STDIN/STDOUT工作)。

你讓你的生活輕鬆了許多,如果數據庫中的字符編碼和文件IO編碼都是一樣的。就我個人而言,我總是使用UTF-8。

最後請注意:由於我不知道什麼燒瓶,我不知道是什麼# -*- coding: utf-8 -*-是應該做的。但有可能這個只告訴解釋器腳本本身是如何編碼的,但不知道哪個編碼用於輸入/輸出/數據庫操作

+0

我不認爲它像你所解釋的那麼難。我可以在message_ = request.json ['Message']'之後正確返回message_。將該字符串插入數據庫時​​會損壞該字符串。數據庫排序規則是utf8_general_ci,列也是utf8_general_ci。 – Sinai

+0

@Sinai你究竟是否確實可以正確返回message_'?你把它轉儲到一個文件中,你打印出來給瀏覽器還是其他東西? – Binarus

+0

我打印出來給瀏覽器。我只是在我的代碼中的'message_ = request.json ['Message']'之後放了一個'return message_',我可以看到確切的字符串! – Sinai

0

試試看看這個代碼。它使用的是與您正在使用的庫幾乎相同的MySQLdb庫(在使用之前使用pip安裝它)。

我試圖以各種可能的方式設置「utf-8」。

# -*- coding: utf-8 -*- 
    import MySQLdb 

    # Open database connection 
    try: 
     db = MySQLdb.connect(host="localhost", 
          user="root", 
          passwd="", 
          db="db_name" 
          #,unix_socket="/opt/lampp/var/mysql/mysql.sock" 
          ) 
     db.set_character_set('utf8') 

     crsr = db.cursor(MySQLdb.cursors.DictCursor) 
     crsr.execute('SET NAMES utf8;') 
     crsr.execute('SET CHARACTER SET utf8;') 
     crsr.execute('SET character_set_connection=utf8;') 

    except MySQLdb.Error as e: 
     print e 
+0

我無法安裝MySqldb.I嘗試了幾種方法,但都沒有工作。我正在使用Python 2.7 – Sinai

相關問題