01.MySql串連錯誤:Cannot get hostname for your address
鄭昀 2010 隸屬於《05.資料入庫》小節
某Web應用的資料庫部署在 100.ZZZ.YYY.XXX 的 MySql 5.5.5 執行個體(新裝機器)上,
但是當用PHP或者Python從遠端機器上試圖訪問該資料庫時,會得到如下錯誤提示:
“Can't get hostname for your address”。
需要琢磨一下才能明白,這句提示是 MySql Server 返回給用戶端的。
也就是說,MySql Server在試圖對用戶端IP地址進行反向網域名稱解析,試圖得到主機名稱,然而我們發起訪問的用戶端要麼是自己
的機器,要麼是機房的伺服器,所以無法得到主機名稱,MySql Server 遂報錯,拒絕用戶端串連。
錯誤截屏
譬如,Python會得到這樣的異常:
事件記錄的報告
此時 MySql Server 所在伺服器上,Windows 事件記錄出現了如下錯誤:
事件類型: 警告
事件來源: MySQL
事件種類: 無
事件 ID: 100
日期: 2010-01-01
事件: 11:29:13
使用者: N/A
電腦: SERVERII
描述:
IP address '100.ZZZ.YYY.XXX' could not be resolved: getnameinfo() returned error (code: 11004).
For more information, see Help and Support Center at http://www.mysql.com.
簡單解釋
MySQL server received a request from you to allow you to connect to the database. So next thing it tried to do is to check what name is bound to your IP address (name resolution) and it failed to do so. So it just denied you access.
可以這麼理解mysql處理用戶端解析的過程:
1,當 mysql client 發起串連請求時,MySql Server 會主動去查 client 的主機名稱。
2,首先尋找Windows系統目錄下 /etc/hosts 檔案,搜尋網域名稱和IP的對應關係。
3,如果hosts檔案沒有,則尋找DNS設定,如果沒有設定DNS伺服器,會立刻返回失敗;如果設定了DNS伺服器,就進行反向解析,直到timeout。
解決辦法
第一種方法 修改Hosts
在 MySql Server 所在伺服器上,修改 Windows 的 hosts 檔案,增加一行記錄,如:
100.ZZZ.YYY.XXX dummy.ju690.cn
然後在 100.ZZZ.YYY.XXX 機器上用 Python 發起串連請求,經測試,可以正常串連,說明 MySql Server 這下可以通過 getnameinfo() 解析出100.ZZZ.YYY.XXX 的主機名稱了。
但這種方法很機械,所以一般採用下面這種方法。
第二種 修改MySql 的設定檔 my.ini
The solution:
Just add skip-name-resolve option to your MySQL configuration file (my.ini).
在 MySql Server 的設定檔 My.ini 中,增加如下兩行:
[mysqld]
skip-name-resolve
它將禁止 MySql Server 對外部串連進行 DNS 解析,使用這一選項可以消除 MySql 進行 DNS 解析的時間。
但需要注意,如果開啟該選項,則所有遠程主機串連授權都要使用IP地址方式,否則MySQL將無法正常處理串連請求。
參考:
http://www.ixdba.net/article/89/2127.html
http://blog.chinaunix.net/u/25264/showart_1936561.html
可能的後果
如果開啟 skip-name-resolve 選項,要確認 MySql 是否採用過主機名稱的授權,
在 mysql 中運行如下命令:
mysql> select user,host from mysql.user where host <> 'localhost' ;
一般會得到以“%”授權(也就是任何地址)的記錄:
+------------------+-------------+
| user | host |
+------------------+-------------+
| root | % |
| user_sync | 192.168.0.113 |
如果有host名是什麼“DB1”“DB2”的,那麼刪除授權表中有 hostanme 的記錄,然後重啟mysqld。