數據庫管理

第5章:數據庫管理

目錄php

5.1. MySQL服務器和服務器啓動腳本
5.1.1. 服務器端腳本和實用工具概述
5.1.2. mysqld-max擴展MySQL服務器
5.1.3. mysqld_safe:MySQL服務器啓動腳本
5.1.4. mysql.server:MySQL服務器啓動腳本
5.1.5. mysqld_multi:管理多個MySQL服務器的程序
5.2. mysqlmanager:MySQL實例管理器
5.2.1. 用MySQL實例管理器啓動MySQL服務器
5.2.2. 鏈接到MySQL實例管理器並建立用戶帳戶
5.2.3. MySQL實例管理器命令行選項
5.2.4. MySQL實例管理器配置文件
5.2.5. MySQL實例管理器識別的命令
5.3. mysqld:MySQL服務器
5.3.1. mysqld命令行選項
5.3.2. SQL服務器模式
5.3.3. 服務器系統變量
5.3.4. 服務器狀態變量
5.4. mysql_fix_privilege_tables:升級MySQL系統表
5.5. MySQL服務器關機進程
5.6. 通常安全問題
5.6.1. 通用安全指南
5.6.2. 使MySQL在攻擊者面前保持安全
5.6.3. Mysqld安全相關啓動選項
5.6.4. LOAD DATA LOCAL安全問題
5.7. MySQL訪問權限系統
5.7.1. 權限系統的做用
5.7.2. 權限系統工做原理
5.7.3. MySQL提供的權限
5.7.4. 與MySQL服務器鏈接
5.7.5. 訪問控制, 階段1:鏈接覈實
5.7.6. 訪問控制, 階段2:請求覈實
5.7.7. 權限更改什麼時候生效
5.7.8. 拒絕訪問錯誤的緣由
5.7.9. MySQL 4.1中的密碼哈希處理
5.8. MySQL用戶帳戶管理
5.8.1. MySQL用戶名和密碼
5.8.2. 向MySQL增長新用戶帳戶
5.8.3. 從MySQL刪除用戶帳戶
5.8.4. 限制帳戶資源
5.8.5. 設置帳戶密碼
5.8.6. 使你的密碼安全
5.8.7. 使用安全鏈接
5.9. 備份與恢復
5.9.1. 數據庫備份
5.9.2. 示例用備份與恢復策略
5.9.3. 自動恢復
5.9.4. 表維護和崩潰恢復
5.9.5. myisamchk:MyISAM表維護實用工具
5.9.6. 創建表維護計劃
5.9.7. 獲取關於表的信息
5.10. MySQL本地化和國際應用
5.10.1. 數據和排序用字符集
5.10.2. 設置錯誤消息語言
5.10.3. 添加新的字符集
5.10.4. 字符定義數組
5.10.5. 字符串比較支持
5.10.6. 多字節字符支持
5.10.7. 字符集問題
5.10.8. MySQL服務器時區支持
5.11. MySQL日誌文件
5.11.1. 錯誤日誌
5.11.2. 通用查詢日誌
5.11.3. 二進制日誌
5.11.4. 慢速查詢日誌
5.11.5. 日誌文件維護
5.12. 在同一臺機器上運行多個MySQL服務器
5.12.1. 在Windows下運行多個服務器
5.12.2. 在Unix中運行多個服務器
5.12.3. 在多服務器環境中使用客戶端程序
5.13. MySQL查詢高速緩衝
5.13.1. 查詢高速緩衝如何工做
5.13.2. 查詢高速緩衝SELECT選項
5.13.3. 查詢高速緩衝配置
5.13.4. 查詢高速緩衝狀態和維護

本章涵蓋了MySQL安裝管理主題,例如配置服務器、管理用戶帳戶和備份。html

5.1. MySQL服務器和服務器啓動腳本

MySQL服務器,即mysqld,是在MySQL安裝中負責大部分工做的主程序。服務器隨附了幾個相關腳本,當你安裝MySQL時它們能夠執行設置操做,或者是幫助你啓動和中止服務器的幫助程序。mysql

本節提供了服務器和相關程序的概述,以及服務器啓動腳本相關信息。關於配置服務器的信息參見5.3節,「mysqld:MySQL服務器」linux

5.1.1. 服務器端腳本和實用工具概述

MySQL程序採用各類不一樣的選項。但每一個MySQL程序提供一個--help選項,你能夠用來查閱程序選項相關說明。例如,你能夠試試mysqld --helpgit

你能夠在命令行中或在選項文件中指定選項來替換全部標準程序中的默認選項。參見4.3節,「指定程序選項」算法

下面簡單描述了MySQL服務器和服務器相關程序:sql

·         mysqldshell

SQL後臺程序(即MySQL服務器)。要想使用客戶端程序,該程序必須運行,由於客戶端經過鏈接服務器來訪問數據庫。參見5.3節,「mysqld:MySQL服務器」數據庫

·         mysqld-max編程

包括更多特性的一個服務器版本。參見5.1.2節,「mysqld-max擴展MySQL服務器」

·         mysqld_safe

服務器啓動腳本。若是mysqld-max存在,mysqld_safe試圖啓動它,不然啓動mysqld。參見5.1.3節,「mysqld_safe:MySQL服務器啓動腳本」

·         mysql.server

服務器啓動腳本。該腳本用於使用包含爲特定級別的運行啓動服務的腳本的運行目錄的系統。它調用mysqld_safe來啓動MySQL服務器。參見5.1.4節,「mysql.server:MySQL服務器啓動腳本」

·         mysqld_multi

服務器啓動腳本,能夠啓動或中止系統上安裝的多個服務器。參見5.1.5節,「mysqld_multi:管理多個MySQL服務器的程序」

·         mysql_install_db

該腳本用默認權限建立MySQL受權表。一般只是在系統上首次安裝MySQL時執行一次。參見2.9.2節,「Unix下安裝後的過程」

·         mysql_fix_ privilege_tables

在升級安裝後,若是新版本MySQL中的 受權表有更改,則使用該腳原本更改受權表。參見2.10.2節,「升級受權表」

服務器主機上還運行其它幾個程序:

·         myisamchk

用來描述、檢查、優化和維護MyISAM表的實用工具。在5.9.5節,「myisamchk:MyISAM表維護實用工具」中描述了myisamchk

·         make_binary_distribution

該程序能夠生成編譯過的MySQL的二進制版本。能夠經過FTP上傳到ftp.mysql.com的/pub/mysql/upload/,供其它MySQL用戶使用。

·         mysqlbug

MySQL 缺陷報告腳本。它能夠用來向MySQL郵件系統發送缺陷報告。(你也能夠訪問http://bugs.mysql.com/在線建立缺陷報告文件。參見1.7.1.3節,「如何通報缺陷和問題」)。

5.1.2. mysqld-max擴展MySQL服務器

MySQL-Max服務器是mysqld MySQL服務器的一個版本,包含了更多的特性。

該分發版的使用取決於你的平臺:

·         對於Windows,MySQL二進制分發版包括標準服務器 (mysqld.exe)和MySQL-Max服務器(mysqld-max.exe),所以你再也不須要專用分發版。只須要使用一個常規Windows分發版,能夠從http://dev.mysql.com/downloads/得到。參見2.3節,「在Windows上安裝MySQL」

·         對於Linux,若是你使用RPM分發版安裝MySQL,首先使用常規MySQL-server RPM來安裝標準mysqld服務器。而後使用MySQL-Max RPM來安裝mysqld-max服務器。MySQL-Max RPM假定你已經安裝了常規服務器RPM。關於Linux RPM軟件包的詳細信息,參見2.4節,「在Linux下安裝MySQL」

·         全部其它MySQL-Max分發版包含一個mysqld服務器,但具備更多的特性。

你能夠從MySQL AB網址http://dev.mysql.com/downloads/找到MySQL-Max二進制版本。

MySQL AB使用下面的configure選項構建MySQL-Max服務器:

·         --with-server-suffix=-max

該選項爲mysqld版本字符串添加一個-max後綴。

·         --with-innodb

該選項啓用InnoDB存儲引擎支持。MySQL-Max服務器包括InnoDB支持。在MySQL 4.0及以上版本中,默認InnoDB包括在全部二進制分發版中,所以你不須要用MySQL-Max服務器只是用來獲取InnoDB支持。

·         --with-bdb

該選項啓用Berkeley DB (BDB)存儲引擎支持。

·         --with-blackhole-storage-engine

該選項啓用BLACKHOLE存儲引擎支持。

·         USE_SYMDIR

啓用該定義來爲Windows打開數據庫符號連接支持。符號連接支持適用於全部Windows服務器,所以Max服務器不須要支持該特性。

·         --with-ndbcluster

該選項啓用NDB Cluster存儲引擎支持。目前(5.1.2-alpha)只有Linux、Solaris和Mac OS X支持Cluster。已有一些用戶報告在BSD 操做系統上成功使用了從源碼構建的MySQL Cluster,但目前尚未獲得官方支持。

MySQL-Max二進制分發版對於想要安裝預編譯程序的用戶很方便。若是你使用源碼分發版構建MySQL,你能夠經過在配置時啓用MySQL-Max二進制分發版構建所用的相同的特性來構建你本身的Max-like服務器。

MySQL-Max服務器包括BerkeleyDB (BDB)存儲引擎,但並不是全部平臺支持BDB。

Solaris、Mac OS X和Linux(在大多數平臺上)的MySQL-Max服務器包括NDB CLUSTER存儲引擎支持。請注意必須用ndbcluster選項啓動服務器,以便使服務器作爲MySQL Cluster的一部分來運行。(詳細信息參見17.4節,「MySQL簇的配置」)。

下面的表顯示了MySQL-Max二進制在哪一個平臺上包括BDB和/或NDB CLUSTER支持:

系統

BDB支持

NDB支持

AIX 4.3

N

N

HP-UX 11.0

N

N

Linux-Alpha

N

Y

Linux-IA-64

N

N

Linux-Intel

Y

Y

Mac OS X

N

N

NetWare

N

N

SCO OSR5

Y

N

Solaris-SPARC

Y

Y

Solaris-Intel

N

Y

UnixWare

Y

N

Windows NT/2000/XP

Y

N

要想找出你的服務器支持哪一個存儲引擎,執行下面的語句:

mysql> SHOW ENGINES;
+------------+---------+----------------------------------------------------------------+
| Engine     | Support | Comment                                                        |
+------------+---------+----------------------------------------------------------------+
| MyISAM     | DEFAULT | Default engine as of MySQL 3.23 with great performance         |
| MEMORY     | YES     | Hash based, stored in memory, useful for temporary tables      |
| HEAP       | YES     | Alias for MEMORY                                               |
| MERGE      | YES     | Collection of identical MyISAM tables                          |
| MRG_MYISAM | YES     | Alias for MERGE                                                |
| ISAM       | NO      | Obsolete storage engine, now replaced by MyISAM                |
| MRG_ISAM   | NO      | Obsolete storage engine, now replaced by MERGE                 |
| InnoDB     | YES     | Supports transactions, row-level locking, and foreign keys     |
| INNOBASE   | YES     | Alias for INNODB                                               |
| BDB        | YES     | Supports transactions and page-level locking                   |
| BERKELEYDB | YES     | Alias for BDB                                                  |
| NDBCLUSTER | NO      | Clustered, fault-tolerant, memory-based tables                 |
| NDB        | NO      | Alias for NDBCLUSTER                                           |
| EXAMPLE    | NO      | Example storage engine                                         |
| ARCHIVE    | YES     | Archive storage engine                                         |
| CSV        | NO      | CSV storage engine                                             |
| FEDERATED  | YES     | Federated MySQL storage engine                                 |
| BLACKHOLE  | YES     | /dev/null storage engine (anything you write to it disappears) |
+------------+---------+----------------------------------------------------------------+
18 rows in set (0.00 sec)

(另參見13.5.4.8節,「SHOW ENGINES語法」)。

你還能夠使用下面的語句代替SHOW ENGINES,並檢查你感興趣的存儲引擎的變量值:

mysql> SHOW VARIABLES LIKE 'have%';
+-----------------------+----------+
| Variable_name         | Value    |
+-----------------------+----------+
| have_archive          | YES      |
| have_bdb              | NO       |
| have_blackhole_engine | YES      |
| have_compress         | YES      |
| have_crypt            | YES      |
| have_csv              | YES      |
| have_example_engine   | NO       |
| have_federated_engine | NO       |
| have_geometry         | YES      |
| have_innodb           | YES      |
| have_isam             | NO       |
| have_ndbcluster       | DISABLED |
| have_openssl          | NO       |
| have_partition_engine | YES      |
| have_query_cache      | YES      |
| have_raid             | NO       |
| have_rtree_keys       | YES      |
| have_symlink          | YES      |
+-----------------------+----------+
18 rows in set (0.01 sec)

SHOW命令的精確輸出隨使用的MySQL版本(和啓用的特性)的不一樣而有變化。第2列的值表示各特性支持的服務器級別,以下所示:

含義

YES

 支持該特性並已經激活。

NO

 不支持該特性。

DISABLED

 支持該特性但被禁用。

NO值表示編譯的服務器不支持該特性,所以在運行時不能激活。

出現DISABLED值是由於服務器啓動時該特性被禁用,或沒有給出啓用它的全部選項。在後一種狀況,host_名.err錯誤日誌文件應包含該選項被禁用的緣由。

若是服務器支持InnoDB或BDB存儲引擎,你還能夠看見DISABLED,但在運行啓動時使用了--skip-innodb或--skip-bdb選項。對於NDB CLUSTER存儲引擎,DISABLED表示服務器支持MySQL Cluster,但啓動時未啓用--ndb-cluster選項。

全部MySQL服務器支持MyISAM表,由於MyISAM是 默認存儲引擎。

5.1.3. mysqld_safe:MySQL服務器啓動腳本

在Unix和NetWare中推薦使用mysqld_safe來啓動mysqld服務器mysqld_safe增長了一些安全特性,例如當出現錯誤時重啓服務器並向錯誤日誌文件寫入運行時間信息。本節後面列出了NetWare的特定行爲。

釋:爲了保持同舊版本MySQL的向後兼容性,MySQL二進制分發版仍然包括safe_mysqld做爲mysqld_safe的符號連接。可是,你不該再依賴它,由於再未來將刪掉它。

默認狀況下,mysqld_safe嘗試啓動可執行mysqld-max(若是存在),不然啓動mysqld。該行爲的含義是:

·         在Linux中,MySQL-Max RPM依賴該mysqld_safe的行爲。RPM安裝可執行mysqld-max,使mysqld_safe從該點起自動使用可執行命令。

·         若是你安裝包括mysqld-max服務器的MySQL-Max分發版,後面升級到非-Max的MySQL版本,mysqld_safe仍然試圖運行舊的 mysqld-max服務器。升級時,你應手動刪除舊的mysqld-max服務器以確保mysqld_safe運行新的mysqld服務器

要想越過默認行爲並顯式指定你想要運行哪一個服務器,爲mysqld_safe指定--mysqld或--mysqld-version選項。

mysqld_safe的許多選項與mysqld的相同的。參見5.3.1節,「mysqld命令行選項」

全部在命令行中爲mysqld_safe指定的選項被傳遞給mysqld。若是你想要使用mysqld不支持的mysqld_safe的選項,不要在命令行中指定。相反,在選項文件的[mysqld_safe]組內將它們列出來。參見4.3.2節,「使用選項文件」

mysqld_safe從選項文件的[mysqld]、[server]和[mysqld_safe]部分讀取全部選項。爲了保證向後兼容性,它還讀取 [safe_mysqld]部分,儘管在MySQL 5.1安裝中你應將這部分從新命名爲[mysqld_safe]。

mysqld_safe支持下面的選項:

·         --help

顯示幫助消息並退出。

·         --autoclose

(只在NetWare中)在NetWare中,mysqld_safe能夠保持窗口。當你關掉mysqld_safe NLM時,窗口不按默認設置消失。相反,它提示用戶輸入:

*<NLM has terminated; Press any key to close the screen>*

若是你想讓NetWare自動關閉窗口,在mysqld_safe中使用--autoclose選項。

·         --basedir=path

MySQL安裝目錄的路徑。

·         --core-file-size=size

mysqld可以建立的內核文件的大小。選項值傳遞給ulimit -c

·         --datadir=path

數據目錄的路徑。

·           --defaults-extra-file=path

除了通用選項文件所讀取的選項文件名。若是給出,必須首選該選項。

·         --defaults-file=path

讀取的代替通用選項文件的選項文件名。若是給出,必須首選該選項。

·         --ledir=path

包含mysqld程序的目錄的路徑。使用該選項來顯式表示服務器位置。

·         --log-error=path

將錯誤日誌寫入給定的文件。參見5.11.1節,「錯誤日誌」

·         --mysqld=prog_name

想要啓動的服務器程序名(在ledir目錄)。若是你使用MySQL二進制分發版但有二進制分發版以外的數據目錄須要該選項。

·         --mysqld-version =suffix

該選項相似--mysqld選項,但你只指定服務器程序名的後綴。基本名假定爲mysqld。例如,若是你使用--mysqld-version =max,mysqld_safe啓動ledir目錄中的mysqld-max程序。若是--mysqld-version的參數爲空,mysqld_safe使用目錄中的mysqld

·         --nice=priority

使用nice程序根據給定值來設置服務器的調度優先級。

·         --no-defaults

不要讀任何選項文件。若是給出,必須首選該選項。

·         --open-files-limit=count

mysqld可以打開的文件的數量。選項值傳遞給 ulimit -n。請注意你須要用root啓動mysqld_safe來保證正確工做!

·         --pid-file=path

進程ID文件的路徑。

·         --port=port_num

 用來幀聽TCP/IP鏈接的端口號。端口號必須爲1024或更大值,除非MySQL以root系統用戶運行。

·         --skip-character-set-client-handshake

忽略客戶端發送的字符集信息,使用服務器的默認字符集。(選擇該選項,MySQL的動做與MySQL 4.0相同)。

·         --socket=path

用於本地鏈接的Unix套接字文件。

·         --timezone=zone

爲給定的選項值設置TZ時區環境變量。從操做系統文檔查閱合法的時區規定格式。

·         --user={user_name | user_id}

以用戶名user_name或數字用戶ID user_id運行mysqld服務器。(本文中的「用戶」指系統登陸帳戶,而不是 受權表中的MySQL用戶)。

執行mysqld_safe時,必須先給出--defaults-file或--defaults-extra-option,或不使用選項文件。例如,該命令將不使用選項文件:

mysqld_safe --port=port_num --defaults-file=file_name

相反,使用下面的命令:

mysqld_safe --defaults-file=file_name --port=port_num

通常狀況mysqld_safe腳本能夠啓動從源碼或二進制MySQL分發版安裝的服務器,即便這些分發版將服務器安裝到稍微不一樣的位置。(參見2.1.5節,「安裝佈局」)。 mysqld_safe指望下面的其中一個條件是真的:

·         能夠根據調用mysqld_safe的目錄找到服務器和數據庫。在二進制分發版中,mysqld_safe看上去在bin和data目錄的工做目錄下。對於源碼分發版,爲libexec和var目錄。若是你從MySQL安裝目錄執行mysqld_safe應知足該條件(例如,二進制分發版爲/usr/local/mysql)。

·         若是不能根據工做目錄找到服務器和數據庫,mysqld_safe試圖經過絕對路徑對它們定位。典型位置爲/usr/local/libexec和/usr/local/var。實際位置由構建分發版時配置的值肯定若是MySQL安裝到配置時指定的位置,它們應該是正確的。

由於mysqld_safe試圖經過工做目錄找到服務器和數據庫,只要你從MySQL安裝目錄運行mysqld_safe能夠將MySQL二進制分發版安裝到其它位置:

shell> cd mysql_installation_directory
shell> bin/mysqld_safe &

若是mysqld_safe失敗,即便從MySQL安裝目錄調用仍然失敗,你能夠指定--ledir和--datadir選項來指示服務器和數據庫在你的系統中的安裝目錄。

通常狀況,你不該編輯mysqld_safe腳本。相反,應使用命令行選項或my.cnf選項文件的[mysqld_safe]部分的選項來配置mysqld_safe。通常不須要編輯mysqld_safe來正確啓動服務器。可是,若是你編輯,未來升級MySQL後會覆蓋你修改的mysqld_safe版本,所以你應對你修改的版本進行備份以便未來重裝。

在NetWare中,mysqld_safe是一個NetWare Loadable Module (NLM),從原Unix shell腳本移植。它執行:

1.    檢查系統和選項。

2.    檢查MyISAM表。

3.    保持MySQL服務器窗口。

4.    啓動並監視mysqld,若是因錯誤終止則重啓。

5.    將mysqld的錯誤消息發送到數據目錄中的host_name.err 文件。

6.    將mysqld_safe的屏幕輸出發送到數據目錄中的host_name.safe文件。

5.1.4. mysql.server:MySQL服務器啓動腳本

在Unix中的MySQL分發版包括mysql.server腳本。它能夠用於使用System V-style運行目錄來啓動和中止系統服務的系統,例如Linux和Solaris。它還用於MySQL的Mac OS X Startup Item。

mysql.server位於MySQL源碼樹MySQL安裝目錄下的support-files目錄中。

若是你使用Linux 服務器RPM軟件包(MySQL-server-VERSION.rpm),mysql.server腳本將安裝到/etc/init.d目錄下,名爲mysql。你不須要 手動安裝。關於Linux RPM軟件包的詳細信息參見2.4節,「在Linux下安裝MySQL」

一些賣方提供的RPM軟件包安裝的啓動腳本用其它名,例如mysqld。

若是你從不自動安裝mysql.server的源碼分發版或二進制分發版格式安裝MySQL,也能夠手動安裝。相關說明參見2.9.2.2節,「自動啓動和中止MySQL」

mysql.server從 [mysql.server]和選項文件的[mysqld]部分讀取選項。(爲了保證向後兼容性,它還讀取 [safe_mysqld]部分,儘管在MySQL 5.1安裝中你應將這部分從新命名爲[mysqld_safe])。

5.1.5. mysqld_multi:管理多個MySQL服務器的程序

mysqld_multi能夠管理多個幀聽不一樣Unix套接字文件和TCP/IP端口的鏈接的mysqld 進程。它能夠啓動或中止服務器,或報告它們的當前狀態。

程序尋找my.cnf中的[mysqldN]組(或--config-file選項指定的文件)。N 能夠爲任何正整數。在下面的討論中該數字指選項組號,或GNR。組號區別各選項組,並用做mysqld_multi的參數來指定想要啓動、中止哪一個服務器或獲取哪一個服務器的狀態報告。這些組中的選項與將用來啓動mysqld的[mysqld]組中的相同。(例如,參見2.9.2.2節,「自動啓動和中止MySQL」)。可是,當使用多個服務器時,須要每一個服務器使用本身的選項值,例如Unix套接字文件和TCP/IP端口號。關於在多服務器環境中,每一個服務器對應惟一選項的詳細信息,參見5.12節,「在同一臺機器上運行多個MySQL服務器」

要想調用mysqld_multi,使用下面的語法:

shell> mysqld_multi [options] {start|stop|report} [GNR[,GNR] ...]

start、stop和report表示你想要執行的操做。你能夠在單個服務器或多個服務器上執行指定的操做,取決於選項名後面的GNR 列。若是沒有該列,mysqld_multi爲選項文件中的全部服務器執行該操做。

每一個GNR值表明一個選項組號或組號範圍。GNR值應爲選項文件中組名末尾的號。例如,組[mysqld17]的GNR爲17。要想指定組號的範圍,用破折號間隔開第1個和最後1個號。GNR值10-13表明組[mysqld10]到[mysqld13]。能夠在命令行中指定多個組或組範圍,用逗號間隔開。GNR列不能有空格字符(空格或tab);空格字符後面的內容將被忽略掉。

該命令使用選項組[mysqld17]啓動單個服務器:

shell> mysqld_multi start 17

該命令中止多個服務器,使用選項組[mysql8]和[mysqld10]至[mysqld13]:

shell> mysqld_multi stop 8,10-13

使用該命令列出設置選項文件的示例:

shell> mysqld_multi --example

mysqld_multi支持下面的選項:

·         --config-file=name

指定選項文件名。這關係到mysqld_multi從哪裏尋找[mysqldN]選項組。沒有該選項,從通用my.cnf文件讀全部選項。選項不影響 mysqld_multi從哪裏讀取本身的選項,老是從通用my.cnf文件的[mysqld_multi]組讀取。

·         --example

顯示示例選項文件。

·         --help

顯示幫助消息並退出。

·         --log=name

指定日誌文件名。若是該文件存在,後面爲日誌輸出。

·         --mysqladmin=prog_name

用來中止服務器的mysqladmin二進制。

·         --mysqld=prog_name

可用的mysqld二進制。請注意你還能夠將該選項的值指定爲mysqld_safe。選項被傳遞給 mysqld。確保在PATH環境變量設定值或mysqld_safe中有mysqld所在目錄。

·         --no-log

按照標準輸出打印日誌信息,不要寫入日誌文件。默認狀況下,輸出寫入日誌文件。

·         --password=password

調用mysqladmin時使用的MySQL帳戶的密碼。請注意該密碼值不是可選項,不象其它MySQL程序。

·         --silent

禁用警告。

·         --tcp-ip

經過TCP/IP端口而不是Unix套接字文件來鏈接每一個MySQL服務器。(若是找不到套接字文件, 服務器仍然能夠運行,但只能經過 TCP/IP端口訪問)。默認狀況下,使用Unix套接字文件進行鏈接。該選項影響stop和report操做。

·         --user=user_name

調用mysqladmin時使用的MySQL帳戶的用戶名。

·         --verbose

更詳細。

·         --version

顯示版本信息並退出。

關於mysqld_multi的一些註解:

·         確保中止mysqld服務器(用mysqladmin程序)的MySQL帳戶在各個服務器中的用戶名和密碼相同。而且應確保帳戶具備SHUTDOWN權限。若是你想要管理的服務器的管理帳戶有許多不一樣的用戶名或密碼,你須要在每一個服務器上建立一個帳戶,並具備相同的用戶名和密碼。例如,你能夠執行下面的命令爲每一個服務器設置一個普通multi_admin帳戶:

·                shell> mysql -u root -S /tmp/mysql.sock -proot_password
·                mysql> GRANT SHUTDOWN ON *.*
·                    -> TO 'multi_admin'@'localhost' IDENTIFIED BY 'multipass';

參見5.7.2節,「權限系統工做原理」。你必須爲每一個mysqld服務器執行該操做。當鏈接時適當更改鏈接參數。請注意帳戶名的主機部分必須容許你用multi_admin從你想要運行mysqld_multi的主機進行鏈接。

·         若是你使用mysqld_safe來啓動mysqld(例如,--mysqld=mysqld_safe),--pid-file選項很重要。每一個mysqld應有本身的進程ID文件。使用mysqld_safe而不使用mysqld的好處是mysqld_safe「守護」其mysqld進程,若是用kill –9發送的信號或因爲其它緣由(例如分段故障)進程終止,則重啓進程。請注意mysqld_safe腳本須要你從某個位置啓動它。這說明運行mysqld_multi前你必須進入某個目錄。若是啓動時有問題,請參見mysqld_safe腳本。特別是要檢查下列行:

·                ----------------------------------------------------------------
·                MY_PWD=`pwd`
·                # Check if we are starting this relative (for the binary release)
·                if test -d $MY_PWD/data/mysql -a -f ./share/mysql/english/errmsg.sys -a \
·                -x ./bin/mysqld
·                ----------------------------------------------------------------

參見5.1.3節,「mysqld_safe:MySQL服務器啓動腳本」。上述行執行的測試應成功,不然你可能遇到了問題。

·         每一個mysqld的Unix套接字文件和TCP/IP端口號必須不一樣。

·         你可能想要爲mysqld使用--user選項,但爲此你須要用Unix root用戶運行mysqld_multi腳本。選項文件中有選項沒關係;若是你不是超級用戶,而且你用本身的Unix帳戶重啓mysqld進程,你只會獲得警告。

·         重要:確保mysqld進程啓動所用Unix帳戶能夠徹底訪問數據目錄。不要使用Unix root帳戶,除非你知道你在作什麼。

·         很是重要:使用mysqld_multi前,確保理解傳遞給mysqld服務器的選項的含義以及你爲何想要獨立的mysqld進程。應清楚 在相同的數據目錄下使用多個mysqld服務器的危險。使用單獨的數據目錄,除非你知道你在作什麼。在線程系統中,在相同的數據目錄下啓動多個服務器不會獲得超性能。參見5.12節,「在同一臺機器上運行多個MySQL服務器」

下面的示例顯示了你如何設置選項文件來使用mysqld_multi。專門省去第1個和第5個[mysqldN]組來講明你的選項文件能夠稍有不一樣。這樣給你更大的靈活性。mysqld程序重啓或中止的順序由它們在選項文件中的順序決定。

# This file should probably be in your home dir (~/.my.cnf)
# or /etc/my.cnf
# Version 2.1 by Jani Tolonen
 
[mysqld_multi]
mysqld     = /usr/local/bin/mysqld_safe
mysqladmin = /usr/local/bin/mysqladmin
user       = multi_admin
password   = multipass
 
[mysqld2]
socket     = /tmp/mysql.sock2
port       = 3307
pid-file   = /usr/local/mysql/var2/hostname.pid2
datadir    = /usr/local/mysql/var2
language   = /usr/local/share/mysql/english
user       = john
 
[mysqld3]
socket     = /tmp/mysql.sock3
port       = 3308
pid-file   = /usr/local/mysql/var3/hostname.pid3
datadir    = /usr/local/mysql/var3
language   = /usr/local/share/mysql/swedish
user       = monty
 
[mysqld4]
socket     = /tmp/mysql.sock4
port       = 3309
pid-file   = /usr/local/mysql/var4/hostname.pid4
datadir    = /usr/local/mysql/var4
language   = /usr/local/share/mysql/estonia
user       = tonu
 
[mysqld6]
socket     = /tmp/mysql.sock6
port       = 3311
pid-file   = /usr/local/mysql/var6/hostname.pid6
datadir    = /usr/local/mysql/var6
language   = /usr/local/share/mysql/japanese
user       = jani

參見4.3.2節,「使用選項文件」

5.2. mysqlmanager:MySQL實例管理器

MySQL實例管理器(IM)是經過TCP/IP端口運行的後臺程序,用來監視和管理MySQL數據庫服務器實例。MySQL實例管理器 適合Unix-類操做系統和Windows。

能夠在mysqld_safe腳本使用MySQL實例管理器來啓動和中止MySQL服務器,甚至能夠從一個遠程主機。MySQL實例管理器還執行mysqld_multi腳本的功能(和大多數語法)。下面爲MySQL實例管理器的詳細描述。

5.2.1. 用MySQL實例管理器啓動MySQL服務器

通常狀況,用mysql.server腳本啓動MySQL Database Server(MySQL數據庫服務器),一般駐留在/etc/init.d/ 文件夾。默認狀況下該腳本調用mysqld_safe腳本。可是,你能夠在腳本中將use_mysqld_safe變量設置爲0(零)以便使用MySQL實例管理器來啓動服務器。

在這種狀況下,Instance Manager的行爲取決於MySQL配置文件中的選項。若是沒有配置文件,MySQL實例管理器建立mysqld實例並試圖用默認(編譯嵌入的)配置來啓動。這說明若是mysqld沒有安裝到 默認位置,IM不能猜出它的位置。若是你已經在非標準位置安裝了MySQL服務器,你應使用配置文件。參見2.1.5節,「安裝佈局」

若是有配置文件,IM將分析配置文件搜索[mysqld]部分(例如[mysqld]、[mysqld1]、[mysqld2]等)。每一個部分指定一個實例。啓動時IM將啓動全部找到的實例。IM關閉時默認中止全部實例。

請注意有一個特殊選項mysqld-path(mysqld-path = path-to-mysqld- binary),只能用IM識別。使用該變量讓IM知道mysqld二進制駐留在哪兒。你還應該爲服務器設置basedir和datadir選項。

啓用MySQL實例管理器的典型MySQL服務器啓動/關閉循環爲:

·          用/etc/init.d/mysql腳本啓動MySQL實例管理器。

·          MySQL實例管理器啓動全部實例並監視它們。

·         若是某個服務器實例失敗,MySQL實例管理器重啓它。

·         若是MySQL實例管理器被關閉(例如用/etc/init.d/mysql stop命令),全部實例被MySQL實例管理器關閉。

5.2.2. 鏈接到MySQL實例管理器並建立用戶帳戶

使用MySQL客戶端-服務器協議來處理同MySQL實例管理器之間的通訊。你不能使用標準mysql客戶端程序和MySQL C API來鏈接IM。IM支持客戶端工具和mysql-4.1或之後的版本所分發的庫所用的MySQL客戶端-服務器協議版本。

IM將用戶信息保存到密碼文件中。密碼文件的默認位置爲/etc/mysqlmanager.passwd。

密碼應相似於:

petr:*35110DC9B4D8140F5DE667E28C72DD2597B5C848

要想生成密碼用--passwd選項調用IM。則輸出能夠重定向到/etc/mysqlmanager.passwd文件以添加新用戶。下面爲示例命令。

./mysqlmanager --passwd >> /etc/mysqlmanager.passwd
Creating record for new user.
Enter user name: mike
Enter password: <password>
Re-type password: <password>

下面的行將加到/etc/mysqlmanager.passwd:

mike:*00A51F3F48415C7D4E8908980D443C29C69B60C9

若是/etc/mysqlmanager.passwd文件中沒有該條,則不能鏈接IM。

5.2.3. MySQL實例管理器命令行選項

MySQL實例管理器支持許多命令行選項。執行 ./mysqlmanager --help命令能夠簡單列出。有下面的選項:

·         --help,-?

顯示幫助消息並退出。

·         --bind-address=name

綁定地址用於鏈接。

·         --default-mysqld-path=name

在Unix中,若是實例部分沒有路徑,則爲尋找MySQL服務器二進制的地點。例如:default-mysqld-path = /usr/sbin/mysqld

·         --defaults-file=file_name

從給定文件讀Instance Manager和MySQL服務器設定值。全部Instance Manager更改的配置將加入該文件。只能用於Instance Manager的第一選項。

·         --install

在Windows中,將Instance Manager安裝爲Windows服務。

·         --log=name

IM日誌文件的路徑。結合--run-as-service選項使用。

·         --monitoring-interval=Seconds

監視實例的間隔,單位爲秒。Instance Manager將嘗試鏈接每一個監視的實例來檢查它們是不是活動的/沒有掛起。出現故障,IM將重啓幾回(其實是屢次)實例。能夠用nonguarded選項爲特定實例禁用該行爲。若是未給定任何值, 默認使用20秒。

·         --passwd,-P

編寫passwd文件並退出。

·         --password-file=name

從該文件中尋找Instance Manager用戶和密碼。默認文件是/etc/mysqlmanager.passwd。

·         --pid-file=name

使用的進程ID文件。默認狀況下,該文件文件名爲mysqlmanager.pid。

·         -- port=port_num

用於鏈接的端口號。(IANA分配的 默認端口號爲2273)。

·         --print-defaults

打印當前的默認值並退出。只能用做Instance Manager的第一選項。

·         --remove

在Windows中,刪掉Instance Manager Windows服務。假定前面已經用--install運行了Instance Manager。

·         --run-as-service

使完善進程變爲後臺程序並啓動。完善進程很簡單,不易崩潰。出現故障後它將本身重啓IM。

·         --socket=name

Unix中用於鏈接的套接字文件。默認狀況下,文件名爲/tmp/mysqlmanager.sock。

·         --standalone

在Windows中以單機模式運行Instance Manager。

·         --user=name

啓動並運行mysqlmanager的用戶名。建議使用運行mysqld服務器的用戶帳戶來運行mysqlmanager

·         --version, -V

輸出版本信息並退出。

5.2.4. MySQL實例管理器配置文件

Instance Manager使用標準my.cnf文件。它使用[manager]部分爲本身讀取選項並讀取[mysqld]部分來建立實例。[manager]部分包含上述列出的選項。下面爲[manager]部分示例:
# MySQL Instance Manager options section
[manager]
default-mysqld-path = /usr/local/mysql/libexec/mysqld
socket=/tmp/manager.sock
pid-file=/tmp/manager.pid
password-file = /home/cps/.mysqlmanager.passwd
monitoring-interval = 2
port = 1999
bind-address = 192.168.1.5

MySQL實例管理器只在Unix中讀取並管理/etc/my.cnf文件。在Windows中,MySQL實例管理器從Instance Manager的安裝目錄讀取my.ini文件。用--defaults-file=file_ name選項能夠更改默認選項文件的位置。

實例部分指定啓動時給每一個實例的選項。這些主要是普通MySQL服務器選項,但有一些IM-專用選項:

·         mysqld-path = <path-to-mysqld-binary>

mysqld服務器二進制的路徑。

·         shutdown-delay = Seconds

IM應等待實例關閉的秒數。 默認爲35秒。超過延遲時間後,IM假定實例正掛起並試圖「kill –9」它。若是你使用帶large表的InnoDB,你應當增長該值。

·         nonguarded

若是你想要爲某個實例禁用IM監視功能,應設置該選項。

下面給出了幾個實例示例。

[mysqld]
mysqld-path=/usr/local/mysql/libexec/mysqld
socket=/tmp/mysql.sock
port=3307
server_id=1
skip-stack-trace
core-file
skip-bdb
log-bin
log-error
log=mylog
log-slow-queries
 
[mysqld2]
nonguarded
port=3308
server_id=2
mysqld-path= /home/cps/mysql/trees/mysql-5.1/sql/mysqld
socket     = /tmp/mysql.sock5
pid-file   = /tmp/hostname.pid5
datadir= /home/cps/mysql_data/data_dir1
language=/home/cps/mysql/trees/mysql-5.1/sql/share/english
log-bin

log=/tmp/fordel.log

5.2.5. MySQL實例管理器識別的命令

一旦你已經爲MySQL實例管理器設置了一個密碼文件而且IM正在運行,你能夠鏈接它。你能夠使用 mysql客戶端工具經過標準MySQL API來鏈接。如下是MySQL實例管理器目前能夠接收的命令的清單和例子。

·         START INSTANCE <instance_name>

該命令將試圖啓動一個實例:

mysql> START INSTANCE mysqld4;
Query OK, 0 rows affected (0,00 sec)

·         STOP INSTANCE <instance_name>

將試圖中止一個實例:

mysql> STOP INSTANCE mysqld4;
Query OK, 0 rows affected (0,00 sec)

·         SHOW INSTANCES

顯示全部載入的實例名:

mysql> show instances;
+---------------+---------+
| instance_name | status  |
+---------------+---------+
| mysqld3       | offline |
| mysqld4       | online  |
| mysqld2       | offline |
+---------------+---------+
3 rows in set (0,04 sec)

·         SHOW INSTANCE STATUS <instance_name>

顯示選定的實例的狀態和版本信息:

mysql> SHOW INSTANCE STATUS mysqld3;
+---------------+--------+---------+
| instance_name | status | version |
+---------------+--------+---------+
| mysqld3       | online | unknown |
+---------------+--------+---------+
1 row in set (0.00 sec)

·         SHOW INSTANCE OPTIONS <instance_name>

顯示實例使用的選項:

mysql> SHOW INSTANCE OPTIONS mysqld3;
+---------------+---------------------------------------------------+
| option_name   | value                                             |
+---------------+---------------------------------------------------+
| instance_name | mysqld3                                           |
| mysqld-path   | /home/cps/mysql/trees/mysql-4.1/sql/mysqld        |
| port          | 3309                                              |
| socket        | /tmp/mysql.sock3                                  |
| pid-file      | hostname.pid3                                     |
| datadir       | /home/cps/mysql_data/data_dir1/                   |
| language      | /home/cps/mysql/trees/mysql-4.1/sql/share/english |
+---------------+---------------------------------------------------+
7 rows in set (0.01 sec)

·         SHOW <instance_name> LOG FILES

該命令提供實例使用的全部日誌文件。結果包含日誌文件的路徑和日誌文件的大小。若是沒有在配置文件中指定日誌文件的路徑 (例如log=/var/mysql.log),IM試圖猜出它的位置。若是IM不能猜出日誌文件的位置,你應明確指定日誌文件的位置。

mysql> SHOW mysqld LOG FILES;
+-------------+------------------------------------+----------+
| Logfile     | Path                               | Filesize |
+-------------+------------------------------------+----------+
| ERROR LOG   | /home/cps/var/mysql/owlet.err      | 9186     |
| GENERAL LOG | /home/cps/var/mysql/owlet.log      | 471503   |
| SLOW LOG    | /home/cps/var/mysql/owlet-slow.log | 4463     |
+-------------+------------------------------------+----------+
3 rows in set (0.01 sec)

·         SHOW <instance_name> LOG {ERROR | SLOW | GENERAL} size[,offset_from_end]

該命令查找指定的日誌文件的一部分。由於大多數用戶關注最新的日誌消息,用size參數定義你想要從日誌末尾開始索取的字節數。你能夠指定可選offset_from_end參數從日誌文件中部索取數據。下面的示例能夠索取21個字節的數據,從日誌文件末尾開始23個字節,2個字節用於結束:

mysql> SHOW mysqld LOG GENERAL 21, 2;
+---------------------+
| Log                 |
+---------------------+
| using password: YES |
+---------------------+
1 row in set (0.00 sec)

·         SET instance_name.option_name=option_value

該命令編輯指定的實例的配置文件以更改/增長實例選項。IM假定配置文件位於/etc/my.cnf。你應檢查文件是否存在,並具備合適的權限。

mysql> SET mysqld2.port=3322;
Query OK, 0 rows affected (0.00 sec)

在MySQL服務器重啓前,對配置文件進行的更改不會生效。而且,執行FLUSH INSTANCES命令後,纔會將這些更改保存到Instance Manager的實例設定值的本地緩存中。

·         UNSET instance_name.option_name

該命令從實例的配置文件刪除一個選項。

mysql> UNSET mysqld2.port;
Query OK, 0 rows affected (0.00 sec)

在MySQL服務器重啓前,對配置文件進行的更改不會生效。而且,執行FLUSH INSTANCES命令後,纔會將這些更改保存到Instance Manager的實例設定值的本地緩存中。

·         FLUSH INSTANCES

該命令強制IM重讀配置文件並清空內部結構。編輯配置文件後應執行該命令。該命令不重啓實例:

mysql> FLUSH INSTANCES;
Query OK, 0 rows affected (0.04 sec)

5.3. mysqld:MySQL服務器

mysqld是MySQL服務器。下面討論MySQL服務器的配置:

·         服務器支持的啓動選項

·         如何設置服務器SQL模式

·         服務器系統變量

·         服務器狀態變量

5.3.1. mysqld命令行選項

當啓動mysqld服務器時,你能夠使用4.3節,「指定程序選項」中描述的方法指定程序選項。最經常使用的方法是在選項文件中或在命令行提供選項。可是,在大多數狀況下,但願服務器每次運行時使用相同的選項。最好的方法是確保將它們列在選項文件中。參見4.3.2節,「使用選項文件」

mysqld從[mysqld]和[server]組讀取選項。mysqld_safe從[mysqld]、[server]、[mysqld_safe]和[safe_mysqld]組讀取選項。mysql.server從 [mysqld]和[mysql.server]組讀取選項。嵌入式MySQL服務器一般從[server]、[embedded]和[xxxxx_SERVER]組讀取選項,其中xxxxx是服務器嵌入的應用程序名。

mysqld接受許多命令行選項。執行mysqld --help能夠簡單列出來。要想看所有列表列,使用命令mysqld --verbose --help

下面列出了一些最經常使用的服務器選項。其它的選項在其它地方描述:

·         影響安全的選項:參見5.6.3節,「Mysqld安全相關啓動選項」

·         SSL-相關選項:參見5.8.7.6節,「SSL命令行選項」

·         二進制日誌控制選項:參見5.11.3節,「二進制日誌」

·         複製相關選項:參見6.8節,「複製啓動選項」

·         特定存儲引擎相關選項:參見15.1.1節,「MyISAM啓動選項」15.5.3節,「BDB啓動選項」15.2.4節,「InnoDB啓動選項」

你還能夠將變量名做爲一個選項,設置服務器系統變量的值,如本節後面所述。

·         --help,-?

顯示簡短的幫助消息並退出。使用--verbose和--help選項來看所有內容。

·         --allow-suspicious-udfs

該選項控制是否用戶定義的函數只有一個xxx符,用做可載入的主函數。默認狀況下,該選項被關閉,只有至少有一個附屬符的UDF  能夠載入。這樣能夠防止從未包含合法UDF的共享文件裝載函數。參見27.2.3.6節,「用戶定義函數安全注意事項」

·         --ansi

使用標準(ANSI)SQL語法代替MySQL語法。參見1.8.3節,「在ANSI模式下運行MySQL」。使用--sql-mode選項能夠更精確控制服務器SQL模式。

·         --basedir=path, -b path

MySQL安裝目錄的路徑。一般全部路徑根據該路徑來解析。

·         --bind-address=IP

待綁定的IP地址。

·         --bootstrap

mysql_install_db腳本使用該選項來建立MySQL受權表,不須要啓動MySQL服務器。

·         --console

將錯誤日誌消息寫入stderr和stdout,即便指定了--log-error。在Windows中,若是使用該選項,mysqld不關閉控制檯窗口。

·         --character-sets-dir=path

字符集安裝的目錄。參見5.10.1節,「數據和排序用字符集」

·         --chroot=path

經過chroot()系統調用在啓動過程當中將mysqld服務器放入一個封閉環境中。這是推薦的一個安全措施。請注意使用該選項能夠 限制LOAD DATA INFILE和SELECT ... INTO OUTFILE。

·         --character-set-server=charset

使用charset做爲 默認服務器字符集。參見5.10.1節,「數據和排序用字符集」

·         --core-file

若是mysqld終止,寫內核文件。在某些系統中,你還必須爲mysqld_safe指定--core-file-size 選項。參見5.1.3節,「mysqld_safe:MySQL服務器啓動腳本」。請注意對於一些系統,例如Solaris,若是你使用--user選項不會得到內核文件。

·         --collation-server=collation

使用collation做爲 默認服務器校對規則。參見5.10.1節,「數據和排序用字符集」

·         --datadir=path, -h path

數據目錄的路徑。

·         --debug[=debug_options], -# [debug_options]

若是MySQL配置了--with-debug,你能夠使用該選項來得到一個跟蹤文件,跟蹤mysqld正進行的操做。debug_options字符串一般爲'd:t:o,file_name'。參見E.1.2節,「建立跟蹤文件」

·         (DEPRECATED) --default-character-set=charset

使用char設置做爲 默認字符集。因爲--character-set-server,反對使用該選項。參見5.10.1節,「數據和排序用字符集」

·         --default-collation=collation

使用collation 做爲默認校對規則。因爲--collation-server,反對使用該選項。參見5.10.1節,「數據和排序用字符集」

·         --default-storage-engine=type

該選項爲--default-table-type的同義詞。

·         --default-table-type=type

設置表的默認類型。參見第15章:存儲引擎和表類型

·         --default-time-zone=type

設置默認服務器時區。該選項設置全局time_zone系統變量。若是未給出該選項, 默認時區與系統時區相同(用system_time_zone系統變量值給定)。

·         --delay-key-write[= OFF | ON | ALL]

如何使用DELAYED KEYS選項。鍵寫入延遲會形成再次寫MyISAM表時鍵緩衝區不能被清空。OFF禁用延遲的鍵寫入。ON啓用用DELAYED KEYS選項建立的表的延遲的鍵寫入。ALL延遲全部MyISAM表的鍵寫入。參見7.5.2節,「調節服務器參數」。參見15.1.1節,「MyISAM啓動選項」

釋:若是你將該變量設置爲ALL,你不該從另外一個正使用MyISAM表的程序中使用MyISAM表(例如從另外一個MySQL服務器或用myisamchk)。這樣操做會致使索引破壞。

·         --des-key-file=file_name

從該文件讀DES_ENCRYPT()和DES_DECRYPT()使用的 默認鍵。

·         --enable-named-pipe

啓用命名管道支持。該選項只適用Windows NT、2000、XP和2003系統,而且只適用支持命名管道鏈接的mysqld-ntmysqld-max-nt服務器。

 

·         --exit-info[=flags], -T [flags]

這是不一樣標誌的一個位掩碼,你能夠用來調試mysqld服務器。不要使用該選項,除非你確切知道它在作什麼!

·         --external-locking

啓用系統鎖定。請注意若是你在lockd不能徹底工做的系統上使用該選項(例如在Linux中),mysqld容易死鎖。該選項之前叫--enable-locking。

釋:若是你在許多MySQL進程中使用該選項來更新MyISAM表,你必須確保知足下述條件:

o        使用正被另外一個進程更新的表的查詢的緩存不可以使用。

o        不該在共享表中使用--delay-key-write=ALL或DELAY_KEY_WRITE=1。

最簡單的方法是結合使用--external-locking和--delay-key-write=OFF --query-cache-size=0。

(默認不能實現,由於在許多設置中,結合使用上述選項頗有用)。

·         --flush

執行SQL語句後向硬盤上清空更改。通常狀況執行SQL語句後 MySQL向硬盤寫入全部更改,讓操做系統處理與硬盤的同步。參見A.4.2節,「若是MySQL依然崩潰,應做些什麼」

·         --init-file=file

啓動時從該文件讀SQL語句。每一個語句必須在同一行中而且不該包括註釋。

·         --language=lang_name, -L lang_name

用給定語言給出客戶端錯誤消息。lang_name能夠爲語言名或語言文件安裝目錄的全路徑名。參見5.10.2節,「設置錯誤消息語言」

·         --large-pages

一些硬件/操做系統架構支持大於 默認值(一般4 KB)的內存頁。實際支持取決於使用的硬件和OS。大量訪問內存的應用程序經過使用較大的頁,下降了Translation Lookaside Buffer (TLB)損失,能夠改善性能。

目前,MySQL只在Linux中支持大頁面(在Linux中被稱做HugeTLB)。咱們已經計劃將該支持擴展到FreeBSD、Solaris和其它可能的平臺。

在Linux中能夠使用大頁面前,須要配置HugeTLB內存池。參考Linux內核源碼中的hugetlbpage.txt文件。

默認狀況下該選項被禁用。

·         ---log[=file], -l [file]

日誌鏈接和對文件的查詢。參見5.11.2節,「通用查詢日誌」。若是你不指定文件名,MySQL使用host_name.log做爲文件名。

·         --log-bin=[file]

二進制日誌文件。將更改數據的全部查詢記入該文件。用於備份和複製。參見5.11.3節,「二進制日誌」。建議指定一個文件名(緣由參見A.8.1節,「MySQL中的打開事宜」),不然MySQL使用host_name-bin做爲日誌文件基本名。

·         --log-bin-index[=file]

二進制日誌文件名的索引文件。參見5.11.3節,「二進制日誌」。若是你不指定文件名,而且若是你沒有在--log-bin中指定,MySQL使用host_name-bin.index做爲文件名。

·         --log-bin-trust-routine-creators[={0|1}]

沒有參數或參數爲1,該選項將系統變量log_bin_trust_routine_creators設置爲1。爲參數 0時,該選項將系統變量設置爲0。log_bin_trust_routine_creators影響MySQL如何對保存的程序的建立強加限制。參見20.4節,「存儲子程序和觸發程序的二進制日誌功能」

·         --log-error[=file]

該文件的日誌錯誤和啓動消息。參見5.11.1節,「錯誤日誌」。若是你不指定文件名,MySQL使用host_name.err做爲文件名。若是文件名沒有擴展名,則加上.err擴展名。

·         --log-isam[=file]

將全部MyISAM更改記入該文件(只有調試MyISAM時才使用)。

·         (DEPRECATED) --log-long-format

記錄激活的更新日誌、二進制更新日誌、和慢查詢日誌的大量信息。例如,全部查詢的用戶名和時間戳將記錄下來。不同意選用該選項,由於它如今表明 默認記錄行爲。(參見--log-short-format描述)。--log-queries-not-using-indexes選項適合將未使用索引的查詢記錄到慢查詢日誌中。

·         --log-queries-not-using-indexes

若是你結合--log-slow-queries使用該選項,未使用索引的查詢也被記錄到慢查詢日誌中。參見5.11.4節,「慢速查詢日誌」

·         --log-short-format

記錄激活的更新日誌、二進制更新日誌、和慢查詢日誌的少許信息。例如,用戶名和時間戳不記錄下來。

·         ---log-slow-admin-statements

將慢管理語句例如OPTIMIZE TABLE、ANALYZE TABLE和ALTER TABLE記入慢查詢日誌。

·         --log-slow-queries[=file]

將全部執行時間超過long_query_time 秒的查詢記入該文件。參見5.11.4節,「慢速查詢日誌」。詳細信息參見--log-long-format和--log-short-format選項描述。

 

·         --log-warnings, -W

將警告例如Aborted connection...打印到錯誤日誌。建議啓用該選項,例如,若是你使用複製 (你能夠獲得關於所發生事情的詳細信息,例如關於網絡故障和從新鏈接的消息)。默認狀況下啓用該選項;要想禁用它,使用--skip-log-warnings。中斷的鏈接不會記入錯誤日誌,除非值大於1。參見A.2.10節,「通訊錯誤和失效鏈接」

·         --low-priority-updates

表修改(INSERT, REPLACE, DELETE, UPDATE)比選擇的優先級要低。也能夠經過{INSERT | REPLACE | DELETE | UPDATE} LOW_PRIORITY ... 來下降某個查詢的優先級來實現,或經過SET LOW_PRIORITY_UPDATES=1來更改一個線程的優先級。參見7.3.2節,「表鎖定事宜」

·          --memlock

將mysqld 進程鎖定在內存中。在支持mlockall()系統調用的系統上有效,例如Solaris。若是操做系統使mysqld在硬盤上交換時出現問題,能夠爲你提供幫助。請注意使用該選項時須要以root運行服務器,但從安全考慮並非一個好注意。

·         --myisam-recover [=option[,option...]]]

將存儲引擎MyISAM設置爲恢復模式。該選項值是DEFAULT、BACKUP、FORCE或QUICK值的任何組合。若是你指定多個值,用逗號間隔開。你還能夠使用""值來禁用該選項。使用若是該選項,當mysqld打開MyISAM表時,檢查是否表標記爲崩潰或沒有正確關閉。(只有用--skip-external-lockingare運行時,最後的選項才工做)。 若是是這種狀況,mysqld則檢查 表。若是表被破壞,mysqld試圖維護它。

下面的選項影響維護工做:

選項

描述

DEFAULT

與沒有使用--myisam-recover選項相同。

BACKUP

若是在恢復過程當中,數據文件被更改了,將tbl_name.MYD文件備份爲tbl_name-datetime.BAK。

FORCE

即便.MYD文件將丟掉多個行也進行恢復。

QUICK

若是沒有刪除塊,不要檢查表中的行。

在表自動修復前,MySQL錯誤日誌添加一條註解。若是你不想用戶干涉干涉大多數問題,你應使用BACKUP,FORCE選項。該選項強制維護表,即便一些行將會被刪除也不例外,但它保持舊的數據文件作爲備份,以便你能夠在後來進行檢查。

·         --ndb-connectstring=connect_string

當使用NDB存儲引擎時,能夠指出經過設置鏈接字符串選項來分發羣集配置的管理服務器。相關語法參見17.4.4.2節,「MySQL簇鏈接字符串」

·         --ndbcluster

若是二進制支持NDB CLUSTER存儲引擎,使用該選項能夠代替禁用MySQL Cluster支持的 默認設置。參見第17章:MySQL簇

·         --old-passwords

強制服務器爲新密碼生成短(4.1前)密碼哈希。若是服務器必須支持舊客戶端程序,爲保證兼容性這頗有用。參見5.7.9節,「MySQL 4.1中的密碼哈希處理」

·         --one-thread

只使用一個線程(用於在Linux中調試)。只有服務器啓用了調試,該選項纔可用。參見E.1節,「調試MySQL服務器」

·         --open-files-limit=count

用來更改mysqld文件描述符的數量。若是沒有設置或設置爲0,則mysqld經過setrlimit()使用該值來保存文件描述符。若是該值爲0,則mysqld 保存max_connections*5或max_connections + table_cache*2(取較大者)個文件。若是mysqld給出你錯誤"打開的文件太多。",你應試試增長該值。

·         --pid-file=path

mysqld_safe使用的進程ID文件的路徑。

·         --port=port_num, -P port_num

幀聽TCP/IP鏈接時使用的端口號。

·         --safe-mode

跳過一些優化階段。

·         (DEPRECATED) --safe-show-database

參見5.7.3節,「MySQL提供的權限」

·         --safe-user-create

啓用後若是用戶沒有mysql.user表或表中列的INSERT權限,則用戶不能用GRANT語句建立新用戶。

·         --secure-auth

不容許使用舊(4.1以前)密碼的帳戶進行鑑定。

·         --shared-memory

啓用本地客戶端的共享內存鏈接。該選項只用於Windows。

·         --shared-memory-base-name=name

共享內存鏈接名。該選項只用於Windows。

·         --skip-bdb

禁用BDB存儲引擎。這樣能夠節省內存,並可能加速某些操做。若是你須要BDB表則不要使用該選項。

·         --skip-concurrent-insert

關閉在同一時間在MyISAM表中選擇和插入的能力。(只有你發現缺陷時才使用該選項)。

·         --skip-external-locking

不要使用系統鎖定。要想使用myisamchk,你必須關閉服務器。(參見1.4.3節,「MySQL穩定性」)。 要避免該需求,使用MySQL Monitor中的CHECK TABLE和REPAIR TABLE來檢查並維護MyISAM表。

·         --skip-grant-tables

該選項使服務器不使用權限系統。該權限容許訪問服務器的用戶不受限制地訪問全部數據庫。你能夠從系統外殼命令行執行mysqladmin flush-privilegesmysqladmin reload命令,或執行MySQL FLUSH PRIVILEGES語句讓運行的服務器從新開始使用 受權表。

·         --skip-host-cache

爲了更快地在名稱-IP之間進行解析,不要使用內部主機名緩存。相反,每次客戶端鏈接時查詢DNS服務器。參見7.5.6節,「MySQL如何使用DNS」

·         --skip-innodb

禁用InnoDB存儲引擎。這樣能夠節省內存,並可能加速某些操做。若是你須要BDB表則不要使用該選項。

·         --skip-name-resolve

不要解析正檢查客戶端鏈接的主機名。只使用IP號。若是你使用該項, 受權表中的全部Host列值必須爲IP號或localhost。參見7.5.6節,「MySQL如何使用DNS」

·         --skip-ndbcluster

禁用NDB CLUSTER存儲引擎。這是支持NDB CLUSTER存儲引擎的二進制的默認設置,說明只有用--ndbcluster選項顯式覆蓋--skip-ndbcluster選項時,系統才爲該存儲引擎分配內存和其它資源。使用示例參見17.4.3節,「MySQL簇的快速測試設置」

·         --skip-networking

不幀聽TCP/IP鏈接。必須經過命名管道或共享內存(在Windows中)或Unix套接字文件(在Unix中)完成mysqld的相互操做。對於只容許本地客戶端的系統,大力推薦該選項。參見7.5.6節,「MySQL如何使用DNS」

·         --standalone

只適合基於Windows-NT的系統;指導MySQL服務器不作爲服務來運行。

·         --symbolic-links, --skip-symbolic-links

啓用或禁用符號連接支持。在Windows和Unix中,該選項的做用是不一樣的:

o        在Windows中,啓用符號連接,你能夠經過建立包含實際目錄路徑的directory.sym文件來創建數據庫目錄的符號連接。參見7.6.1.3節,「在Windows平臺上使用關於數據庫的符號連接」

在Unix中,啓用符號連接表示你能夠用CREATE TABLE語句的INDEX DIRECTORY或DATA DIRECTORY選項將MyISAM索引文件或數據文件連接到另外一個目錄。若是你刪除或從新命名錶,符號連接所指的文件也被刪除或從新命名。參見13.1.5節,「CREATE TABLE語法」

·         --skip-safemalloc

若是MySQL配置了--with-debug=full,全部MySQL程序在內存分配和釋放時檢查內存是否溢出。檢查很慢,所以若是你不須要你能夠用--skip-safemalloc選項來避免。

·         --skip-show-database

使用該選項,只容許具備SHOW DATABASES權限的用戶執行SHOW DATABASES語句,該語句顯示全部數據庫名。不使用該選項,容許全部用戶執行SHOW DATABASES,但只向具備SHOW DATABASES權限或部分數據庫權限的用戶顯示每一個數據庫名。請注意全局權限爲數據庫的一種權限。

·         --skip-stack-trace

不跟蹤寫堆棧。當調試運行mysqld時該選項有用。在一些系統中,你還必須使用該選項來得到內核文件。參見E.1節,「調試MySQL服務器」

·         --skip-thread-priority

在快速響應中禁用線程優先級。

·         --socket=path

在Unix中,該選項指定用於本地鏈接的Unix套接字文件。 默認值是/tmp/mysql.sock。在Windows中,該選項指定本地鏈接所使用的管道名。 默認值是MySQL。

·         --sql-mode=value[,value[,value...]]

將MySQL設置爲SQL模式。參見5.3.2節,「SQL服務器模式」

·         --temp-pool

該選項使服務器建立的大多數臨時文件使用一系列文件名,而不是每一個新文件使用惟一的文件名。這樣解決了在Linux內核中用 不一樣的名建立許多新文件的問題。在之前,Linux彷佛「泄漏」內存,由於它被直接分配到directory entry緩存而不是硬盤緩存。

·         --transaction-isolation=level

設置默認事務隔離級別,能夠READ-UNCOMMITTED、READ-COMMITTEE、REPEATABLE-READ或SERIALIZABLE。參見13.4.6節,「SET TRANSACTION語法」

·         --tmpdir=path, -t path

建立臨時文件的目錄路徑。默認/tmp目錄在過小不能容納臨時表的分區時該選項頗有用。該選項接受round-robin模式的幾個路徑。在Unix中路徑應用冒號(‘:’) 間隔開,在Windows、NetWare和OS/2中用分號(‘;’) 間隔開。若是MySQL服務器爲複製從機,你不該讓--tmpdir指向基於內存的文件系統中的目錄或服務器主機重啓時會清除的目錄。複製從機須要臨時文件,機器重啓時能夠複製臨時表或執行LOAD DATA INFILE操做。若是服務器重啓時臨時文件目錄中的文件丟失,複製失敗。

·         --user={user_name | user_id}, -u {user_name | user_id}

user_name或數字用戶ID user_id運行mysqld服務器。(「用戶」指系統登陸帳戶,而不是 受權表中所列的MySQL用戶)。

用root啓動mysqld時強制使用該選項。服務器在啓動序列中更改用戶ID,讓它作爲具體用戶而不是root運行。參見5.6.1節,「通用安全指南」

要避免用戶在my.cnf文件中添加--user=root選項(使服務器用root運行)時可能出現的安全漏洞,mysqld只使用指定的第1個--user選項,若是有多個--user選項則會出現警告。在命令行選項前處理/etc/my.cnf和$MYSQL_HOME/my.cnf中的選項,所以建議你在/etc/my.cnf中放一個--user選項,並指定root以外的其它值。在其它--user選項前先找到/etc/my.cnf中的選項,確保服務器用其它用戶運行,若是找到其它--user選項則會出現警告。

·         --version, -V

顯示版本信息並退出。

你能夠使用--var_name=value形式的選項爲服務器系統變量。例如,--key_buffer_size=32M將變量key_buffer_size設爲32MB。

請注意設置變量時,MySQL能夠自動將它糾正到某個給定範圍內,或若是隻容許某個值,則將設置值調節到最接近容許的值。

還能夠經過--set-variable=var_name=value或-O var_name=value語法來設置變量。可是,如今不同意使用該語法。

5.3.3節,「服務器系統變量」徹底描述了所有系統變量。調節服務器參數部分包括如何對他們進行優化。參見7.5.2節,「調節服務器參數」

你能夠用SET語句更改大多數服務器系統變量的值。參見13.5.3節,「SET語法」

若是你想用SET 限制啓動項可設的最大值,你能夠使用--maximum-var_name命令行選項來定義。

5.3.2. SQL服務器模式

MySQL服務器能夠以不一樣的SQL模式來操做,而且能夠爲不一樣客戶端應用不一樣模式。這樣每一個應用程序能夠根據本身的需求來定製服務器的操做模式。

模式定義MySQL應支持哪些SQL語法,以及應執行哪一種數據驗證檢查。這樣能夠更容易地在不一樣的環境中使用MySQL,並結合其它數據庫服務器使用MySQL。

你能夠用--sql-mode="modes"選項啓動mysqld來設置默認SQL模式。若是你想要重設,該值還能夠爲空(--sql-mode ="")。

你還能夠在啓動後用SET [SESSION|GLOBAL] sql_mode='modes'語句設置sql_mode變量來更改SQL模式。設置 GLOBAL變量時須要擁有SUPER權限,而且會影響從那時起鏈接的全部客戶端的操做。設置SESSION變量隻影響當前的客戶端。任何客戶端能夠隨時更改本身的會話 sql_mode值。

Modesis是用逗號(‘,’)間隔開的一系列不一樣的模式。你能夠用SELECT @@sql_mode語句查詢當前的模式。默認值是空(沒有設置任何模式)。

主要重要sql_mode值爲:

·         ANSI

更改語法和行爲,使其更符合標準SQL。

·         STRICT_TRANS_TABLES

若是不能將給定的值插入到事務表中,則放棄該語句。對於非事務表,若是值出如今單行語句或多行語句的第1行,則放棄該語句。本節後面給出了更詳細的描述。

·         TRADITIONAL

Make MySQL的行爲象「傳統」SQL數據庫系統。該模式的簡單描述是當在列中插入不正確的值時「給出錯誤而不是警告」。釋:一旦發現錯誤當即放棄INSERT/UPDATE。若是你使用非事務存儲引擎,這種方式不是你想要的,由於出現錯誤前進行的數據更改不會「滾動」,結果是更新「只進行了一部分」。

本手冊指「嚴格模式」,表示至少STRICT _TRANS_TABLES或STRICT _ALL_TABLES被啓用的模式。

下面描述了支持的全部模式:

·         ALLOW_INVALID_DATES

在嚴格模式下不要檢查所有日期。只檢查1到12之間的月份和1到31之間的日。這在Web應用程序中,當你從三個不一樣的字段獲取年、月、日,而且想要確切保存用戶插入的內容(不進行日期驗證)時很重要。該模式適用於DATE和DATETIME列。不適合TIMESTAMP列,TIMESTAMP列須要驗證日期。

啓用嚴格模式後,服務器須要合法的月和日,不只僅是分別在1到12和1到31範圍內。例如,禁用嚴格模式時'2004-04-31'是合法的,但啓用嚴格模式後是非法的。要想在嚴格模式容許遮掩固定日期,還應啓用ALLOW_INVALID_DATES。

·         ANSI_QUOTES

將‘"’視爲識別符引號(‘`’引號字符),不要視爲字符串的引號字符。在ANSI模式,你能夠仍然使用‘`’來引用識別符。啓用ANSI_QUOTES後,你不能用雙引號來引用字符串,由於它被解釋爲識別符。

·         ERROR_FOR_DIVISION_BY_ZERO

在嚴格模式,在INSERT或UPDATE過程當中,若是被零除(或MOD(X,0)),則產生錯誤(不然爲警告)。若是未給出該模式,被零除時MySQL返回NULL。若是用到INSERT IGNORE或UPDATE IGNORE中,MySQL生成被零除警告,但操做結果爲NULL。

·         HIGH_NOT_PRECEDENCE

NOT操做符的優先順序是表達式例如NOT a BETWEEN b AND c被解釋爲NOT (a BETWEEN b AND c)。在一些舊版本MySQL中, 表達式被解釋爲(NOT a) BETWEEN b AND c。啓用HIGH_NOT_PRECEDENCESQL模式,能夠得到之前的更高優先級的結果。

mysql> SET sql_mode = '';
mysql> SELECT NOT 1 BETWEEN -5 AND 5;
        -> 0
mysql> SET sql_mode = 'broken_not';
mysql> SELECT NOT 1 BETWEEN -5 AND 5;
        -> 1

·         IGNORE_SPACE

容許函數名和‘(’之間有空格。強制將全部函數名視爲保存的字。結果是,若是你想要訪問保存爲字的數據庫、表或列名,你必須引用它。例如,由於有USER()函數,mysql數據庫中的user表名和該表內的User列被保存下來,所以你必須引用它們:

SELECT "User" FROM mysql."user";

·         NO_AUTO_CREATE_USER

防止GRANT自動建立新用戶,除非還指定了密碼。

·         NO_AUTO_VALUE_ON_ZERO

NO_AUTO_VALUE_ON_ZERO影響AUTO_INCREMENT列的處理。通常狀況,你能夠向該列插入NULL或0生成下一個序列號。NO_AUTO_VALUE_ON_ZERO禁用0,所以只有NULL能夠生成下一個序列號。

若是將0保存到表的AUTO_INCREMENT列,該模式會頗有用。(不推薦採用該慣例)。例如,若是你用mysqldump轉儲表並重載,MySQL遇到0值通常會生成新的序列號,生成的表的內容與轉儲的表不一樣。重載轉儲文件前啓用NO_AUTO_VALUE_ON_ZERO能夠解決該問題。mysqldump在輸出中自動包括啓用NO_AUTO_VALUE_ON_ZERO的語句。

·         NO_BACKSLASH_ESCAPES

禁用反斜線字符(‘\’)作爲字符串內的退出字符。啓用該模式,反斜線則成爲普通字符。

·         NO_DIR_IN_CREATE

建立表時,忽視全部INDEX DIRECTORY和DATA DIRECTORY指令。該選項對從複製服務器有用。

·         NO_ENGINE_SUBSTITUTION

若是須要的存儲引擎被禁用或未編譯,能夠防止自動替換存儲引擎。

·         NO_FIELD_OPTIONS

不要在SHOW CREATE TABLE的輸出中打印MySQL專用列選項。該模式在可移植模式(portability mode)下用於mysqldump

·         NO_KEY_OPTIONS

不要在SHOW CREATE TABLE的輸出中打印MySQL專用索引選項。該模式在可移植模式(portability mode)下用於mysqldump

·         NO_TABLE_OPTIONS

不要在SHOW CREATE TABLE的輸出中打印MySQL專用表選項(例如ENGINE)。該模式在可移植模式(portability mode)下用於mysqldump

·         NO_UNSIGNED_SUBTRACTION

在減運算中,若是某個操做數沒有符號,不要將結果標記爲UNSIGNED。請注意這樣使UNSIGNED BIGINT不能100%用於上下文中。參見12.8節,「Cast函數和操做符」

 

·         NO_ZERO_DATE

在嚴格模式,不要將 '0000-00-00'作爲合法日期。你仍然能夠用IGNORE選項插入零日期。在非嚴格模式,能夠接受該日期,但會生成警告。

·         NO_ZERO_IN_DATE

在嚴格模式,不接受月或日部分爲0的日期。若是使用IGNORE選項,咱們爲相似的日期插入'0000-00-00'。在非嚴格模式,能夠接受該日期,但會生成警告。

·         ONLY_FULL_GROUP_BY

不要讓GROUP BY部分中的查詢指向未選擇的列。

·         PIPES_AS_CONCAT

將||視爲字符串鏈接操做符(+)(同CONCAT()),而不視爲OR。

·         REAL_AS_FLOAT

將REAL視爲FLOAT的同義詞,而不是DOUBLE的同義詞。

·         STRICT_TRANS_TABLES

爲全部存儲引擎啓用嚴格模式。非法數據值被拒絕。後面有詳細說明。

·         STRICT_TRANS_TABLES

爲事務存儲引擎啓用嚴格模式,也可能爲非事務存儲引擎啓用嚴格模式。後面有詳細說明。

嚴格模式控制MySQL如何處理非法或丟失的輸入值。有幾種緣由能夠使一個值爲非法。例如,數據類型錯誤,不適合列,或超出範圍。當新插入的行不包含某列的沒有顯示定義DEFAULT子句的值,則該值被丟失。

對於事務表,當啓用STRICT_ALL_TABLES或STRICT_TRANS_TABLES模式時,若是語句中有非法或丟失值,則會出現錯誤。語句被放棄並滾動。

對於非事務表,若是插入或更新的第1行出現壞值,兩種模式的行爲相同。語句被放棄,表保持不變。若是語句插入或修改多行,而且壞值出如今第2或後面的行,結果取決於啓用了哪一個嚴格選項:

·         對於STRICT_ALL_TABLES,MySQL返回錯誤並忽視剩餘的行。可是,在這種狀況下,前面的行已經被插入或更新。這說明你能夠部分更新,這可能不是你想要的。要避免這點,最好使用單行語句,由於這樣能夠不更改表便可以放棄。

·         對於STRICT_TRANS_TABLES,MySQL將非法值轉換爲最接近該列的合法值並插入調整後的值。若是值丟失,MySQL在列中插入隱式 默認值。在任何狀況下,MySQL都會生成警告而不是給出錯誤並繼續執行語句。13.1.5節,「CREATE TABLE語法」描述了隱式默認值。

嚴格模式不容許非法日期,例如'2004-04-31'。它不容許禁止日期使用「零」部分,例如'2004-04-00'或「零」日期。要想禁止,應在嚴格模式基礎上,啓用NO_ZERO_IN_DATE和NO_ZERO_DATE SQL模式。

若是你不使用嚴格模式(即不啓用STRICT_TRANS_TABLES或STRICT_ALL_TABLES模式),對於非法或丟失的值,MySQL將插入調整後的值並給出警告。在嚴格模式,你能夠經過INSERT IGNORE或UPDATE IGNORE來實現。參見13.5.4.22節,「SHOW WARNINGS語法」

下面的特殊模式快速組合了前面所列的模式。

其中包括大多數最新版本MySQL中的全部模式值。舊版本中,組合模式不包括新版本中沒有的不適用的具體模式值。

·         ANSI

等同REAL_AS_FLOAT、PIPES_AS_CONCAT、ANSI_QUOTES、IGNORE_SPACE。參見1.8.3節,「在ANSI模式下運行MySQL」

·         DB2

等同PIPES_AS_CONCAT、ANSI_QUOTES、IGNORE_SPACE、NO_KEY_OPTIONS、NO_TABLE_OPTIONS、NO_FIELD_OPTIONS。

·         MAXDB

等同PIPES_AS_CONCAT、ANSI_QUOTES、IGNORE_SPACE、NO_KEY_OPTIONS、NO_TABLE_OPTIONS、NO_FIELD_OPTIONS、 NO_AUTO_CREATE_USER。

·         MSSQL

等同PIPES_AS_CONCAT、ANSI_QUOTES、IGNORE_SPACE、NO_KEY_OPTIONS、NO_TABLE_OPTIONS、 NO_FIELD_OPTIONS。

·         MYSQL323

等同NO_FIELD_OPTIONS、HIGH_NOT_PRECEDENCE。

·         MYSQL40

等同NO_FIELD_OPTIONS、HIGH_NOT_PRECEDENCE。

·         ORACLE

等同PIPES_AS_CONCAT、ANSI_QUOTES、IGNORE_SPACE、NO_KEY_OPTIONS、NO_TABLE_OPTIONS、NO_FIELD_OPTIONS、NO_AUTO_CREATE_USER。

·         POSTGRESQL

等同PIPES_AS_CONCAT、ANSI_QUOTES、IGNORE_SPACE、NO_KEY_OPTIONS、NO_TABLE_OPTIONS、NO_FIELD_OPTIONS。

·         TRADITIONAL

等同STRICT_TRANS_TABLES、STRICT_ALL_TABLES、NO_ZERO_IN_DATE、NO_ZERO_DATE、ERROR_FOR_DIVISION_BY_ZERO、NO_AUTO_CREATE_USER。

5.3.3. 服務器系統變量

服務器將維護許多表示其配置的系統變量。全部變量均有默認值。能夠在命令行中或選項文件設置選項在服務器啓動時對它們進行設置。大多數能夠在運行時使用SET語句來設置。

mysqld服務器維護兩種變量。全局變量影響服務器的全局操做。會話變量影響具體客戶端鏈接相關操做。

服務器啓動時,將全部全局變量初始化爲默認值。能夠在選項文件或命令行中指定的選項來更改這些默認值。服務器啓動後,經過鏈接服務器並執行SET GLOBAL var_name語句能夠更改動態全局變量。要想更改全局變量,必須具備SUPER權限。

服務器還爲每一個客戶端鏈接維護會話變量。鏈接時使用相應全局變量的當前值對客戶端會話變量進行初始化。客戶能夠經過SET SESSION var_name語句來更改動態會話變量。設置會話變量不須要特殊權限,但客戶能夠只更改本身的會話變量,而不更改其它客戶的會話變量。

任何訪問全局變量的客戶端均可以看見對全局變量的更改。可是,它隻影響在更改後鏈接的從該全局變量初始化相應會話變量的客戶端。它不會影響已經鏈接上的客戶端的會話變量(甚至是執行SET GLOBAL語句的客戶端)。

當使用啓動選項設置變量時,變量值能夠使用後綴K、M或G分別表示千字節、兆字節或gigabytes。例如,下面的命令啓動服務器時的鍵值緩衝區大小爲16 megabytes:

mysqld --key_buffer_size=16M

後綴的大小寫美關係;16M和16m是一樣的。

運行時,使用SET語句來設置系統變量。此時,不能使用後綴,但值能夠採起下列表達式:

mysql> SET sort_buffer_size = 10 * 1024 * 1024;

要想顯式指定是否設置全局或會話變量,使用GLOBAL或SESSION選項:

mysql> SET GLOBAL sort_buffer_size = 10 * 1024 * 1024;
mysql> SET SESSION sort_buffer_size = 10 * 1024 * 1024;

兩個選項均沒有,則語句設置會話變量。

5.3.3.1節,「動態系統變量」中列出了能夠在運行時設置的變量。

若是你想用SET語句限制系統變量可設的最大值,能夠在服務器啓動時經過--maximum-var_name形式的選項來指定。例如,要想防止query_cache_size的值運行時超過32MB,使用選項--maximum-query_cache_size=32M。

你能夠經過SHOW VARIABLES語句查看系統變量及其值。詳細信息參見9.4節,「系統變量」

mysql> SHOW VARIABLES;
+---------------------------------+-------------------------------------------+
| Variable_name                   | Value                                     |
+---------------------------------+-------------------------------------------+
| auto_increment_increment        | 1                                         |
| auto_increment_offset           | 1                                         |
| automatic_sp_privileges         | ON                                        |
| back_log                        | 50                                        |
| basedir                         | /home/jon/bin/mysql/                      |
| binlog_cache_size               | 32768                                     |
| bulk_insert_buffer_size         | 8388608                                   |
| character_set_client            | latin1                                    |
| character_set_connection        | latin1                                    |
| character_set_database          | latin1                                    |
| character_set_results           | latin1                                    |
| character_set_server            | latin1                                    |
| character_set_system            | utf8                                      |
| character_sets_dir              | /home/jon/bin/mysql/share/mysql/charsets/ |
| collation_connection            | latin1_swedish_ci                         |
| collation_database              | latin1_swedish_ci                         |
| collation_server                | latin1_swedish_ci                         |
| completion_type                 | 0                                         |
| concurrent_insert               | 1                                         |
| connect_timeout                 | 5                                         |
| datadir                         | /home/jon/bin/mysql/var/                  |
| date_format                     | %Y-%m-%d                                  |
| datetime_format                 | %Y-%m-%d %H:%i:%s                         |
| default_week_format             | 0                                         |
| delay_key_write                 | ON                                        |
| delayed_insert_limit            | 100                                       |
| delayed_insert_timeout          | 300                                       |
| delayed_queue_size              | 1000                                      |
| div_precision_increment         | 4                                         |
| engine_condition_pushdown       | OFF                                       |
| expire_logs_days                | 0                                         |
| flush                           | OFF                                       |
| flush_time                      | 0                                         |
| ft_boolean_syntax               | + -><()~*:""&|                            |
| ft_max_word_len                 | 84                                        |
| ft_min_word_len                 | 4                                         |
| ft_query_expansion_limit        | 20                                        |
| ft_stopword_file                | (built-in)                                |
| group_concat_max_len            | 1024                                      |
| have_archive                    | YES                                       |
| have_bdb                        | NO                                        |
| have_blackhole_engine           | YES                                       |
| have_compress                   | YES                                       |
| have_crypt                      | YES                                       |
| have_csv                        | YES                                       |
| have_example_engine             | NO                                        |
| have_federated_engine           | NO                                        |
| have_geometry                   | YES                                       |
| have_innodb                     | YES                                       |
| have_isam                       | NO                                        |
| have_ndbcluster                 | DISABLED                                  |
| have_openssl                    | NO                                        |
| have_partition_engine           | YES                                       |
| have_query_cache                | YES                                       |
| have_raid                       | NO                                        |
| have_rtree_keys                 | YES                                       |
| have_symlink                    | YES                                       |
| init_connect                    |                                           |
| init_file                       |                                           |
| init_slave                      |                                           |
| innodb_additional_mem_pool_size | 1048576                                   |
| innodb_autoextend_increment     | 8                                         |
| innodb_buffer_pool_awe_mem_mb   | 0                                         |
| innodb_buffer_pool_size         | 8388608                                   |
| innodb_checksums                | ON                                        |
| innodb_commit_concurrency       | 0                                         |
| innodb_concurrency_tickets      | 500                                       |
| innodb_data_file_path           | ibdata1:10M:autoextend                    |
| innodb_data_home_dir            |                                           |
| innodb_doublewrite              | ON                                        |
| innodb_fast_shutdown            | 1                                         |
| innodb_file_io_threads          | 4                                         |
| innodb_file_per_table           | OFF                                       |
| innodb_flush_log_at_trx_commit  | 1                                         |
| innodb_flush_method             |                                           |
| innodb_force_recovery           | 0                                         |
| innodb_lock_wait_timeout        | 50                                        |
| innodb_locks_unsafe_for_binlog  | OFF                                       |
| innodb_log_arch_dir             |                                           |
| innodb_log_archive              | OFF                                       |
| innodb_log_buffer_size          | 1048576                                   |
| innodb_log_file_size            | 5242880                                   |
| innodb_log_files_in_group       | 2                                         |
| innodb_log_group_home_dir       | ./                                        |
| innodb_max_dirty_pages_pct      | 90                                        |
| innodb_max_purge_lag            | 0                                         |
| innodb_mirrored_log_groups      | 1                                         |
| innodb_open_files               | 300                                       |
| innodb_support_xa               | ON                                        |
| innodb_sync_spin_loops          | 20                                        |
| innodb_table_locks              | ON                                        |
| innodb_thread_concurrency       | 20                                        |
| innodb_thread_sleep_delay       | 10000                                     |
| interactive_timeout             | 28800                                     |
| join_buffer_size                | 131072                                    |
| key_buffer_size                 | 8388600                                   |
| key_cache_age_threshold         | 300                                       |
| key_cache_block_size            | 1024                                      |
| key_cache_division_limit        | 100                                       |
| language                        | /home/jon/bin/mysql/share/mysql/english/  |
| large_files_support             | ON                                        |
| large_page_size                 | 0                                         |
| large_pages                     | OFF                                       |
| license                         | GPL                                       |
| local_infile                    | ON                                        |
| locked_in_memory                | OFF                                       |
| log                             | ON                                        |
| log_bin                         | ON                                        |
| log_bin_trust_routine_creators  | OFF                                       |
| log_error                       | /home/jon/bin/mysql/var/master1.err       |
| log_slave_updates               | OFF                                       |
| log_slow_queries                | OFF                                       |
| log_warnings                    | 1                                         |
| long_query_time                 | 10                                        |
| low_priority_updates            | OFF                                       |
| lower_case_file_system          | OFF                                       |
| lower_case_table_names          | 0                                         |
| max_allowed_packet              | 1048576                                   |
| max_binlog_cache_size           | 4294967295                                |
| max_binlog_size                 | 1073741824                                |
| max_connect_errors              | 10                                        |
| max_connections                 | 100                                       |
| max_delayed_threads             | 20                                        |
| max_error_count                 | 64                                        |
| max_heap_table_size             | 16777216                                  |
| max_insert_delayed_threads      | 20                                        |
| max_join_size                   | 4294967295                                |
| max_length_for_sort_data        | 1024                                      |
| max_relay_log_size              | 0                                         |
| max_seeks_for_key               | 4294967295                                |
| max_sort_length                 | 1024                                      |
| max_tmp_tables                  | 32                                        |
| max_user_connections            | 0                                         |
| max_write_lock_count            | 4294967295                                |
| multi_range_count               | 256                                       |
| myisam_data_pointer_size        | 6                                         |
| myisam_max_sort_file_size       | 2147483647                                |
| myisam_recover_options          | OFF                                       |
| myisam_repair_threads           | 1                                         |
| myisam_sort_buffer_size         | 8388608                                   |
| ndb_autoincrement_prefetch_sz   | 32                                        |
| ndb_cache_check_time            | 0                                         |
| ndb_force_send                  | ON                                        |
| ndb_index_stat_cache_entries    | 32                                        |
| ndb_index_stat_enable           | ON                                        |
| ndb_index_stat_update_freq      | 20                                        |
| ndb_use_exact_count             | ON                                        |
| ndb_use_transactions            | ON                                        |
| net_buffer_length               | 16384                                     |
| net_read_timeout                | 30                                        |
| net_retry_count                 | 10                                        |
| net_write_timeout               | 60                                        |
| new                             | OFF                                       |
| old_alter_table                 | OFF                                       |
| old_passwords                   | OFF                                       |
| open_files_limit                | 1024                                      |
| optimizer_prune_level           | 1                                         |
| optimizer_search_depth          | 62                                        |
| pid_file                        | /home/jon/bin/mysql/var/hostname.pid1     |
| port                            | 3306                                      |
| preload_buffer_size             | 32768                                     |
| protocol_version                | 10                                        |
| query_alloc_block_size          | 8192                                      |
| query_cache_limit               | 1048576                                   |
| query_cache_min_res_unit        | 4096                                      |
| query_cache_size                | 0                                         |
| query_cache_type                | ON                                        |
| query_cache_wlock_invalidate    | OFF                                       |
| query_prealloc_size             | 8192                                      |
| range_alloc_block_size          | 2048                                      |
| read_buffer_size                | 131072                                    |
| read_only                       | OFF                                       |
| read_rnd_buffer_size            | 262144                                    |
| relay_log_purge                 | ON                                        |
| relay_log_space_limit           | 0                                         |
| rpl_recovery_rank               | 0                                         |
| secure_auth                     | OFF                                       |
| server_id                       | 1                                         |
| skip_external_locking           | ON                                        |
| skip_networking                 | OFF                                       |
| skip_show_database              | OFF                                       |
| slave_compressed_protocol       | OFF                                       |
| slave_load_tmpdir               | /tmp/                                     |
| slave_net_timeout               | 3600                                      |
| slave_skip_errors               | OFF                                       |
| slave_transaction_retries       | 10                                        |
| slow_launch_time                | 2                                         |
| socket                          | /tmp/mysql.sock                           |
| sort_buffer_size                | 2097144                                   |
| sql_mode                        |                                           |
| sql_notes                       | ON                                        |
| sql_warnings                    | ON                                        |
| storage_engine                  | MyISAM                                    |
| sync_binlog                     | 0                                         |
| sync_frm                        | ON                                        |
| sync_replication                | 0                                         |
| sync_replication_slave_id       | 0                                         |
| sync_replication_timeout        | 10                                        |
| system_time_zone                | EST                                       |
| table_cache                     | 64                                        |
| table_lock_wait_timeout         | 50                                        |
| table_type                      | MyISAM                                    |
| thread_cache_size               | 0                                         |
| thread_stack                    | 196608                                    |
| time_format                     | %H:%i:%s                                  |
| time_zone                       | SYSTEM                                    |
| timed_mutexes                   | OFF                                       |
| tmp_table_size                  | 33554432                                  |
| tmpdir                          |                                           |
| transaction_alloc_block_size    | 8192                                      |
| transaction_prealloc_size       | 4096                                      |
| tx_isolation                    | REPEATABLE-READ                           |
| updatable_views_with_limit      | YES                                       |
| version                         | 5.1.2-alpha-log                           |
| version_comment                 | Source distribution                       |
| version_compile_machine         | i686                                      |
| version_compile_os              | suse-linux                                |
| wait_timeout                    | 28800                                     |
+---------------------------------+-------------------------------------------+
218 rows in set (0.03 sec)

此處描述了大多數系統變量。沒有版本的變量在全部MySQL 5.1 發佈中適用。關於其使用歷史信息,請參見MySQL 5.0參考指南MySQL 4.1參考指南。InnoDB系統變量列於 15.2.4節,「InnoDB啓動選項」

若沒有另行規定,緩衝區大小、長度和堆棧大小的單位均爲字節。

關於這些變量的調節信息參見7.5.2節,「調節服務器參數」

·         auto_increment_increment

auto_increment_increment和auto_increment_offset用於主服務器-主服務器(master-to-master)複製,並能夠用來控制AUTO_INCREMENT列的操做。兩個變量都可以設置爲全局或局部變量,而且假定每一個值均可覺得1到65,535之間的整數值。將其中一個變量設置爲0會使該變量爲1。若是試圖將這些變量設置爲大於65,535或小於0的值,則會將該值設置爲65,535。若是向將auto_increment_increment或auto_increment_offset設置爲非整數值,則會給出錯誤,而且變量的實際值在這種狀況下保持不變。

這兩個變量影響AUTO_INCREMENT列的方式:

o        auto_increment_increment控制列中的值的增量值。例如:

o                       mysql> SHOW VARIABLES LIKE 'auto_inc%';
o                       +--------------------------+-------+
o                       | Variable_name            | Value |
o                       +--------------------------+-------+
o                       | auto_increment_increment | 1     |
o                       | auto_increment_offset    | 1     |
o                       +--------------------------+-------+
o                       2 rows in set (0.00 sec)
o                      
o                       mysql> CREATE TABLE autoinc1 (col INT NOT NULL AUTO_INCREMENT PRIMARY KEY);
o                       Query OK, 0 rows affected (0.04 sec)
o                      
o                       mysql> SET @auto_increment_increment=10;
o                       Query OK, 0 rows affected (0.00 sec)
o                      
o                       mysql> SHOW VARIABLES LIKE 'auto_inc%';
o                       +--------------------------+-------+
o                       | Variable_name            | Value |
o                       +--------------------------+-------+
o                       | auto_increment_increment | 10    |
o                       | auto_increment_offset    | 1     |
o                       +--------------------------+-------+
o                       2 rows in set (0.01 sec)
o                      
o                       mysql> INSERT INTO autoinc1 VALUES (NULL), (NULL), (NULL), (NULL);
o                       Query OK, 4 rows affected (0.00 sec)
o                       Records: 4  Duplicates: 0  Warnings: 0
o                      
o                       mysql> SELECT col FROM autoinc1;
o                       +-----+
o                       | col |
o                       +-----+
o                       |   1 |
o                       |  11 |
o                       |  21 |
o                       |  31 |
o                       +-----+
o                       4 rows in set (0.00 sec)

(註明如何使用SHOW VARIABLES來獲取這些變量的當前值)。

o        auto_increment_offset肯定AUTO_INCREMENT列值的起點。假定在與前面的例子的相同的會話中執行下面的命令:

o                       mysql> SET @auto_increment_offset=5;
o                       Query OK, 0 rows affected (0.00 sec)
o                      
o                       mysql> SHOW VARIABLES LIKE 'auto_inc%';
o                       +--------------------------+-------+
o                       | Variable_name            | Value |
o                       +--------------------------+-------+
o                       | auto_increment_increment | 10    |
o                       | auto_increment_offset    | 5     |
o                       +--------------------------+-------+
o                       2 rows in set (0.00 sec)
o                      
o                       mysql> CREATE TABLE autoinc2 (col INT NOT NULL AUTO_INCREMENT PRIMARY KEY);
o                       Query OK, 0 rows affected (0.06 sec)
o                      
o                       mysql> INSERT INTO autoinc2 VALUES (NULL), (NULL), (NULL), (NULL);
o                       Query OK, 4 rows affected (0.00 sec)
o                       Records: 4  Duplicates: 0  Warnings: 0
o                      
o                       mysql> SELECT col FROM autoinc2;
o                       +-----+
o                       | col |
o                       +-----+
o                       |   5 |
o                       |  15 |
o                       |  25 |
o                       |  35 |
o                       +-----+
o                       4 rows in set (0.02 sec)
o                      

若是auto_increment_offset的值大於auto_increment_increment的值,則auto_increment_offset的值被忽略。

若是其中一個或兩個變量被更改了,而後更改插入到包含AUTO_INCREMENT列的表中的新行,結果可能看上去有問題,因爲計算AUTO_INCREMENT系列值時沒有考慮列內已經存在的值,而且插入的下一個值是列內最小的值,大於AUTO_INCREMENT列內已有的最大值。換句話說,數值的計算方法爲:

auto_increment_offset+ N * auto_increment_increment

其中N爲系列內的正整數值[1,2,3,...]。例如:

mysql> SHOW VARIABLES LIKE 'auto_inc%';
+--------------------------+-------+
| Variable_name            | Value |
+--------------------------+-------+
| auto_increment_increment | 10    |
| auto_increment_offset    | 5     |
+--------------------------+-------+
2 rows in set (0.00 sec)
 
mysql> SELECT col FROM autoinc1;
+-----+
| col |
+-----+
|   1 |
|  11 |
|  21 |
|  31 |
+-----+
4 rows in set (0.00 sec)
 
mysql> INSERT INTO autoinc1 VALUES (NULL), (NULL), (NULL), (NULL);
Query OK, 4 rows affected (0.00 sec)
Records: 4  Duplicates: 0  Warnings: 0
 
mysql> SELECT col FROM autoinc1;
+-----+
| col |
+-----+
|   1 |
|  11 |
|  21 |
|  31 |
|  35 |
|  45 |
|  55 |
|  65 |
+-----+
8 rows in set (0.00 sec)

auto_increment_increment和auto_increment_offset所示的值能夠生成系列5 + N * 10,即,[5,15,25,35,45,...]。在INSERT前col 列內最大的值爲31,AUTO_INCREMENT數列的下一個值爲35,所以col中插入的值從該點開始,結果如SELECT查詢所示。

必定要記住不可能將這兩個變量的結果限制到一個表中,所以不會替代其它數據庫管理系統提供的序列;這些變量控制MySQL服務器上all表AUTO_INCREMENT列的全部行爲。若是某個變量設爲全局變量,則只有經過局部設置將全局值更改和覆蓋後或mysqld重啓後其做用方可改變;若是局部設置,則新值影響全部表的AUTO_INCREMENT列,在這個會話期間當前用戶在這些表中插入了新行,除非在會話期間更改了這些值。

auto_increment_increment的 默認值爲1。參見6.12節,「多服務器複製中的Auto-Increment」

·         auto_increment_offset

該變量的默認值爲1。詳見auto_increment_increment的描述。

·         back_log

MySQL有的主要鏈接請求的數量。當主MySQL線程在短期內獲得許多鏈接請求時發揮做用。主線程須要花一些時間(儘管不多)來檢查鏈接並啓動一個新線程。back_log值說明MySQL臨時中止響應新請求前在短期內能夠堆起多少請求。若是你須要在短期內容許大量鏈接,能夠增長該數值。

換句話說,該值爲「進」TCP/IP鏈接幀聽隊列的大小。操做系統有該隊列本身的限制值。本手冊中Unix listen()系統調用頁應有更詳細的信息。該變量最大值請查閱OS文檔。企圖將back_log設置爲高於你的操做系統限值是徒勞無益的。

·         basedir

MySQL安裝基準目錄。能夠用--basedir選項設置該變量。

·         bdb_cache_size

爲BDB表緩存索引和行分配的緩衝區的大小。若是你不使用BDB表,你應用--skip-bdb啓動mysqld以便不浪費該緩存。

·         bdb_home

BDB表基準目錄。應與datadir變量的值相同。

·         bdb_log_buffer_size

爲BDB表緩存索引和行分配的緩衝區的大小。若是你不使用BDB表,你應將該值設置爲0或用--skip-bdb啓動mysqld以便不浪費該緩存。

·         bdb_logdir

BDB存儲引擎寫它日誌文件的目錄。能夠用--bdb-logdir選項設置該變量。

·         bdb_max_lock

在BDB表下能夠激活的最大鎖數(默認爲10,000)。若是當你執行長事務或當mysqld必須檢查許多行來計算查詢時出現下面的錯誤,你應增長該值:

bdb: Lock table is out of available locks
Got error 12 from ...

·         bdb_shared_data

若是你正使用--bdb-shared-data應爲ON。

·         bdb_tmpdir

--bdb-tmpdir選項的值。

 

·         binlog_cache_size

在事務過程當中容納二進制日誌SQL語句的緩存大小。二進制日誌緩存是服務器支持事務存儲引擎而且服務器啓用了二進制日誌(--log-bin選項)的前提下爲每一個客戶端分配的內存。若是你常用大的,多語句事務,你能夠增長該值以得到更有的性能。Binlog_cache_use和Binlog_cache_disk_use狀態變量能夠用來調整該變量的大小。參見5.11.3節,「二進制日誌」

·         bulk_insert_buffer_size

MyISAM 使用專用樹狀緩存來使INSERT ... SELECT、INSERT ... VALUES (...)、(...)、 ...和LOAD DATA INFILE的大塊插入更快。該變量用每線程的字節數限制緩存樹的大小。將它設置爲0禁用優化。釋:只有向非空表添加數據時才使用該緩存。 默認值是8MB。

·         character_set_client

來自客戶端的語句的字符集。

·         character_set_connection

用於沒有字符集導入符的文字和數字-字符串轉換。

·         character_set_database

默認數據庫使用的字符集。當默認數據庫更改時,服務器則設置該變量。若是沒有默認數據庫,變量的值同character_set_server。

·         character_set_results

用於向客戶端返回查詢結果的字符集。

·         character_set_ server

服務器的默認字符集。

·         character_set_system

服務器用來保存識別符的字符集。該值必定是utf8。

·         character_sets_dir

字符集安裝目錄。

·         collation_connection

鏈接字符集的校對規則。

·         collation_database

默認數據庫使用的校對規則。當默認數據庫改變時服務器則設置該變量。若是沒有默認數據庫,變量的值同collation_server。

·         collation_server

服務器的默認校對規則。

·         completion_type

事務結束類型:

o        若是該值爲0(默認),COMMIT和ROLLBACK不受影響。

o        若是該值爲1,COMMIT和ROLLBACK分別等同於COMMIT AND CHAIN和ROLLBACK AND CHAIN。(新事務用剛剛結束的事務相同的間隔等級當即啓動)。

o        若是該值爲2,COMMIT和ROLLBACK分別等同於COMM它RELEASE和ROLLBACK RELEASE。(事務終止後,服務器斷開)。

·         concurrent_insert

若是爲ON(默認值),MySQL容許INSERT和SELECT語句在中間沒有空數據塊的MyISAM表中並行運行。你能夠用--safe或--skip-new啓動mysqld關閉該選項。

該變量爲整數,有3個值:

描述

0

1

(默認)在沒有空數據塊的MyISAM表中啓用並行插入

2

爲全部MyISAM表啓用並行插入。若是表有空記錄或正被另外一線程使用,新行將插入到表的最後。若是表未使用,MySQL將進行普通讀鎖定並將新行插入空記錄。

·         connect_timeout

mysqld服務器用Bad handshake響應前等待鏈接包的秒數。

·         datadir

MySQL數據目錄。能夠用--datadir選項設置該變量。

·         date_format

該變量未使用。

·         datetime_format

該變量未使用。

·         default_week_format

WEEK() 函數使用的默認模式。

·         delay_key_write

該選項只適用MyISAM表。它具備下述值能夠影響CREATE TABLE語句使用的DELAY_KEY_WRITE表選項的處理。

選項

描述

OFF

DELAY_KEY_WRITE被忽略。

ON

MySQL在CREATE TABLE中用DELAY_KEY_WRITE選項。這是 默認值。

ALL

用啓用DELAY_KEY_WRITE選項建立表的相同方法對全部新打開表的進行處理。

若是啓用了DELAY_KEY_WRITE,說明使用該項的表的鍵緩衝區在每次更新索引時不被清空,只有關閉表時才清空。遮掩蓋能夠大大加快鍵的寫操做,但若是你使用該特性,你應用--myisam-recover選項啓動服務器,爲全部MyISAM表添加自動檢查(例如,--myisam-recover=BACKUP,FORCE)。參見5.3.1節,「mysqld命令行選項」15.1.1節,「MyISAM啓動選項」

請注意--external-locking不爲使用延遲鍵寫入的表提供索引破壞保護。

·         delayed_insert_limit

插入delayed_insert_limit 延遲行後,INSERT DELAYED 處理器線程檢查是否有掛起的SELECT語句。若是有,在繼續插入延遲的行以前,容許它們先執行。

·         delayed_insert_timeout

INSERT DELAYED處理器線程終止前應等待INSERT語句的時間。

·         delayed_queue_size

這是各個表中處理INSERT DELAYED語句時隊列中行的數量限制。若是隊列滿了,執行INSERT DELAYED語句的客戶端應等待直到隊列內再有空間。

·         div_precision_increment

該變量說明用/操做符執行除操做的結果可增長的精確度的位數。 默認值是4。最小和最大值分別爲0和30。下面的示例說明了增長 默認值的結果。

mysql> SELECT 1/7;
+--------+
| 1/7    |
+--------+
| 0.1429 |
+--------+
mysql> SET div_precision_increment = 12;
mysql> SELECT 1/7;
+----------------+
| 1/7            |
+----------------+
| 0.142857142857 |
+----------------+

·         engine_condition_pushdown

該變量適用於NDB。默認值爲0(OFF):若是你執行相似查詢SELECT * FROM t WHERE mycol = 42,其中mycol爲沒有索引的列,當滿了的表掃描每一個NDB節點時,執行該查詢。每一個節點使用WHERE條件將每一行發送給MySQL服務器。若是engine_condition_pushdown被設置爲1(ON),該條件「pushed down」給存儲引擎併發送給NDB節點。每一個節點都執行掃描,並只向MySQL服務器發送回匹配條件的行。

·         expire_logs_days

二進制日誌自動刪除的天數。默認值爲0,表示「沒有自動刪除」。啓動時和二進制日誌循環時可能刪除。

·         flush

若是用--flush選項啓動mysqld該值爲ON。

·         flush_time

若是設爲非零值,每隔flush_time秒則關閉全部表以釋放硬盤資源並同步未清空的數據。咱們建議只在Windows 9x或Me,或有最小資源的系統中使用該選項。

·         ft_boolean_syntax

使用IN BOOLEAN MODE執行的布爾全文搜索支持的操做符系列。參見12.7.1節,「布爾全文搜索」

默認變量值爲 '+ -><()~*:""&|'。更改這些值的規則是:

o        操做符函數由其在字符串內的位置決定。

o        替換值必須是14個字符。

o        每一個字符必須爲ASCII碼非文字數字字符。

o        第1個或第2個字符必須爲空格。

o        除非語句在第11個字符和第12個字符處引用了操做符,不然不容許複製。這兩個字符能夠不相同,但這是惟一可能的兩個。

o        位置十、13和14(默認設置爲‘:’、‘&’和‘|’)保留用於未來擴展。

·         ft_max_word_len

FULLTEXT索引中所包含的字的最大長度。

釋:更改該變量後必須重建FULLTEXT索引。應使用REPAIR TABLE tbl_name QUICK。

·         ft_min_word_len

FULLTEXT索引中所包含的字的最小長度。

釋:更改該變量後必須重建FULLTEXT索引。應使用REPAIR TABLE tbl_name QUICK。

·         ft_query_expansion_limit

使用WITH QUERY EXPANSION進行全文搜索的最大匹配數。

·         ft_stopword_file

用於讀取全文搜索的中止字清單的文件。該文件中的全部字都會用到;註釋不重要。默認狀況下,使用內嵌式中止字清單(如myisam/ft_static.c文件中所定義)。將該變量設置爲空字符串('')則禁用中止字過濾。

釋:更改該變量或中止字文件的內容後必須重建FULLTEXT索引。應使用REPAIR TABLE tbl_name QUICK。

·         group_concat_max_len

容許的GROUP_CONCAT()函數結果的最大長度。

·         have_archive

若是mysqld支持ARCHIVE表則爲YES,不然爲NO。

·         have_bdb

若是mysqld支持BDB表則爲YES。若是使用--skip-bdb則爲DISABLED。

·         have_blackhole_engine

若是mysqld支持BLACKHOLE表則爲YES,不然爲NO。

·         have_compress

是否zlib壓縮庫適合該服務器。若是不適合,不能使用COMPRESS()和UNCOMPRESS()函數。

·         have_crypt

是否crypt()系統調用適合該服務器。若是不適合,不能使用CRYPT()函數。

·         have_csv

若是mysqld支持ARCHIVE表則爲YES,不然爲NO。

·         have_example_engine

若是mysqld支持EXAMPLE表則爲YES,不然爲NO。

have_federated_engine

若是mysqld支持FEDERATED表則爲YES,不然爲NO。

·         have_geometry

是否服務器支持空間數據類型。

·         have_innodb

若是mysqld支持InnoDB表則爲YES。若是使用--skip-innodb則爲DISABLED。

·         have_isam

在MySQL 5.1中,只是爲了向後兼容顯示該值,而且老是NO,由於再也不支持ISAM表。

·         have_ndbcluster

若是mysqld支持NDB CLUSTER表則爲YES。若是使用了--skip-ndbcluster則爲DISABLED。

·         have_partition_engine

若是mysqld支持分區則爲YES。在MySQL 5.1.1中加入。

·         have_openssl

若是mysqld支持客戶端/服務器協議的SSL(加密)則爲YES。

·         have_query_cache

若是mysqld支持查詢緩存則爲YES。

·         have_raid

若是mysqld支持RAID選項則爲YES。

·         have_rtree_keys

RTREE索引是否可用。(用於MyISAM表的空間索引)。

·         have_symlink

是否啓用符號連接支持。在Unix中須要用於支持DATA DIRECTORY和INDEX DIRECTORY表選項。

·         init_connect

服務器爲每一個鏈接的客戶端執行的字符串。字符串由一個或多個SQL語句組成。要想指定多個語句,用分號間隔開。例如,每一個客戶端開始時默認啓用autocommit模式。沒有全局服務器變量能夠規定autocommit默認狀況下應禁用,但能夠用init_connect來得到相同的效果:

SET GLOBAL init_connect='SET AUTOCOMMIT=0';

還能夠在命令行或選項文件中設置該變量。要想使用選項文件設置變量,應包括下述行:

[mysqld]
init_connect='SET AUTOCOMMIT=0'

請注意init_connect的內容並不爲擁有SUPER權限的用戶執行;實際是內容設置錯誤(包含錯誤查詢,例如語法錯誤),這樣使全部鏈接失敗。不爲SUPER用戶執行,使SUPER用戶能夠打開鏈接並固定init_connect。

·         init_file

啓動服務器時用--init-file選項指定的文件名。文件中包含服務器啓動時要執行的SQL語句。每一個語句必須在同一行中而且不能包括註釋。

·         init_slave

該變量相似init_connect,可是每次SQL線程啓動時從服務器應執行該字符串。該字符串的格式與init_connect變量相同。

·         innodb_xxx

InnoDB系統變量列入15.2.4節,「InnoDB啓動選項」

·         interactive_timeout

服務器關閉交互式鏈接前等待活動的秒數。交互式客戶端定義爲在mysql_real_connect()中使用CLIENT_INTERACTIVE選項的客戶端。又見wait_timeout。

·         join_buffer_size

用於徹底聯接的緩衝區的大小(當不使用索引的時候使用聯接操做)。通常狀況得到快速聯接的最好方法是添加索引。當增長索引時不可能經過增長join_buffer_size值來得到快速徹底聯接。將爲兩個表之間的每一個徹底聯接分配聯接緩衝區。對於多個表之間不使用索引的複雜聯接,須要多聯接緩衝區。

·         key_buffer_size

MyISAM表的索引塊分配了緩衝區,由全部線程共享。key_buffer_size是索引塊緩衝區的大小。鍵值緩衝區即爲鍵值緩存。

key_buffer_size的最大容許設定值爲4GB。有效最大值能夠更小,取決於可用物理RAM和操做系統或硬件平臺強加的每一個進程的RAM限制。

增長該值,達到你能夠提供的更好的索引處理(全部讀和多個寫操做)。一般爲主要運行MySQL的機器內存的25%。可是,若是你將該值設得過大(例如,大於總內存的50%),系統將轉換爲頁並變得極慢。MySQL依賴操做系統來執行數據讀取時的文件系統緩存,所以你必須爲文件系統緩存留一些空間。

同時寫多行時要想速度更快,應使用LOCK TABLES。參見13.4.5節,「LOCK TABLES和UNLOCK TABLES語法」

你能夠經過執行SHOW STATUS語句並檢查Key_read_requests、Key_reads、Key_write_requests和Key_writes狀態變量來檢查鍵值緩衝區的性能。參見13.5.4節,「SHOW語法」

Key_reads/Key_read_requests比例通常應小於0.01。若是你使用更新和刪除,Key_writes/Key_write_requests比例一般接近1,但若是你更新時會同時影響到多行或若是你正使用DELAY_KEY_WRITE表選項,可能小得多。

用key_buffer_size結合Key_blocks_unused狀態變量和緩衝區塊大小,能夠肯定使用的鍵值緩衝區的比例。從key_cache_block_size服務器變量能夠得到緩衝區塊大小。使用的緩衝區的比例爲:

1 - ((Key_blocks_unused * key_cache_block_size) / key_buffer_size)

該值爲約數,由於鍵值緩衝區的部分空間被分配用做內部管理結構。

能夠建立多個MyISAM鍵值緩存。4GB限制能夠適合每一個緩存,而不是一個組。參見7.4.6節,「MyISAM鍵高速緩衝」

·         key_cache_age_threshold

該值控制將緩衝區從鍵值緩存熱子鏈(sub-chain)降級到溫子鏈(sub-chain)。若是值更低,則降級更快。最小值爲100。 默認值是300。參見7.4.6節,「MyISAM鍵高速緩衝」

·         key_cache_block_size

鍵值緩存內塊的字節大小。默認值是1024。參見7.4.6節,「MyISAM鍵高速緩衝」

·         key_cache_division_limit

鍵值緩存緩衝區鏈熱子鏈和溫子鏈的劃分點。該值爲緩衝區鏈用於溫子鏈的百分比。容許的值的範圍爲1到100。 默認值是100。參見7.4.6節,「MyISAM鍵高速緩衝」

·         language

錯誤消息所用語言。

·          large_file_support

mysqld編譯時是否使用了大文件支持選項。

·         large_pages

說明是否啓用了大頁面支持。

·         license

服務器的許可類型。

·         local_infile

是否LOCAL支持LOAD DATA INFILE語句。

·         locked_in_memory

是否用–memlock將mysqld鎖在內存中。

·         log

是否啓用將全部查詢記錄到常規查詢日誌中。參見5.11.2節,「通用查詢日誌」

·         log_bin

是否啓用二進制日誌。參見5.11.3節,「二進制日誌」

·         log_bin_trust_routine_creators

若啓用了二進制記錄,則該變量適用。它控制是否能夠信任保存的程序的做者不會建立向二進制日誌寫入不安全事件的程序。若是設置爲0(默認狀況),不容許用戶建立或修改保存的程序,除非他們不只擁有CREATE ROUTINE或ALTER ROUTINE權限還擁有SUPER權限。

設置爲0還強制限制,程序必須用DETERMINISTIC 特徵或用READS SQL DATA或NO SQL特徵聲明。若是變量設置爲1,MySQL不對保存程序的建立強加限制。

參見20.4節,「存儲子程序和觸發程序的二進制日誌功能」

·         log_error

錯誤日誌的位置。

·         log_slave_updates

是否從服務器從主服務器收到的更新應記入從服務器本身的二進制日誌。要想生效,必須啓用從服務器的二進制記錄。參見6.8節,「複製啓動選項」

·         log_slow_queries

是否記錄慢查詢。用long_query_time變量的值來肯定「慢查詢」。參見5.11.4節,「慢速查詢日誌」

·         log_warnings

是否產生其它警告消息。默認狀況下啓用。放棄的鏈接不記入錯誤日誌,除非值大於1。

·         long_query_time

若是查詢時間超過該值,則增長Slow_queries狀態變量。若是你正使用--log-slow-queries選項,則查詢記入慢查詢日誌文件。用實際時間測量該值,而不是CPU時間,所以低於輕負載系統閾值的查詢可能超太重負載系統的閾值。參見5.11.4節,「慢速查詢日誌」

·         low_priority_updates

若是設置爲1,全部INSERT、UPDATE、DELETE和LOCK TABLE WRITE語句將等待直到受影響的表沒有掛起的SELECT或LOCK TABLE READ。該變量之前叫作sql_low_priority_updates。

·         lower_case_file_system

該變量說明是否數據目錄所在的文件系統對文件名的大小寫敏感。ON說明對文件名的大小寫不敏感,OFF表示敏感。

·           lower_case_table_names

若是設置爲1,表名用小寫保存到硬盤上,而且表名比較時不對大小寫敏感。若是設置爲2,按照指定的保存表名,但按照小寫來比較。該選項還適合數據庫名和表的別名。參見9.2.2節,「識別符大小寫敏感性」

若是你正使用InnoDB表,你應在全部平臺上將該變量設置爲1,強制將名字轉換爲小寫。

若是運行MySQL的系統對文件名的大小寫不敏感(例如Windows或Mac OS X),你不該將該變量設置爲0。若是啓動時沒有設置該變量,而且數據目錄所在文件系統對文件名的大小寫不敏感,MySQL自動將lower_case_table_names設置爲2。

·         max_allowed_packet

包或任何生成的/中間字符串的最大大小。

包消息緩衝區初始化爲net_buffer_length字節,但須要時能夠增加到max_allowed_packet字節。該值默認很小,以捕獲大的(多是錯誤的)數據包。

若是你使用大的BLOB 列或長字符串,你必須增長該值。應同你想要使用的最大的BLOB同樣大。max_allowed_packet的協議限制爲1GB。

·         max_binlog_cache_size

若是多語句事務須要更大的內存,你會獲得錯誤Multi-statement transaction required more than 'max_binlog_cache_size' bytes of storage。

·         max_binlog_size

若是二進制日誌寫入的內容超出給定值,日誌就會發生滾動。你不能將該變量設置爲大於1GB或小於4096字節。 默認值是1GB。

請注意若是你正使用事務:事務以一個塊寫入二進制日誌,所以不不能被幾個二進制日誌拆分。所以,若是你有大的事務,二進制日誌可能會大於max_binlog_size。

若是max_relay_log_size爲0, max_binlog_size的值也適用於中繼日誌。

·         max_connect_errors

若是中斷的與主機的鏈接超過該數目,該主機則阻塞後面的鏈接。你能夠用 FLUSH HOSTS語句解鎖鎖定的主機。

·         max_connections

容許的並行客戶端鏈接數目。增大該值則增長mysqld 須要的文件描述符的數量。關於文件描述符限制的註釋參見7.4.9節,「MySQL如何打開和關閉表」。還可參見A.2.6節,「鏈接數過多」

·         max_delayed_threads

不要啓動大於該數目的線程來處理INSERT DELAYED語句。若是全部INSERT DELAYED線程已經在使用,你想在新表中插入數據,行 插入時好像未指定DELAYED屬性。若是你將該值設置爲0,MySQL不會建立線程來處理DELAYED行;其結果是徹底禁用了DELAYED。

·         max_error_count

保存由SHOW ERRORS或SHOW WARNINGS顯示的錯誤、警告和註解的最大數目。

·         max_heap_table_size

該變量設置MEMORY (HEAP)表能夠增加到的最大空間大小。該變量用來計算MEMORY表的MAX_ROWS值。在已有的MEMORY表上設置該變量沒有效果,除非用CREATE TABLE或TRUNCATE TABLE等語句從新建立表。

·         max_insert_delayed_threads

該變量爲max_delayed_threads的同義詞。

·         max_join_size

不容許可能須要檢查多於max_join_size行(爲單個表語句)或行組合(爲多個表語句)或可能執行大於max_join_size次硬盤查詢的SELECT語句。經過設置該值,你能夠捕獲鍵使用不正確並可能花很長時間的SELECT語句。若是用戶想要執行沒有WHERE子句的花較長時間或返回數百萬行的聯接,則設置它。

將該變量設置爲DEFAULT以外的值,將SQL_BIG_SELECTS的值重設爲0。若是你從新設置SQL_BIG_SELECTS值,max_join_size變量被忽略。

若是查詢結果位於查詢緩存中,則不檢查結果大小,由於前面已經計算告終果,不會要求服務器將它發送給客戶端。

該變量之前叫作sql_max_join_size。

·         max_length_for_sort_data

肯定使用的filesort算法的索引值大小的限值。參見7.2.12節,「MySQL如何優化ORDER BY

·         max_relay_log_size

若是複製從服務器寫入中繼日誌時超出給定值,則滾動中繼日誌。經過該變量你能夠對中繼日誌和二進制日誌設置不一樣的限制。可是,將該變量設置爲0,MySQL能夠對二進制日誌和中繼日誌使用max_binlog_size。max_relay_log_size必須設置在4096字節和1GB(包括)之間,或爲0。 默認值是0。參見6.3節,「複製實施細節」

·         max_seeks_for_key

限制根據鍵值尋找行時的最大搜索數。MySQL優化器假定當用掃描鍵在表內搜索匹配的行時,不須要超過該數量的鍵值搜索,而無論鍵的實際基數是什麼(參見13.5.4.11節,「SHOW INDEX語法」)。將該值設置爲較低的值(100?),你能夠強制MySQL選擇鍵值而不選擇表掃描。

·         max_sort_length

當排序BLOB或TEXT值時使用的字節數。只使用每一個值的前max_sort_length字節;其它的被忽略。

·         max_tmp_tables

客戶端能夠同時打開的臨時表的最大數。(但該選項還未生效)。

·         max_user_connections

任何給定的MySQL帳戶容許的最大同時鏈接數。0值表示「沒有限制」。

該變量具備全局範圍和(只讀)會話範圍。會話變量的的值與全局變量的值相同,除非當前帳戶具備非零MAX_USER_CONNECTIONS資源限制。在這種狀況下,會話值反應了帳戶限制。

·         max_write_lock_count

超過寫鎖定限制後,容許部分讀鎖定。

·         myisam_data_pointer_size

默認指針大小,單位是字節,當未指定MAX_ROWS選項時,CREATE TABLE使用該變量建立MyISAM表。該變量不能小於2或大於7。 默認值是6。參見A.2.11節,「表已滿」

·         (DEPRECATED) myisam_max_extra_sort_file_size

釋:MySQL 5.1不支持該變量。詳細信息參見MySQL 5.0 參考手冊

·         myisam_max_sort_file_size

重建MyISAM索引(在REPAIR TABLE、ALTER TABLE或LOAD DATA INFILE過程當中)時,容許MySQL使用的臨時文件的最大空間大小。若是文件的大小超過該值,則使用鍵值緩存建立索引,要慢得多。該值的單位爲字節。

·         myisam_recover_options

--myisam-recover選項的值。

·         myisam_repair_threads

若是該值大於1,在Repair by sorting過程當中並行建立MyISAM表索引(每一個索引在本身的線程內)。 默認值是1。釋:多線程維護仍然是alpha 編碼。

·         myisam_sort_buffer_size

當在REPAIR TABLE或用CREATE INDEX建立索引或ALTER TABLE過程當中排序 MyISAM索引分配的緩衝區。

·         myisam_stats_method

當爲MyISAM表蒐集關於索引值分發的統計信息時服務器如何處理NULL值。該變量有兩個可能的值,nulls_equal和nulls_unequal。對於nulls_equal,認爲全部NULL索引值時相等的,並造成一個數值組,其空間大小等於NULL值的數。對於nulls_unequal,NULL值認爲是不相等的,每一個NULL造成一個數值組,大小爲1。

方法用於生成表統計信息,影響優化器如何選擇索引來執行查詢,詳細描述見7.4.7節,「MyISAM索引統計集合」

·         multi_read_range

指定範圍選擇過程當中發送到存儲引擎的範圍的最大值。默認值是256。向引擎發送多個範圍能夠大大改進某些選擇的性能,特別是對NDBCLUSTER。該引擎須要向全部節點發送範圍請求,同時發送許多請求能夠大大下降通訊成本。

·         named_pipe

(只適用Windows)說明服務器是否支持命名管道鏈接。

·         net_buffer_length

在查詢之間將通訊緩衝區重設爲該值。通常狀況不該改變,但若是內存很小,能夠將它設置爲指望的客戶端發送的SQL語句的長度。若是語句超出該長度,緩衝區自動擴大,直到max_allowed_packet字節。

·         net_read_timeout

中斷讀前等待鏈接的其它數據的秒數。當服務器從客戶端讀數時,net_read_timeout指控制什麼時候中斷的超時值。當服務器向客戶端寫時,net_write_timeout指控制什麼時候中斷的超時值。又見slave_net_timeout。

·         net_retry_count

若是某個通訊端口的讀操做中斷了,在放棄前重試屢次。在FreeBSD中該值應設得很高,由於內部中斷將發送至全部線程。

·         net_write_timeout

中斷寫以前等待塊寫入鏈接的秒數。又見net_read_timeout。

·         new

在MySQL 4.0中使用該變量來打開4.1中的一些行爲,並用於向後兼容性。在MySQL 5.1中,它的值一直是OFF.

·         old_passwords

是否服務器應爲MySQL用戶帳戶使用pre-4.1-style密碼。參見A.2.3節,「客戶端不支持鑑定協議」

·         one_shot

這不是一個變量,但當設置變量是能夠使用它。其描述見13.5.3節,「SET語法」

·         one_shot

這不是一個變量,但當設置變量是能夠使用它。其描述見13.5.3節,「SET語法」

·         open_files_limit

操做系統容許mysqld打開的文件的數量。這是系統容許的實際值,可能與你在啓動選項中賦給mysqld的值不一樣。若在系統中MySQL不能更改打開的文件的數量,則該值爲0。

·         optimizer_prune_level

在查詢優化從優化器搜索空間裁減低但願局部計劃中使用的控制方法。0值禁用該方法,以便優化器進行窮舉搜索。值爲1使優化器根據中間方案中得出的行數來裁減方案。

·         optimizer_search_depth

查詢優化器進行的搜索的最大深度。若是值大於查詢中的關係數則查詢方案比較佳,但生成查詢執行方案須要的時間更長。值大於查詢中的關係數則返回的執行方案更快,但方案遠沒有優化。若是設置爲0, 系統自動選擇合理的值。若是設置爲查詢中使用的表的最大數加2,優化器轉換爲MySQL 5.0.0(和之前的版本)中使用的算法並搜索。

·         pid_file

進程ID (PID)文件的路徑名。能夠用--pid-file選項設置該變量。

·         plugin_dir

插件目錄的路徑。在MySQL 5.1.2中加入了該變量。

·         port

服務器幀聽TCP/IP鏈接所用端口。能夠用--port選項設置該變量。

·         preload_buffer_size

重載索引時分配的緩衝區大小。

·         protocol_version

MySQL服務器使用的客戶端/服務器協議的版本。

·         query_alloc_block_size

爲查詢分析和執行過程當中建立的對象分配的內存塊大小。若是內存分段過程當中遇到問題,將該變量增長一位會有幫助。

·         query_cache_limit

不要緩存大於該值的結果。默認值是1048576(1MB)。

·         query_cache_min_res_unit

查詢緩存分配的最小塊的大小(字節)。 默認值是4096(4KB)。關於該變量的調節信息參見5.13.3節,「查詢高速緩衝配置」

·         query_cache_size

爲緩存查詢結果分配的內存的數量。默認值是0,即禁用查詢緩存。請注意即便query_cache_type設置爲0也將分配此數量的內存。詳細信息參見5.13.3節,「查詢高速緩衝配置」

·         query_cache_type

設置查詢緩存類型。設置GLOBAL值能夠設置後面的全部客戶端鏈接的類型。客戶端能夠設置SESSION值以影響他們本身對查詢緩存的使用。下面的表顯示了可能的值:

選項

描述

0或OFF

不要緩存或查詢結果。請注意這樣不會取消分配的查詢緩存區。要想取消,你應將query_cache_size設置爲0。

1或ON

緩存除了以SELECT SQL_NO_CACHE開頭的全部查詢結果。

2或DEMAND

只緩存以SELECT SQL_NO_CACHE開頭的查詢結果。

該變量默認設爲ON。

·         query_cache_wlock_invalidate

通常狀況,當客戶端對MyISAM表進行WRITE鎖定時,若是查詢結果位於查詢緩存中,則其它客戶端未被鎖定,能夠對該表進行查詢。將該變量設置爲1,則能夠對錶進行WRITE鎖定,使查詢緩存內全部對該表進行的查詢變得非法。這樣當鎖定生效時,能夠強制其它試圖訪問表的客戶端來等待。

·         query_prealloc_size

用於查詢分析和執行的固定緩衝區的大小。在查詢之間該緩衝區不釋放。若是你執行復雜查詢,分配更大的query_prealloc_size值能夠幫助提升性能,由於它能夠下降查詢過程當中服務器分配內存的需求。

·         range_alloc_block_size

範圍優化時分配的塊的大小。

·         read_buffer_size

每一個線程連續掃描時爲掃描的每一個表分配的緩衝區的大小(字節)。若是進行屢次連續掃描,可能須要增長該值, 默認值爲131072。

·         read_only

當變量對複製從服務器設置爲ON時,從服務器不容許更新,除非經過從服務器的線程或用戶擁有SUPER權限。能夠確保從服務器不接受客戶端的更新命令。

·         relay_log_purge

當再也不須要中繼日誌時禁用或啓用自動清空中繼日誌。默認值是1(啓用)。

·         read_rnd_buffer_size

當排序後按排序後的順序讀取行時,則經過該緩衝區讀取行,避免搜索硬盤。將該變量設置爲較大的值能夠大大改進ORDER BY的性能。可是,這是爲每一個客戶端分配的緩衝區,所以你不該將全局變量設置爲較大的值。相反,只爲須要運行大查詢的客戶端更改會話變量。

·         secure_auth

若是用--secure-auth選項啓動了MySQL服務器,它將阻塞有舊格式(4.1以前)密碼的全部帳戶所發起的鏈接。在這種狀況下,該變量的值爲ON,不然爲OFF。

若是你想要防止使用舊格式的密碼(導致網絡通訊不安全),你應啓用該選項。

若是啓用該選項而且受權表爲pre-4.1格式,服務器啓動失敗而且會出現錯誤。參見A.2.3節,「客戶端不支持鑑定協議」

當用於客戶端選項時,若是服務器須要該客戶端帳戶的舊格式的密碼,則客戶端拒絕鏈接該服務器。

·         server_id

--server-id選項的值。用於主複製服務器和從複製服務器。

·         shared_memory

(只用於Windows)服務器是否容許共享內存鏈接。

·         shared_memory_base_name

(只用於Windows)說明服務器是否容許共享內存鏈接,併爲共享內存設置識別符。當在單臺機器上運行多個MySQL實例時頗有用。

·         skip_external_locking

若是mysqld使用外部鎖定,該值爲OFF。

·         skip_networking

若是服務器只容許本地(非TCP/IP)鏈接,該值爲ON。在Unix中,本地鏈接使用Unix套接字文件。在Windows中,本地鏈接使用命名管道或共享內存。在NetWare中,只支持TCP/IP鏈接,所以不要將該變量設置爲ON。

·         skip_show_database

防止不具備SHOW DATABASES權限的人們使用SHOW DATABASES語句。若是你擔憂用戶可以看見屬於其它用戶的數據庫,這樣設置能夠提升安全性。其效果取決於SHOW DATABASES權限:若是變量值爲ON,只容許具備SHOW DATABASES權限的人們使用SHOW DATABASES 語句,而且該語句將顯示全部數據庫名。若是值爲OFF,容許全部用戶執行SHOW DATABASES,但只顯示用戶具備SHOW DATABASES或其它權限的數據庫的名稱。

·         slave_compressed_protocol

若是主、從服務器均支持,肯定是否使用從/主壓縮協議。

·         slave_load_tmpdir

從服務器爲複製LOAD DATA INFILE語句建立臨時文件的目錄名。

·         slave_net_timeout

放棄讀操做前等待主/從鏈接的更多數據的等待秒數。

·         slave_skip_errors

從服務器應跳過(忽視)的複製錯誤。

·         slave_transaction_retries

若是因爲ofInnoDB死鎖或超過InnoDB的innodb_lock_wait_timeout或NDBCLUSTER的TransactionDeadlockDetectionTimeout或TransactionInactiveTimeout,複製從服務器SQL線程未能執行事務,在提示錯誤並中止前它自動重複slave_transaction_retries次。 默認值是10。

·         slow_launch_time

若是建立線程的時間超過該秒數,服務器增長Slow_launch_threads狀態變量。

·         socket

Unix平臺:用於本地客戶端鏈接的套接字文件。默認爲/var/lib/mysql/mysql.sock。

Windows:用於本地客戶端鏈接的命名管道名。默認爲mysql。

·         sort_buffer_size

每一個排序線程分配的緩衝區的大小。增長該值能夠加快ORDER BY或GROUP BY操做。參見A.4.4節,「MySQL將臨時文件儲存在哪裏」

·         sql_mode

當前的服務器SQL模式,能夠動態設置。參見5.3.2節,「SQL服務器模式」

·         sql_slave_skip_counter

從服務器應跳過的來自主服務器的事件數。

·         storage_engine

該變量是table_typeis的同義詞。在MySQL 5.1中,首選storage_engine。

·         sync_binlog

若是爲正,當每一個sync_binlog'th寫入該二進制日誌後,MySQL服務器將它的二進制日誌同步到硬盤上(fdatasync())。請注意若是在autocommit模式,每執行一個語句向二進制日誌寫入一次,不然每一個事務寫入一次。 默認值是0,不與硬盤同步。值爲1是最安全的選擇,由於崩潰時,你最多丟掉二進制日誌中的一個語句/事務;可是,這是最慢的選擇(除非硬盤有電池備份緩存,從而使同步工做較快)。

·         sync_frm

若是該變量設爲1,當建立非臨時表時它的.frm文件被同步到硬盤上(fdatasync());這樣較慢但出現崩潰時較安全。 默認值爲1。

·         system_time_zone

服務器系統時區。當 服務器開始執行時,它繼承機器默認時區設置值,能夠由運行服務器的帳戶或在啓動腳本中進行修改。該值用來設置system_time_zone。典型狀況用TZ環境變量來指定時區。還能夠用mysqld_safe腳本的--timez選項來指定。

·         table_cache

全部線程打開的表的數目。增大該值能夠增長mysqld須要的文件描述符的數量。你能夠檢查Opened_tables狀態變量來檢查你是否須要增長表緩存。參見5.3.4節,「服務器狀態變量」。若是Opened_tables值較大,而且屢次執行FLUSH TABLES(只是強制關閉全部表並從新),則應增長table_cache變量的值。

關於表緩存的詳細信息,參見7.4.9節,「MySQL如何打開和關閉表」

·         table_type

默認表類型(存儲引擎)。要想在服務器啓動時設置表類型,使用--default-table-type選項。參見5.3.1節,「mysqld命令行選項」

·         thread_cache_size

服務器應緩存多少線程以便從新使用。當客戶端斷開鏈接時,若是線程少於thread_cache_size,則客戶端的線程被放入緩存。當請求線程時若是容許能夠從緩存中從新利用線程,而且只有當緩存空了時纔會建立新線程。若是新鏈接不少,能夠增長該變量以提升性能。(通常狀況,若是線程執行得很好,性能提升不明顯)。檢查Connections和Threads_created狀態變量的差(詳見5.3.4節,「服務器狀態變量」),你能夠看見線程緩存的效率。

·         thread_concurrency

在Solaris中,mysqld用該值調用thr_setconcurrency()。該函數使應用程序向線程系統提供須要同時運行的指望的線程數目的提示。

·         thread_stack

每一個線程的堆棧大小。用crash-me測試檢測出的許多限制取決於該值。 默認值足夠大,能夠知足普通操做。參見7.1.4節,「MySQL基準套件」

·         time_format

該變量爲使用。

·         time_zone

當前的時區。初使值是'SYSTEM'(使用system_time_zone的值),但能夠用--default-time-zone選項在服務器啓動時顯式指定。

·         tmp_table_size

若是內存內的臨時表超過該值,MySQL自動將它轉換爲硬盤上的MyISAM表。若是你執行許多高級GROUP BY查詢而且有大量內存,則能夠增長tmp_table_size的值。

·         tmpdir

保存臨時文件和臨時表的目錄。該變量能夠設置爲幾個路徑,按round-robin模式使用。在Unix中應該用冒號(‘:’)間隔開路徑,在Windows、NetWare和OS/2中用分號(‘;’)。

用來將負荷分散到幾個物理硬盤上。若是MySQL服務器爲複製從服務器,你不該將tmpdir設置爲指向基於內存的文件系統上的目錄或當服務器主機重啓時聲明的目錄。複製從服務器須要部分臨時文件來在機器重啓後仍可用,以便它能夠複製臨時表或執行LOAD DATA INFILE操做。若是服務器重啓時臨時文件夾中的文件丟失了,則複製失敗。可是,若是你使用MySQL 4.0.0或更新版本,你能夠使用 slave_load_tmpdir變量設置從服務器的臨時目錄。在這種狀況下,從服務器再也不使用常規tmpdir,說明你能夠將tmpdir設置到一個非固定位置。

·         transaction_alloc_block_size

爲保存將保存到二進制日誌中的事務的查詢而分配的內存塊的大小(字節)。

·         transaction_prealloc_size

爲transaction_alloc_blocks分配的固定緩衝區的大小(字節),在兩次查詢之間不會釋放。使該值足夠大,將全部查詢固定到一個事務中,能夠避免屢次malloc()調用。

·         tx_isolation

默認事務隔離級別。默認值爲REPEATABLE-READ。

·         updatable_views_with_limit

該變量控制若是更新包含LIMIT子句,是否能夠在當前表中使用不包含主關鍵字的視圖進行更新。(一般用GUI工具生成這類更新)。更新指UPDATE或DELETE語句。這兒主關鍵字指PRIMARY KEY,或一個UNIQUE索引,其中任何列不能夠包含NULL。

該變量有兩個值:

o        1或YES:只發出警告(沒有錯誤消息)。這是 默認值。

o        0或NO:禁止更新。

·         version

服務器版本號。

·         version_bdb

BDB存儲引擎版本。

·         version_comment

configure腳本有一個--with-comment選項,當構建MySQL時能夠進行註釋。該變量包含註釋值。

·         version_compile_machine

MySQL構建的機器或架構的類型。

·         version_compile_os

MySQL構建的操做系統的類型。

·         wait_timeout

服務器關閉非交互鏈接以前等待活動的秒數。

在線程啓動時,根據全局wait_timeout值或全局interactive_timeout值初始化會話wait_timeout值,取決於客戶端類型(由mysql_real_connect()的鏈接選項CLIENT_INTERACTIVE定義)。又見interactive_timeout。

5.3.3.1. 動態系統變量

許多服務器系統變量是動態的,能夠使用SET GLOBAL或SET SESSION在運行時設置。你還能夠使用SELECT得到它們的值。參見9.4節,「系統變量」

下面的表列出了全部動態系統變量。最後1列說明每一個變量是否適用GLOBAL或SESSION(或兩者)。

變量名

值類型

類型

autocommit

boolean

SESSION

big_tables

boolean

SESSION

binlog_cache_size

numeric

GLOBAL

bulk_insert_buffer_size

numeric

GLOBAL | SESSION

character_set_client

string

GLOBAL | SESSION

character_set_connection

string

GLOBAL | SESSION

character_set_results

string

GLOBAL | SESSION

character_set_server

string

GLOBAL | SESSION

collation_connection

string

GLOBAL | SESSION

collation_server

string

GLOBAL | SESSION

completion_type

numeric

GLOBAL | SESSION

concurrent_insert

boolean

GLOBAL

connect_timeout

numeric

GLOBAL

convert_character_set

string

GLOBAL | SESSION

default_week_format

numeric

GLOBAL | SESSION

delay_key_write

OFF | ON | ALL

GLOBAL

delayed_insert_limit

numeric

GLOBAL

delayed_insert_timeout

numeric

GLOBAL

delayed_queue_size

numeric

GLOBAL

div_precision_increment

numeric

GLOBAL | SESSION

engine_condition_pushdown

boolean

GLOBAL | SESSION

error_count

numeric

SESSION

expire_logs_days

numeric

GLOBAL

flush

boolean

GLOBAL

flush_time

numeric

GLOBAL

foreign_key_checks

boolean

SESSION

ft_boolean_syntax

numeric

GLOBAL

group_concat_max_len

numeric

GLOBAL | SESSION

identity

numeric

SESSION

innodb_autoextend_increment

numeric

GLOBAL

innodb_concurrency_tickets

numeric

GLOBAL

innodb_max_dirty_pages_pct

numeric

GLOBAL

innodb_max_purge_lag

numeric

GLOBAL

innodb_support_xa

boolean

GLOBAL | SESSION

innodb_sync_spin_loops

numeric

GLOBAL

innodb_table_locks

boolean

GLOBAL | SESSION

innodb_thread_concurrency

numeric GLOBAL

 

innodb_thread_sleep_delay

numeric GLOBAL

 

insert_id

boolean

SESSION

interactive_timeout

numeric

GLOBAL | SESSION

join_buffer_size

numeric

GLOBAL | SESSION

key_buffer_size

numeric

GLOBAL

last_insert_id

numeric

SESSION

local_infile

boolean

GLOBAL

log_warnings

numeric

GLOBAL

long_query_time

numeric

GLOBAL | SESSION

low_priority_updates

boolean

GLOBAL | SESSION

max_allowed_packet

numeric

GLOBAL | SESSION

max_binlog_cache_size

numeric

GLOBAL

max_binlog_size

numeric

GLOBAL

max_connect_errors

numeric

GLOBAL

max_connections

numeric

GLOBAL

max_delayed_threads

numeric

GLOBAL

max_error_count

numeric

GLOBAL | SESSION

max_heap_table_size

numeric

GLOBAL | SESSION

max_insert_delayed_threads

numeric

GLOBAL

max_join_size

numeric

GLOBAL | SESSION

max_relay_log_size

numeric

GLOBAL

max_seeks_for_key

numeric

GLOBAL | SESSION

max_sort_length

numeric

GLOBAL | SESSION

max_tmp_tables

numeric

GLOBAL | SESSION

max_user_connections

numeric

GLOBAL

max_write_lock_count

numeric

GLOBAL

myisam_stats_method

enum

GLOBAL | SESSION

multi_read_range

numeric

GLOBAL | SESSION

myisam_data_pointer_size

numeric

GLOBAL

log_bin_trust_routine_creators

boolean

GLOBAL

myisam_max_sort_file_size

numeric

GLOBAL | SESSION

myisam_repair_threads

numeric

GLOBAL | SESSION

myisam_sort_buffer_size

numeric

GLOBAL | SESSION

net_buffer_length

numeric

GLOBAL | SESSION

net_read_timeout

numeric

GLOBAL | SESSION

net_retry_count

numeric

GLOBAL | SESSION

net_write_timeout

numeric

GLOBAL | SESSION

old_passwords

numeric

GLOBAL | SESSION

optimizer_prune_level

numeric

GLOBAL | SESSION

optimizer_search_depth

numeric

GLOBAL | SESSION

preload_buffer_size

numeric

GLOBAL | SESSION

query_alloc_block_size

numeric

GLOBAL | SESSION

query_cache_limit

numeric

GLOBAL

query_cache_size

numeric

GLOBAL

query_cache_type

enumeration

GLOBAL | SESSION

query_cache_wlock_invalidate

boolean

GLOBAL | SESSION

query_prealloc_size

numeric

GLOBAL | SESSION

range_alloc_block_size

numeric

GLOBAL | SESSION

read_buffer_size

numeric

GLOBAL | SESSION

read_only

numeric

GLOBAL

read_rnd_buffer_size

numeric

GLOBAL | SESSION

rpl_recovery_rank

numeric

GLOBAL

safe_show_database

boolean

GLOBAL

secure_auth

boolean

GLOBAL

server_id

numeric

GLOBAL

slave_compressed_protocol

boolean

GLOBAL

slave_net_timeout

numeric

GLOBAL

slave_transaction_retries

numeric

GLOBAL

slow_launch_time

numeric

GLOBAL

sort_buffer_size

numeric

GLOBAL | SESSION

sql_auto_is_null

boolean

SESSION

sql_big_selects

boolean

SESSION

sql_big_tables

boolean

SESSION

sql_buffer_result

boolean

SESSION

sql_log_bin

boolean

SESSION

sql_log_off

boolean

SESSION

sql_log_update

boolean

SESSION

sql_low_priority_updates

boolean

GLOBAL | SESSION

sql_max_join_size

numeric

GLOBAL | SESSION

sql_mode

enumeration

GLOBAL | SESSION

sql_notes

boolean

SESSION

sql_quote_show_create

boolean

SESSION

sql_safe_updates

boolean

SESSION

sql_select_limit

numeric

SESSION

sql_slave_skip_counter

numeric

GLOBAL

updatable_views_with_limit

enumeration

GLOBAL | SESSION

sql_warnings

boolean

SESSION

sync_binlog

numeric

GLOBAL

sync_frm

boolean

GLOBAL

storage_engine

enumeration

GLOBAL | SESSION

table_cache

numeric

GLOBAL

table_type

enumeration

GLOBAL | SESSION

thread_cache_size

numeric

GLOBAL

time_zone

string

GLOBAL | SESSION

timestamp

boolean

SESSION

tmp_table_size

enumeration

GLOBAL | SESSION

transaction_alloc_block_size

numeric

GLOBAL | SESSION

transaction_prealloc_size

numeric

GLOBAL | SESSION

tx_isolation

enumeration

GLOBAL | SESSION

unique_checks

boolean

SESSION

wait_timeout

numeric

GLOBAL | SESSION

warning_count

numeric

SESSION

標記爲string的變量採用字符串值。標記爲numeric的變量採用數字值。標記爲boolean的變量能夠設置爲0、一、ON或OFF。標記爲enumeration的變量通常狀況應設置爲該變量的某個可用值,但還能夠設置爲對應指望的枚舉值的數字。對於枚舉系統變量,第1個枚舉值應對應0。這不一樣於ENUM列,第1個枚舉值對應1。

5.3.4. 服務器狀態變量

服務器維護許多提供操做相關信息的狀態變量。你能夠經過SHOW STATUS語句查看這些變量和它們的值:

mysql> SHOW STATUS;
+-----------------------------------+------------+
| Variable_name                     | Value      |
+-----------------------------------+------------+
| Aborted_clients                   | 0          |
| Aborted_connects                  | 0          |
| Bytes_received                    | 155372598  |
| Bytes_sent                        | 1176560426 |
 
 
| Connections                       | 30023      |
| Created_tmp_disk_tables           | 0          |
| Created_tmp_files                 | 3          |
| Created_tmp_tables                | 2          |
 
 
| Threads_created                   | 217        |
| Threads_running                   | 88         |
| Uptime                            | 1389872    |
+-----------------------------------+------------+
 

用FLUSH STATUS語句能夠將許多狀態變量重設爲0。

狀態變量有如下含義。沒有指示版本的變量在MySQL 5.1以前已經出現。關於它們的使用歷史,參見MySQL 5.0參考手冊

·         Aborted_clients

因爲客戶端沒有正確關閉鏈接致使客戶端終止而中斷的鏈接數。參見A.2.10節,「通訊錯誤和失效鏈接」

·         Aborted_connects

試圖鏈接到MySQL服務器而失敗的鏈接數。參見A.2.10節,「通訊錯誤和失效鏈接」

·         Binlog_cache_disk_use

使用臨時二進制日誌緩存但超過binlog_cache_size值並使用臨時文件來保存事務中的語句的事務數量。

·         Binlog_cache_use

使用臨時二進制日誌緩存的事務數量。

·         Bytes_received

從全部客戶端接收到的字節數。

·         Bytes_sent

發送給全部客戶端的字節數。

·         Com_xxx

Com_xxx 語句計數變量表示每一個xxx 語句執行的次數。每類語句有一個狀態變量。例如,Com_delete和Com_insert分別統計DELETE 和INSERT語句執行的次數。

Com_stmt_xxx狀態變量爲:

o        Com_stmt_prepare

o        Com_stmt_execute

o        Com_stmt_fetch

o        Com_stmt_send_long_data

o        Com_stmt_reset

o        Com_stmt_close

這些變量表明準備好的語句命令。它們的名字對應網絡層使用的COM_xxx 命令系列;換句話說:當準備好的語句API調用如mysql_stmt_prepare()mysql_stmt_執行()並執行時,它們的值增長。可是,當執行下面的SQL語句時,Com_stmt_prepare, Com_stmt_execute和Com_stmt_close也增長:PREPARE、EXECUTE或DEALLOCATE PREPARE。此外,舊(從MySQL 4.1.3起可用)語句計數變量Com_prepare_sql、Com_execute_sql和Com_dealloc_sql的值也隨PREPARE、EXECUTE和DEALLOCATE PREPARE語句增長。Com_stmt_fetch表明經過光標獲取的網絡round-trips的總數量。

全部Com_stmt_xxx變量將增長,即便語句參數未知或執行過程當中出現錯誤。換句話說,它們的值對應發出的請求數,而不是成功完成的請求數。

·         Connections

試圖鏈接到(無論是否成功)MySQL服務器的鏈接數。

·         Created_tmp_disk_tables

服務器執行語句時在硬盤上自動建立的臨時表的數量。

·         Created_tmp_files

mysqld已經建立的臨時文件的數量。

·         Created_tmp_files

服務器執行語句時自動建立的內存中的臨時表的數量。若是Created_tmp_disk_tables較大,你可能要增長tmp_table_size值使臨時 表基於內存而不基於硬盤。

·         Delayed_errors

用INSERT DELAYED寫的出現錯誤的行數(可能爲duplicate key)。

·         Delayed_insert_threads

使用的INSERT DELAYED處理器線程數。

·         Delayed_writes

寫入的INSERT DELAYED行數。

·         Flush_commands

執行的FLUSH語句數。

·         Handler_commit

內部提交語句數。

·         Handler_discover

MySQL服務器能夠問NDB CLUSTER存儲引擎是否知道某一名字的表。這被稱做發現。Handler_discover說明經過該方法發現的次數。

·         Handler_delete

行從表中刪除的次數。

·         Handler_read_first

索引中第一條被讀的次數。若是較高,它建議服務器正執行大量全索引掃描;例如,SELECT col1 FROM foo,假定col1有索引。

·         Handler_read_key

根據鍵讀一行的請求數。若是較高,說明查詢和表的索引正確。

·         Handler_read_next

按照鍵順序讀下一行的請求數。若是你用範圍約束或若是執行索引掃描來查詢索引列,該值增長。

·         Handler_read_prev

按照鍵順序讀前一行的請求數。該讀方法主要用於優化ORDER BY ... DESC。

·         Handler_read_rnd

根據固定位置讀一行的請求數。若是你正執行大量查詢並須要對結果進行排序該值較高。你可能使用了大量須要MySQL掃描整個表的查詢或你的鏈接沒有正確使用鍵。

·         Handler_read_rnd_next

在數據文件中讀下一行的請求數。若是你正進行大量的表掃描,該值較高。一般說明你的表索引不正確或寫入的查詢沒有利用索引。

·         Handler_rollback

內部ROLLBACK語句的數量。

·         Handler_update

在表內更新一行的請求數。

·         Handler_write

在表內插入一行的請求數。

·         Innodb_buffer_pool_pages_data

包含數據的頁數(髒或乾淨)。

·         Innodb_buffer_pool_pages_dirty

當前的髒頁數。

·         Innodb_buffer_pool_pages_flushed

要求清空的緩衝池頁數。

·         Innodb_buffer_pool_pages_free

空頁數。

·         Innodb_buffer_pool_pages_latched

在InnoDB緩衝池中鎖定的頁數。這是當前正讀或寫或因爲其它緣由不能清空或刪除的頁數。

·           Innodb_buffer_pool_pages_misc

忙的頁數,由於它們已經被分配優先用做管理,例如行鎖定或適用的哈希索引。該值還能夠計算爲Innodb_buffer_pool_pages_total - Innodb_buffer_pool_pages_free - Innodb_buffer_pool_pages_data。

·         Innodb_buffer_pool_pages_total

緩衝池總大小(頁數)。

·         Innodb_buffer_pool_read_ahead_rnd

InnoDB初始化的「隨機」read-aheads數。當查詢以隨機順序掃描表的一大部分時發生。

·         Innodb_buffer_pool_read_ahead_seq

InnoDB初始化的順序read-aheads數。當InnoDB執行順序全表掃描時發生。

·         Innodb_buffer_pool_read_requests

InnoDB已經完成的邏輯讀請求數。

·         Innodb_buffer_pool_reads

不能知足InnoDB必須單頁讀取的緩衝池中的邏輯讀數量。

·         Innodb_buffer_pool_wait_free

通常狀況,經過後臺向InnoDB緩衝池寫。可是,若是須要讀或建立頁,而且沒有乾淨的頁可用,則它還須要先等待頁面清空。該計數器對等待實例進行記數。若是已經適當設置緩衝池大小,該值應小。

·         Innodb_buffer_pool_write_requests

向InnoDB緩衝池的寫數量。

·         Innodb_data_fsyncs

fsync()操做數。

·         Innodb_data_pending_fsyncs

當前掛起的fsync()操做數。

·         Innodb_data_pending_reads

當前掛起的讀數。

·         Innodb_data_pending_writes

當前掛起的寫數。

·         Innodb_data_read

至此已經讀取的數據數量(字節)。

·         Innodb_data_reads

數據讀總數量。

·         Innodb_data_writes

數據寫總數量。

·         Innodb_data_written

至此已經寫入的數據量(字節)。

·         Innodb_dblwr_writes, Innodb_dblwr_pages_written

已經執行的雙寫操做數量和爲此目的已經寫好的頁數。參見15.2.14.1節,「磁盤I/O」

·         Innodb_log_waits

咱們必須等待的時間,由於日誌緩衝區過小,咱們在繼續前必須先等待對它清空。

·         Innodb_log_write_requests

日誌寫請求數。

·         Innodb_log_writes

向日志文件的物理寫數量。

·         Innodb_os_log_fsyncs

向日志文件完成的fsync()寫數量。

·         Innodb_os_log_pending_fsyncs

掛起的日誌文件fsync()操做數量。

·         Innodb_os_log_pending_writes

掛起的日誌文件寫操做。

·         Innodb_os_log_written

寫入日誌文件的字節數。

·         Innodb_page_size

編譯的InnoDB頁大小(默認16KB)。許多值用頁來記數;頁的大小很容易轉換爲字節。

·         Innodb_pages_created

建立的頁數。

·         Innodb_pages_read

讀取的頁數。

·         Innodb_pages_written

寫入的頁數。

·         Innodb_row_lock_current_waits

當前等待的待鎖定的行數。

·         Innodb_row_lock_time

行鎖定花費的總時間,單位毫秒。

·         Innodb_row_lock_time_avg

行鎖定的平均時間,單位毫秒。

·         Innodb_row_lock_time_max

行鎖定的最長時間,單位毫秒。

·         Innodb_row_lock_waits

一行鎖定必須等待的時間數。

·         Innodb_rows_deleted

從InnoDB表刪除的行數。

·         Innodb_rows_inserted

插入到InnoDB表的行數。

·         Innodb_rows_read

從InnoDB表讀取的行數。

·         Innodb_rows_updated

InnoDB表內更新的行數。

·         Key_blocks_not_flushed

鍵緩存內已經更改但尚未清空到硬盤上的鍵的數據塊數量。

·         Key_blocks_unused

鍵緩存內未使用的塊數量。你能夠使用該值來肯定使用了多少鍵緩存;參見5.3.3節,「服務器系統變量」中Key_buffer_size的討論。

·         Key_blocks_used

鍵緩存內使用的塊數量。該值爲高水平線標記,說明已經同時最多使用了多少塊。

·         Key_read_requests

從緩存讀鍵的數據塊的請求數。

·         Key_reads

從硬盤讀取鍵的數據塊的次數。若是Key_reads較大,則Key_buffer_size值可能過小。能夠用Key_reads/Key_read_requests計算緩存損失率。

·         Key_write_requests

將鍵的數據塊寫入緩存的請求數。

·         Key_writes

向硬盤寫入將鍵的數據塊的物理寫操做的次數。

·         Last_query_cost

用查詢優化器計算的最後編譯的查詢的總成本。用於對比同一查詢的不一樣查詢方案的成本。默認值0表示尚未編譯查詢。 默認值是0。Last_query_cost具備會話範圍。

·         Max_used_connections

服務器啓動後已經同時使用的鏈接的最大數量。

·         Not_flushed_delayed_rows

等待寫入INSERT DELAY隊列的行數。

·         Open_files

打開的文件的數目。

·         Open_streams

打開的流的數量(主要用於記錄)。

·         Open_tables

當前打開的表的數量。

·         Opened_tables

已經打開的表的數量。若是Opened_tables較大,table_cache 值可能過小。

·         QCACHE_free_blocks

查詢緩存內自由內存塊的數量。

·         QCACHE_free_memory

用於查詢緩存的自由內存的數量。

·         QCACHE_hits

查詢緩存被訪問的次數。

·         QCACHE_inserts

加入到緩存的查詢數量。

·         QCACHE_lowmem_prunes

因爲內存較少從緩存刪除的查詢數量。

·         QCACHE_not_cached

非緩存查詢數(不可緩存,或因爲query_cache_type設定值未緩存)。

·         Qcache_queries_in_cache

登記到緩存內的查詢的數量。

·         Qcache_total_blocks

查詢緩存內的總塊數。

·         Questions

已經發送給服務器的查詢的個數。

·         Rpl_status

失敗安全複製狀態(還未使用)。

·         Select_full_join

沒有使用索引的聯接的數量。若是該值不爲0,你應仔細檢查表的索引。

·         Select_full_range_join

在引用的表中使用範圍搜索的聯接的數量。

·         Select_range

在第一個表中使用範圍的聯接的數量。通常狀況不是關鍵問題,即便該值至關大。

·         Select_range_check

在每一行數據後對鍵值進行檢查的不帶鍵值的聯接的數量。若是不爲0,你應仔細檢查表的索引。

·         Select_scan

對第一個表進行徹底掃描的聯接的數量。

·         Slave_open_temp_tables

當前由從SQL線程打開的臨時表的數量。

·         Slave_running

若是該服務器是鏈接到主服務器的從服務器,則該值爲ON。

·         Slave_retried_transactions

啓動後複製從服務器SQL線程嘗試事務的總次數。

·         Slow_launch_threads

建立時間超過slow_launch_time秒的線程數。

·         Slow_queries

查詢時間超過long_query_time秒的查詢的個數。參見5.11.4節,「慢速查詢日誌」

·         Sort_merge_passes

排序算法已經執行的合併的數量。若是這個變量值較大,應考慮增長sort_buffer_size系統變量的值。

·         Sort_range

在範圍內執行的排序的數量。

·         Sort_rows

已經排序的行數。

·         Sort_scan

經過掃描表完成的排序的數量。

·         Ssl_xxx

用於SSL鏈接的變量。

·         Table_locks_immediate

當即得到的表的鎖的次數。

·         Table_locks_waited

不能當即得到的表的鎖的次數。若是該值較高,而且有性能問題,你應首先優化查詢,而後拆分表或使用複製。

·         Threads_cached

線程緩存內的線程的數量。

·         Threads_connected

當前打開的鏈接的數量。

·         Threads_created

建立用來處理鏈接的線程數。若是Threads_created較大,你可能要增長thread_cache_size值。緩存訪問率的計算方法Threads_created/Connections。

·           Threads_running

激活的(非睡眠狀態)線程數。

·         Uptime

服務器已經運行的時間(以秒爲單位)。

5.4. mysql_fix_privilege_tables:升級MySQL系統表

一些MySQL發佈對mysql數據庫中的系統表的結構進行了更改,添加了新權限或特性。當你更新到新版本MySQL,你應同時更新系統表,以確保它們的結構最新。首先備份mysql數據庫,而後按照下面的程序操做。

在Unix或Unix類系統中,運行mysql_fix_privilege_tables腳原本更新系統表:

shell> mysql_fix_privilege_tables

你必須在服務器運行時執行該腳本。它試圖鏈接本機上用root運行的服務器。若是root帳戶須要密碼,在命令行中按下述方法給出密碼:

shell> mysql_fix_privilege_tables--password=root_password

mysql_fix_privilege_tables腳本能夠執行將系統錶轉換爲當前格式的任何動做。運行時你可能會看見一些Duplicate column name警告;你能夠忽略它們。

運行完腳本後,中止服務器並重啓。

在Windows系統中,MySQL分發包括mysql_fix_privilege_tables.sql SQL腳本,你能夠用mysql客戶端來運行。例如,若是MySQL安裝到C:\Program Files\MySQL\MySQL Server 5.1,命令應爲:

C:\> C:\Program Files\MySQL\MySQL Server 5.1\bin\mysql -u root -p mysql
mysql> SOURCE C:/Program Files/MySQL/MySQL Server 5.1/scripts/mysql_fix_privilege_tables.sql

若是安裝到其它目錄,相應地更改路徑名。

mysql命令將提示輸入root密碼;按照提示輸入密碼。

在Unix中,當mysql處理mysql_fix_privilege_tables.sql script腳本中的語句時,你可能會看見一些Duplicate column name警告;你能夠忽略它們。

運行完腳本後,中止服務器並重啓。

5.5. MySQL服務器關機進程

  1.  服務器關閉進程能夠歸納爲:

    1.    啓動關閉進程

    2.    服務器根據須要建立關閉線程

    3.    服務器中止接收新鏈接

    4.    服務器終止當前的活動

    5.    存儲引擎被停掉或關閉

    6.    服務器退出

    下面是更詳細的描述:

    1.    啓動關閉進程。

    能夠用多種方法啓動服務器的關閉。例如,擁有SHUTDOWN權限的用戶能夠執行mysqladmin shutdown命令。mysqladmin能夠用於全部支持MySQL的平臺上。其它操做系統相關的關閉開始方法還可能有:在Unix中,當接收到SIGTERM信號後,服務器關閉。對於在Windows中做爲服務運行的服務器,當服務管理器讓它關閉時,則關閉。

    2.    服務器根據須要建立關閉線程。

    根據開始關閉的方式,服務器能夠建立線程來處理關閉進程。若是客戶端須要關閉,則建立關閉線程。若是收到SIGTERM信號後關閉,信號線程能夠本身關閉,或者建立單獨的線程來完成。若是服務器嘗試建立關閉線程而不能建立(例如,若是內存被耗盡),它在錯誤日誌中給出診斷消息:

    Error: Can't create thread to kill server

    3.    服務器中止接收新鏈接。

    在關閉過程當中要想防止啓動新活動,服務器中止接收新的客戶端鏈接。它將關閉它幀聽的網絡鏈接:TCP/IP端口、Unix套接字文件、Windows命名管道和在Windows中的共享內存。

    4.    服務器終止當前的活動。

    對於每一個與客戶端鏈接相關的線程,與客戶端的鏈接被中斷,線程被標記爲「殺掉的」。當線程注意到此類標記後則線程終止。空閒鏈接的線程很快終止。當前正處理查詢的線程按期檢查它們的狀態,終止的時間較長。關於線程終止的詳細信息,參見13.5.5.3節,「KILL語法」,特別是關於對MyISAM表的殺掉的REPAIR TABLE或OPTIMIZE TABLE操做。

    對於有打開事務的線程,事務被回滾。請注意若是某個線程正在更新非事務表,多行UPDATE或INSERT等操做會使表部分更新,由於操做在完成前會終止。

    若是服務器是主複製服務器,與當前鏈接的從服務器相關的線程的處理方式同其它客戶端線程。即每一個線程被標記爲殺掉的,在下次檢查他的狀態後會退出。

    若是服務器是從複製服務器,在客戶端線程標記爲殺掉的以前,激活的I/O和SQL線程被中止。SQL線程容許先結束它當前的語句(以免形成複製問題)而後中止。若是此時SQL線程正位於事務中部,事務則 回滾。

    5.    存儲引擎被停掉或關閉。

    在該階段,表緩存被清空,全部打開的表被關閉。

    每一個存儲引擎執行它管理的表須要的任何動做。例如,MyISAM清空任何掛起的表索引寫操做。InnoDB將它的緩衝池清空到硬盤上(除非innodb_fast_shutdown爲2),將當前的LSN寫入表內,並終止本身的內部線程。

    6.    服務器退出。

5.6. 通常安全問題

本節描述一些常見的須要注意的安全問題,以及一些能夠使你的MySQL安裝更加安全以防止黑客和誤用的措施。關於MySQL用於設置用戶帳戶並檢查數據庫訪問的訪問控制系統的具體信息,參見5.7節,「MySQL訪問權限系統」

5.6.1. 通用安全指南

任何在與Internet聯網的計算機上使用MySQL的用戶都應仔細閱讀本節,以免最多見的安全問題。

討論安全時,咱們強調必須徹底保護整個服務器主機的安全(而不僅是MySQL服務器)防範各類類型的可能的攻擊:偷聽、修改、重放和拒絕服務。咱們在這裏不能覆蓋各方面的內容和措施。

MySQL根據訪問控制列表(ACL)對全部鏈接、查詢和其它用戶嘗試執行的操做進行安全管理。MySQL客戶端和服務器之間還支持SSL-加密鏈接。這兒討論的許多概念並非MySQL專有的;該思想幾乎一樣適合全部應用程序。

運行MySQL時,應儘可能聽從下面的指導:

·         不要讓任何人(除了MySQL root帳戶)訪問mysql數據庫中的user表!這很關鍵。加密的密碼纔是MySQL中的真正的密碼。知道user表中所列的密碼而且能訪問該帳戶客訪問的主機的人能夠很容易地用該用戶登陸

·         學習MySQL訪問權限系統。用GRANT和REVOKE語句來控制對MySQL的訪問。不要授予超過需求的權限。決不能爲全部主機受權。

檢查清單:

o        試試mysql -u root。若是你可以成功鏈接服務器而沒有要任何密碼,則說明有問題。任何人能夠做爲MySQLroot用戶用它的所有權限來鏈接MySQL服務器!查閱MySQL安裝說明,應特別注意關於設置root密碼的信息。參見2.9.3節,「使初始MySQL帳戶安全」

o        經過SHOW GRANTS語句檢查查看誰已經訪問了什麼。而後使用REVOKE語句刪除再也不須要的權限。

·         不要將純文本密碼保存到數據庫中。若是你的計算機有安全危險,入侵者能夠得到全部的密碼並使用它們。相反,應使用MD5()、SHA1()或單向哈希函數。

·         不要從詞典中選擇密碼。有專門的程序能夠破解它們。即便象「xfish98」這樣的密碼也不好。而「duag98」要好得多,雖然包含了相同的字「fish」,但從標準QWERTY鍵盤向左輸入。另外一種方法是使用「Mhall」,來自句子「Mary had a little lamb.」中每一個字的第一個字符。這樣很容易記住並輸入,可是不知道的人很難猜出來。

·         購買防火牆。這樣能夠保護你防範各類軟件中至少50%的各類類型的攻擊。把MySQL放到防火牆後或隔離區(DMZ)。

檢查清單:

o        試試從Internet使用nmap工具掃描端口。MySQL默認使用端口3306。不該從不可信任主機訪問該端口。另外一種檢查是否MySQL端口打開的簡單方式是從遠程機器試試下面的命令,其中server_host是MySQL服務器運行的主機:

o                     shell> telnet server_host 3306

若是獲得鏈接並獲得一些垃圾字符,則端口打開着,則應從防火牆或路由器上關閉,除非你有合理的理由讓它開着。若是telnet掛起或鏈接被拒絕,則端口被阻塞,這是你所但願的。

不要信任應用程序的用戶輸入的任何數據。它們能夠用Web形式、URL或構建的應用程序輸入特殊或逃溢字符序列來嘗試欺騙你的代碼。若是某個用戶輸入「; DROP DATABASE mysql;」等內容,應確保你的應用程序保持安全。這是特例,但當黑客使用相似技術時,若是你沒有作好準備,結果可能會出現大的安全漏洞和數據丟失。

一個常見的錯誤是隻保護字符串數據值。必定要記住還應檢查數字數據。若是當用戶輸入值234時,應用程序生成查詢SELECT * FROM table WHERE ID=234,用戶能夠輸入值234 OR 1=1使應用程序生成查詢SELECT * FROM table WHERE ID=234 OR 1=1。結果是服務器查找表內的每一個記錄。這樣會暴露每一個記錄並形成過多的服務器負載。保護防範這類攻擊的最簡單的方法是使用單引號將數字常量引發來:SELECT * FROM table WHERE ID='234'。若是用戶輸入其它信息,均變爲字符串的一部分。在數字部分,MySQL自動將字符串轉換爲數字並剝離字符串包含的附加的非數字字符。

有時候人們會認爲若是數據庫只包含供公共使用的數據,則不須要保護。這是不正確的。即便容許顯示數據庫中的任何記錄,你仍然應保護防範拒絕服務攻擊(例如,基於前面段落中所述的技術的攻擊,會使服務器浪費資源)。不然,你的服務器再也不響應合法用戶。

檢查清單:

o        試試用Web形式輸入單引號和雙引號(‘'’和‘"’)。若是獲得任何形式的MySQL錯誤,當即分析緣由。

o        試試修改動態URL,能夠在其中添加%22(‘"’)、%23(‘#’)和%27(‘'’)。

o        試試在動態URL中修改數據類型,使用前面示例中的字符,包括數字和字符類型。你的應用程序應足夠安全,能夠防範此類修改和相似攻擊。

o        試試輸入字符、空格和特殊符號,不要輸入數值字段的數字。你的應用程序應在將它們傳遞到MySQL以前將它們刪除或生成錯誤。將未通過檢查的值傳遞給MySQL是很危險的!

o        將數據傳給MySQL以前先檢查其大小。

o        用管理帳戶以外的用戶名將應用程序鏈接到數據庫。不要給應用程序任何不須要的訪問權限。

·         許多應用程序編程接口提供了措施逃逸數據值中的特殊字符。若是使用正確,能夠防止應用程序用戶輸入使應用程序生成不指望的效果的語句的數值:

o        MySQL C API:使用mysql_real_escape_string() API調用。

o        MySQL++:查詢流使用escape和quote修訂符。

o        PHP:使用mysql_escape_string()函數基於MySQL C API中的同名函數。(在PHP 4.0.3以前,使用addslashes())。在PHP 5中,能夠使用mysqli擴展名,它支持改進的MySQL鑑定協議和密碼,以及用佔位符編寫的語句。

o        Perl DBI:使用quote()方法或使用佔位符。

o        Java JDBC:使用一個PreparedStatement對象和佔位符。

其它編程接口有相似的功能。

·         不要經過Internet傳送明文(未加密的)數據。該信息能夠被有足夠時間和能力來截取它並用於我的目的的任何人訪問。相反,應使用加密協議,例如SSL或SSH。MySQL支持內部SSL鏈接,例如版本 4.0.0。能夠使用SSH端口映射爲通訊建立加密(並壓縮)的隧道。

·         學會使用tcpdump和strings工具。在大多數狀況下,你能夠使用下面的命令檢查是否MySQL數據流未加密:

·                shell> tcpdump -l -i eth0 -w - src or dst port 3306 | strings

(該命令在Linux中能夠工做,在其它系統中通過小小的修改後應能夠工做)。 警告:若是你沒有看見明文數據,並不必定說明信息實際上被加密了。若是你須要較高級別的安全,你應諮詢安全專家。

5.6.2. 使MySQL在攻擊者面前保持安全

當你鏈接到MySQL服務器時,你應使用一個密碼。密碼不以明文在上傳輸。客戶端鏈接序列中的密碼處理在MySQL 4.1.1中已經升級,很安全。若是你仍然使用pre-4.1.1-風格的密碼,加密算法不如新算法強;經過一些工做,能夠竊取客戶端和服務器之間的通訊的聰明的攻擊者能夠破解密碼。(關於不一樣的密碼處理方法的討論參見5.7.9節,「MySQL 4.1中的密碼哈希處理」)。 若是客戶端和服務器之間的鏈接經過不可信任網絡,你應使用SSH隧道來加密通訊。

全部其它信息以文本傳送,能夠被能夠看到鏈接的任何人讀取。若是你擔憂這個,你能夠使用壓縮協議來使通訊更難以解密。要想使鏈接更加安全,你應使用SSH來得到加密的MySQL服務器和MySQL客戶端之間的TCP/IP鏈接。你能夠從http://www.openssh.org/找到開放源碼SSH 客戶端,並能夠從http://www.ssh.com/得到商業SSH客戶端。

你還能夠使用MySQL內部OpenSSL支持。參見5.8.7節,「使用安全鏈接」

爲了使MySQL系統安全,強烈要求你考慮下列建議:

·         對全部MySQL用戶使用密碼。客戶端程序不須要知道運行它的人員的身份。對於客戶端/服務器應用程序,用戶能夠指定客戶端程序的用戶名。例如,若是other_user沒有密碼,任何人能夠簡單地用mysql -u other_user db_name冒充他人調用mysql程序進行鏈接。若是全部用戶有密碼,使用其它用戶的帳戶進行鏈接要困可貴多。

要想更改用戶的密碼,應使用SET PASSWORD語句。還能夠直接更新mysql數據庫中的user表。例如,要更改全部root用戶的MySQL帳戶的密碼,應:

shell> mysql -u root
mysql> UPDATE mysql.user SET Password=PASSWORD('newpwd')
    -> WHERE User='root';
mysql> FLUSH PRIVILEGES;

·         絕對不要做爲Unix的root用戶運行MySQL服務器。這樣作很是危險,由於任何具備FILE權限的用戶可以用root建立文件(例如,~root/.bashrc)。爲了防止,mysqld拒絕用root運行,除非使用--user=root選項明顯指定。

應能夠(而且應該)用普通非特權用戶運行mysqld。你能夠建立獨立的Unix中的mysql帳戶來以便使全部內容更加安全。該帳戶只用於管理MySQL。要想用其它Unix用戶啓動mysqld,增長user選項指定/etc/my.cnf選項文件或服務器數據目錄的my.cnf選項文件中的[mysqld]組的用戶名。例如:

[mysqld]
user=mysql

該命令使服務器用指定的用戶來啓動,不管你手動啓動或經過mysqld_safemysql.server啓動。詳細信息參見A.3.2節,「如何以普通用戶身份運行MySQL」

做爲其它Unix用戶而不用root運行mysqld,你不須要更改user表中的root用戶名,由於MySQL帳戶的用戶名與Unix帳戶的用戶名無關。

·         不要容許使用表的符號連接。(能夠用--skip-symbolic-links選項禁用)。若是你用root運行mysqld則特別重要,由於任何對服務器的數據目錄有寫訪問權限的人則可以刪除系統中的任何文件!參見7.6.1.2節,「在Unix平臺上使用表的符號連接」。

·         確保mysqld運行時,只使用對數據庫目錄具備讀或寫權限的Unix用戶來運行。

·         不要將PROCESS或SUPER權限授給非管理用戶。mysqladmin processlist的輸出顯示出當前執行的查詢正文,若是另外的用戶發出一個UPDATE user SET password=PASSWORD('not_secure')查詢,被容許執行那個命令的任何用戶可能看獲得。

mysqld爲有SUPER權限的用戶專門保留一個額外的鏈接,所以即便全部普通鏈接被佔用,MySQL root用戶仍能夠登陸並檢查服務器的活動。

能夠使用SUPER權限來終止客戶端鏈接,經過更改系統變量的值更改服務的器操做,並控制複製服務器。

·         不要向非管理用戶授予FILE權限。有這權限的任何用戶能在擁有mysqld守護進程權限的文件系統那裏寫一個文件!爲了更加安全,由SELECT ... INTO OUTFILE生成的全部文件對每一個人是可寫的,而且你不能覆蓋已經存在的文件。

file權限也能夠被用來讀取任何做爲運行服務器的Unix用戶可讀取或訪問的文件。使用該權限,你能夠將任何文件讀入數據庫表。這可能被濫用,例如,經過使用LOAD DATA裝載「/etc/passwd」進一個數據庫表,而後能用SELECT顯示它。

·         若是你不信任你的DNS,你應該在受權表中使用IP數字而不是主機名。在任何狀況下,你應該很是當心地使用包含通配符的主機名來建立 受權表條目!

·         若是你想要限制單個帳戶容許的鏈接數量,你能夠設置mysqld中的max_user_connections變量來完成。GRANT語句也能夠支持 資源控制選項來限制服務器對一個帳戶容許的使用範圍。參見13.5.1.3節,「GRANT和REVOKE語法」

5.6.3. Mysqld安全相關啓動選項

下列mysqld選項影響安全:

·         --allow-suspicious-udfs

該選項控制是否能夠載入主函數只有xxx符的用戶定義函數。默認狀況下,該選項被關閉,而且只能載入至少有輔助符的UDF。這樣能夠防止從未包含合法UDF的共享對象文件載入函數。參見27.2.3.6節,「用戶定義函數安全注意事項」

·         --local-infile[={0|1}]

若是用--local-infile=0啓動服務器,則客戶端不能使用LOCAL in LOAD DATA語句。參見5.6.4節,「LOAD DATA LOCAL安全問題

·         --old-passwords

強制服務器爲新密碼生成短(pre-4.1)密碼哈希。當服務器必須支持舊版本客戶端程序時,爲了保證兼容性這頗有用。參見5.7.9節,「MySQL 4.1中的密碼哈希處理」

·         (OBSOLETE) --safe-show-database

在之前版本的MySQL中,該選項使SHOW DATABASES語句只顯示用戶具備部分權限的數據庫名。在MySQL 5.1中,該選項再也不做爲如今的 默認行爲使用,有一個SHOW DATABASES權限能夠用來控制每一個帳戶對數據庫名的訪問。參見13.5.1.3節,「GRANT和REVOKE語法」

·         --safe-user-create

若是啓用,用戶不能用GRANT語句建立新用戶,除非用戶有mysql.user表的INSERT權限。若是你想讓用戶具備受權權限來建立新用戶,你應給用戶授予下面的權限:

mysql> GRANT INSERT(user) ON mysql.user TO 'user_name'@'host_name';

這樣確保用戶不能直接更改權限列,必須使用GRANT語句給其它用戶授予該權限。

·         --secure-auth

不容許鑑定有舊(pre-4.1)密碼的帳戶。

·         --skip-grant-tables

這個選項致使服務器根本不使用權限系統。這給每一個人以徹底訪問全部的數據庫的權力!(經過執行mysqladmin flush-privilegesmysqladmin reload命令,或執行FLUSH PRIVILEGES語句,你能告訴一個正在運行的服務器再次開始使用受權表。)  

·         --skip-name-resolve

主機名不被解析。全部在受權表的Host的列值必須是IP號或localhost。

·         --skip-networking

在網絡上不容許TCP/IP鏈接。全部到mysqld的鏈接必須經由Unix套接字進行。

·         --skip-show-database

使用該選項,只容許有SHOW DATABASES權限的用戶執行SHOW DATABASES語句,該語句顯示全部數據庫名。不使用該選項,容許全部用戶執行SHOW DATABASES,但只顯示用戶有SHOW DATABASES權限或部分數據庫權限的數據庫名。請注意全局權限指數據庫的權限。

5.6.4. LOAD DATA LOCAL安全問題

LOAD DATA語句能夠裝載服務器主機上的文件,若指定LOCAL關鍵字,能夠裝載客戶端文件。

支持LOCAL版本的LOAD DATA語句有兩個可能的安全問題:

·         由MySQL服務器啓動文件從客戶端向服務器主機的傳輸。理論上,打過補丁的服務器能夠告訴客戶端程序傳輸服務器選擇的文件,而不是客戶用LOAD DATA語句指定的文件。這樣服務器能夠訪問客戶端上客戶有讀訪問權限的任何文件。

·         在Web環境中,客戶從Web服務器鏈接,用戶能夠使用LOAD DATA LOCAL來讀取Web服務器進程有讀訪問權限的任何文件(假定用戶能夠運行SQL服務器的任何命令)。在這種環境中,MySQL服務器的客戶其實是Web服務器,而不是鏈接Web服務器的用戶運行的程序。

要處理這些問題,咱們更改了MySQL 3.23.49和MySQL 4.0.2(Windows中的4.0.13)中的LOAD DATA LOCAL的處理方法:

·         默認狀況下,如今全部二進制分中的發MySQL客戶端和庫是用--enable-local-infile選項編譯,以便與MySQL 3.23.48和之前的版本兼容。

·         若是你從源碼構建MySQL但沒有使用--enable-local-infile選項來進行configure,則客戶不能使用LOAD DATA LOCAL,除非顯式調用mysql_options (...MYSQL_OPT_本地_INFILE,0)。參見25.2.3.48節,「mysql_options()」

·         你能夠用--local-infile=0選項啓動mysqld從服務器端禁用全部LOAD DATA LOCAL命令。

·         對於mysql命令行客戶端,能夠經過指定--local-infile[=1]選項啓用LOAD DATA LOCAL,或經過--local-infile=0選項禁用。相似地,對於mysqlimport,--local or -L選項啓用本地數據文件裝載。在任何狀況下,成功進行本地裝載須要服務器啓用相關選項。

·         若是你使用LOAD DATA LOCAL Perl腳本或其它讀選項文件中的[client]組的程序,你能夠在組內添加local-infile=1選項。可是,爲了便面不理解local-infile的程序產生問題,則規定使用loose- prefix:

·                [client]
·                loose-local-infile=1

·         若是LOAD DATA LOCAL INFILE在服務器或客戶端被禁用,試圖執行該語句的客戶端將收到下面的錯誤消息:

ERROR 1148: The used command is not allowed with this MySQL version

5.7. MySQL訪問權限系統

MySQL有先進但非標準的安全/權限系統。本節描述它的工做原理。

5.7.1. 權限系統的做用

MySQL權限系統的主要功能是證明鏈接到一臺給定主機的用戶,而且賦予該用戶在數據庫上的SELECT、INSERT、UPDATE和DELETE權限。

附加的功能包括有匿名的用戶並對於MySQL特定的功能例如LOAD DATA INFILE進行受權及管理操做的能力。

5.7.2. 權限系統工做原理

MySQL權限系統保證全部的用戶只執行容許作的事情。當你鏈接MySQL服務器時,你的身份由你從那兒鏈接的主機你指定的用戶名來決定。鏈接後發出請求後,系統根據你的身份和你想作什麼來授予權限。

MySQL在認定身份中考慮你的主機名和用戶名字,是由於幾乎沒有緣由假定一個給定的用戶在因特網上屬於同一我的。例如,從office.com鏈接的用戶joe不必定和從elsewhere.com鏈接的joe是同一我的。MySQL經過容許你區分在不一樣的主機上碰巧有一樣名字的用戶來處理它:你能夠對joe從office.com進行的鏈接授與一個權限集,而爲joe從elsewhere.com的鏈接授予一個不一樣的權限集。

MySQL存取控制包含2個階段:

  • 階段1:服務器檢查是否容許你鏈接。
  • 階段2:假定你能鏈接,服務器檢查你發出的每一個請求。看你是否有足夠的權限實施它。例如,若是你從數據庫表中選擇(select)行或從數據庫刪除表,服務器肯定你對錶有SELECT權限或對數據庫有DROP權限。

若是鏈接時你的權限被更改了(經過你和其它人),這些更改不必定當即對你發出的下一個語句生效。詳情參見5.7.7節,「權限更改什麼時候生效」

服務器在mysql數據庫的 受權表中保存權限信息(即在mysql數據庫中)。當MySQL服務器啓動時將這些表的內容讀入內存,在5.7.7節,「權限更改什麼時候生效」的環境下從新讀取它們。訪問控制決策取決於內存中的 受權表的份數。

通常狀況,你經過GRANT和REVOKE語句間接來操做 受權表的內容,設置帳戶並控制我的的權限。參見13.5.1.3節,「GRANT和REVOKE語法」。下面討論了 受權表的結構以及服務器與客戶端交互操做時如何使用其內容。

服務器在存取控制的兩個階段使用mysql數據庫中的user、db和host表,這些受權表中的列以下:

表名

user

db

host

列範圍

Host

Host

Host

 

User

Db

Db

 

Password

User

 

權限列

Select_priv

Select_priv

Select_priv

 

Insert_priv

Insert_priv

Insert_priv

 

Update_priv

Update_priv

Update_priv

 

Delete_priv

Delete_priv

Delete_priv

 

Index_priv

Index_priv

Index_priv

 

Alter_priv

Alter_priv

Alter_priv

 

Create_priv

Create_priv

Create_priv

 

Drop_priv

Drop_priv

Drop_priv

 

Grant_priv

Grant_priv

Grant_priv

 

Create_view_priv

Create_view_priv

Create_view_priv

 

Show_view_priv

Show_view_priv

Show_view_priv

 

Create_routine_priv

Create_routine_priv

 

 

Alter_routine_priv

Alter_routine_priv

 

 

References_priv

References_priv

References_priv

 

Reload_priv

 

 

 

Shutdown_priv

 

 

 

Process_priv

 

 

 

File_priv

 

 

 

Show_db_priv

 

 

 

Super_priv

 

 

 

Create_tmp_table_priv

Create_tmp_table_priv

Create_tmp_table_priv

 

Lock_tables_priv

Lock_tables_priv

Lock_tables_priv

 

Execute_priv

 

 

 

Repl_slave_priv

 

 

 

Repl_client_priv

 

 

安全列

ssl_type

 

 

 

ssl_cipher

 

 

 

x509_issuer

 

 

 

x509_subject

 

 

資源控制列

max_questions

 

 

 

max_updates

 

 

 

max_connections

 

 

 

max_user_connections

 

 

對存取控制的第二階段(請求證明),服務器執行請求驗證以確保每一個客戶端有充分的權限知足各需求。除了user、db和host受權表,若是請求涉及表,服務器能夠另外參考tables_priv和columns_priv表。tables_priv和columns_priv表能夠對錶和列提供更精確的權限控制。這些表的列以下:

表名

tables_priv

columns_priv

範圍列

Host

Host

 

Db

Db

 

User

User

 

Table_name

Table_name

 

 

Column_name

權限列

Table_priv

Column_priv

 

Column_priv

 

其它列

Timestamp

Timestamp

 

Grantor

 

Timestamp和Grantor列當前還未使用,這兒再也不進一步討論。

爲了對涉及保存程序的請求進行驗證,服務器將查閱procs_priv表。該表具備如下列:

表名

procs_priv

範圍列

Host

 

Db

 

User

 

Routine_name

 

Routine_type

權限列

Proc_priv

其它列

Timestamp

 

Grantor

Routine_type列爲ENUM列,值爲'FUNCTION'或'PROCEDURE',表示行所指的程序類型。該列容許爲同名函數和程序單獨受權。

Timestamp和Grantor列當前還未使用,這兒再也不進一步討論。

每一個受權表包含範圍列和權限列:

l        範圍列決定表中每一個條目(行)的範圍,即,行適用的上下文。例如, 一個user錶行的Host和User值爲'thomas.loc.gov'和'bob',將被用於證明來自主機thomas.loc.gov的bob對服務器的鏈接。一樣,一個db錶行的Host、User和Db列的值是'thomas.loc.gov'、'bob'和'reports'將用在bob從主機thomas.loc.gov聯接訪問reports數據庫的時候。tables_priv和columns_priv表包含範圍列,指出每一個行適用的表或表/列的組合。procs_priv範圍列指出每一個行適用的保存程序。

對於檢查存取的用途,比較Host值是忽略大小寫的。User、Password、Db和Table_name值是區分大小寫的。Column_name值在MySQL3.22.12或之後版本是忽略大小寫的。

l        權限列指出由一個錶行授予的權限,即,可實施什麼操做。服務器組合各類的受權表的信息造成一個用戶權限的完整描述。爲此使用的規則在5.7.6節,「訪問控制, 階段2:請求覈實」描述。

範圍列包含字符串,以下所述;每一個列的默認值是空字符串:

列名

類型

Host

CHAR(60)

User

CHAR(16)

Password

CHAR(16)

Db

CHAR(64)

Table_name

CHAR(64)

Column_name

CHAR(64)

Routine_name

CHAR(64)

爲了訪問檢查目的,Host值的比較對大小寫不敏感。User、Password、Db和Table_name值對大小寫敏感。Column_name值對大小寫不敏感。

在user、db和host表中,全部權限列於單獨的列內,被聲明爲ENUM('N','Y') DEFAULT 'N'。換句話說,每個權限均可以被禁用和啓用,而且 默認是禁用。

在tables_priv、columns_priv和procs_priv表中,權限列被聲明爲SET列。這些列的值能夠包含該表控制的權限的組合:

表名

列名

可能的設置元素

tables_priv

Table_priv

'Select', 'Insert', 'Update', 'Delete', 'Create', 'Drop', 'Grant', 'References', 'Index', 'Alter'

tables_priv

Column_priv

'Select', 'Insert', 'Update', 'References'

columns_priv

Column_priv

'Select', 'Insert', 'Update', 'References'

procs_priv

Proc_priv

'Execute', 'Alter Routine', 'Grant'

簡單地說,服務器使用這樣的受權表:

·         user表範圍列決定是否容許或拒絕到來的鏈接。對於容許的鏈接,user表授予的權限指出用戶的全局(超級用戶)權限。這些權限適用於服務器上的all數據庫。

·         db表範圍列決定用戶能從哪一個主機存取哪一個數據庫。權限列決定容許哪一個操做。授予的數據庫級別的權限適用於數據庫和它的表。

·         當你想要一個給定的db錶行應用於若干主機時,db和host表一塊兒使用。例如,若是你想要一個用戶能在你的網絡從若干主機使用一個數據庫,在用戶的db錶行的Host值設爲空值,而後將那些主機的每個移入host表。這個機制詳細描述在5.7.6節,「訪問控制, 階段2:請求覈實」

釋:host表不受GRANT和REVOKE語句的影響。大多數MySQL安裝根本不須要使用該表。

·         tables_priv和columns_priv表相似於db表,可是更精緻:它們在表和列級應用而非在數據庫級。授予表級別的權限適用於表和全部它的列。授予列級別的權限只適用於專用列。

·         procs_priv表適用於保存的程序。授予程序級別的權限只適用於單個程序。

管理權限(例如RELOAD或SHUTDOWN等等)僅在user表中被指定。這是由於管理性操做是服務器自己的操做而且不是特定數據庫,所以沒有理由在其餘受權表中列出這樣的權限。事實上,只須要查詢user表來決定你是否執行一個管理操做。

FILE權限也僅在user表中指定。它不是管理性權限,但你在服務器主機上讀或寫文件的能力與你正在存取的數據庫無關。

mysqld服務器啓動時,將受權表的內容讀入到內存中。你能夠經過FLUSH PRIVILEGES語句或執行mysqladmin flush-privilegesmysqladmin reload命令讓它從新讀取表。對受權表的更改生效在5.7.7節,「權限更改什麼時候生效」描述。

當你修改受權表的內容時,確保你按你想要的方式更改權限設置是一個好主意。要檢查給定帳戶的權限,使用SHOW GRANTS語句。例如,要檢查Host和User值分別爲pc84.example.com和bob的帳戶所授予的權限,應經過語句:

 

mysql> SHOW GRANTS FOR 'bob'@'pc84.example.com';

一個有用的診斷工具是mysqlaccess腳本,由Carlier Yves 提供給MySQL分發。使用--help選項調用mysqlaccess查明它怎樣工做。注意:mysqlaccess僅用user、db和host表檢查存取。它不檢查tables_priv、columns_priv或procs_priv表中指定的表、列和程序級權限。

對於診斷權限相關的問題的其它幫助,參見5.7.8節,「拒絕訪問錯誤的緣由。對於安全問題常規建議,參見5.6節,「通常安全問題」

5.7.3. MySQL提供的權限

帳戶權限信息被存儲在mysql數據庫的user、db、host、tables_priv、columns_priv和procs_priv表中。在MySQL啓動時並在5.7.7節,「權限更改什麼時候生效」所說的狀況時,服務器將這些數據庫表內容讀入內存。

GRANT和REVOKE語句所用的涉及權限的名稱顯示在下表,還有在受權表中每一個權限的表列名稱和每一個權限有關的上下文。關於每一個權限的含義相關的詳細信息參見13.5.1.3節,「GRANT和REVOKE語法」

權限

上下文

CREATE

Create_priv

數據庫、表或索引

DROP

Drop_priv

數據庫或表

GRANT OPTION

Grant_priv

數據庫、表或保存的程序

REFERENCES

References_priv

數據庫或表

ALTER

Alter_priv

DELETE

Delete_priv

INDEX

Index_priv

INSERT

Insert_priv

SELECT

Select_priv

UPDATE

Update_priv

CREATE VIEW

Create_view_priv

視圖

SHOW VIEW

Show_view_priv

視圖

ALTER ROUTINE

Alter_routine_priv

保存的程序

CREATE ROUTINE

Create_routine_priv

保存的程序

EXECUTE

Execute_priv

保存的程序

FILE

File_priv

服務器主機上的文件訪問

CREATE TEMPORARY TABLES

Create_tmp_table_priv

服務器管理

LOCK TABLES

Lock_tables_priv

服務器管理

CREATE USER

Create_user_priv

服務器管理

PROCESS

Process_priv

服務器管理

RELOAD

Reload_priv

服務器管理

REPLICATION CLIENT

Repl_client_priv

服務器管理

REPLICATION SLAVE

Repl_slave_priv

服務器管理

SHOW DATABASES

Show_db_priv

服務器管理

SHUTDOWN

Shutdown_priv

服務器管理

SUPER

Super_priv

服務器管理

當從早期的沒有CREATE VIEW、SHOW VIEW、CREATE ROUTINE、ALTER ROUTINE和EXECUTE權限的版本的MySQL中升級時,要想使用這些權限,你必須使用MySQL分發提供的mysql_fix_privilege_tables腳本升級 受權表。參見2.10.2節,「升級受權表」

若是啓用了二進制記錄,要想建立或修改保存的程序,你還須要SUPER權限,詳細描述見20.4節,「存儲子程序和觸發程序的二進制日誌功能」

經過CREATE和DROP權限,你能夠建立新數據庫和表,或刪除(移掉)已有數據庫和表。若是你將mysql數據庫中的DROP權限授予某用戶,用戶能夠刪掉MySQL訪問權限保存的數據庫。

SELECT、INSERT、UPDATE和DELETE權限容許你在一個數據庫現有的表上實施操做。

SELECT語句只有在他們真正從一個表中檢索行時才須要SELECT權限。一些SELECT語句不訪問表,甚至沒有任何到服務器上的數據庫裏的存取任何東西的許可。例如,你可以使用mysql客戶端做爲一個簡單的計算器來評估未引用表的表達式:

mysql> SELECT 1+1;
mysql> SELECT PI()*2;

INDEX權限容許你建立或刪除索引。INDEX適用已有表。若是你具備某個表的CREATE權限,你能夠在CREATE TABLE語句中包括索引定義。

經過ALTER權限,你能夠使用ALTER TABLE來更改表的結構和從新命名錶。

須要CREATE ROUTINE權限來建立保存的程序(函數和程序),ALTER ROUTINE權限來更改和刪除保存的程序,EXECUTE來執行保存的程序。

GRANT權限容許你把你本身擁有的那些權限授給其餘的用戶。能夠用於數據庫、表和保存的程序。

FILE權限給予你用LOAD DATA INFILE和SELECT ... INTO OUTFILE語句讀和寫服務器上的文件,任何被授予FILE權限的用戶都能讀或寫MySQL服務器能讀或寫的任何文件。(說明用戶能夠讀任何數據庫目錄下的文件,由於服務器能夠訪問這些文件)。 FILE權限容許用戶在MySQL服務器具備寫權限的目錄下建立新文件。不能覆蓋已有文件。

其他的權限用於管理性操做,它使用mysqladmin程序或SQL語句實施。下表顯示每一個管理性權限容許你執行的mysqladmin命令:

權限

權限擁有者容許執行的命令

RELOAD

flush-hosts, flush-logs, flush-privileges, flush-status, flush-tables, flush-threads, refresh, reload

SHUTDOWN

shutdown

PROCESS

processlist

SUPER

kill

reload命令告訴服務器將受權表從新讀入內存。flush-privileges是reload的同義詞,refresh命令清空全部表並打開並關閉記錄文件,其它flush-xxx命令執行相似refresh的功能,可是範圍更有限,而且在某些狀況下可能更好用。例如,若是你只是想清空記錄文件,flush-logs比refresh是更好的選擇。

shutdown命令關掉服務器。只能從mysqladmin發出命令。沒有相應的SQL語句。

processlist命令顯示在服務器內執行的線程的信息(即其它帳戶相關的客戶端執行的語句)。kill命令殺死服務器線程。你老是能顯示或殺死你本身的線程,可是你須要PROCESS權限來顯示或殺死其餘用戶和SUPER權限啓動的線程。參見13.5.5.3節,「KILL語法」

擁有CREATE TEMPORARY TABLES權限即可以使用CREATE TABLE語句中的關鍵字TEMPORARY。

擁有LOCK TABLES權限即可以直接使用LOCK TABLES語句來鎖定你擁有SELECT權限的表。包括使用寫鎖定,能夠防止他人讀鎖定的表。

擁有REPLICATION CLIENT權限即可以使用SHOW MASTER STATUS和SHOW SLAVE STATUS。

REPLICATION SLAVE權限應授予從服務器所使用的將當前服務器鏈接爲主服務器的帳戶。沒有這個權限,從服務器不能發出對主服務器上的數據庫所發出的更新請求。

擁有SHOW DATABASES權限便容許帳戶使用SHOW DATABASE語句來查看數據庫名。沒有該權限的帳戶只能看到他們具備部分權限的數據庫, 若是數據庫用--skip-show-database選項啓動,則根本不能使用這些語句。請注意全局權限指數據庫的權限。

總的說來,只授予權限給須要他們的那些用戶是好主意,可是你應該在授予FILE和管理權限時試驗特定的警告:

  • FILE權限能夠被濫用於將服務器主機上MySQL能讀取的任何文件讀入到數據庫表中。包括任何人可讀的文件和服務器數據目錄中的文件。能夠使用SELECT訪問數據庫表,而後將其內容傳輸到客戶端上。
  • GRANT權限容許用戶將他們的權限給其餘用戶。有不一樣的權限並有GRANT權限的2個用戶能夠合併權限。
  • ALTER權限能夠用於經過從新命名錶來推翻權限系統。
  • SHUTDOWN權限經過終止服務器能夠被濫用徹底拒絕爲其餘用戶服務。
  • PROCESS權限能被用來察看當前執行的查詢的明文文本,包括設定或改變密碼的查詢。
  • SUPER權限能用來終止其它用戶或更改服務器的操做方式。
  • 授給mysql數據庫自己的權限能用來改變密碼和其餘訪問權限信息。密碼被加密存儲,因此惡意的用戶不能簡單地讀取他們以知道明文密碼。然而,具備user表Password列寫訪問權限的用戶能夠更改帳戶的密碼,並能夠用該帳戶鏈接MySQL服務器。

有一些事情你不能用MySQL權限系統作到:

  • 你不能明顯地指定某個給定的用戶應該被拒絕訪問。即,你不能明顯地匹配用戶而後拒絕鏈接。
  • 你不能指定用戶有權建立立或刪除數據庫中的表,但不能建立或刪除數據庫自己。

5.7.4. 與MySQL服務器鏈接

當你想要訪問MySQL服務器時,MySQL客戶端程序通常要求你指定參數:

·         MySQL服務器運行的主機名

·         姓名

·         密碼

例如,能夠從命令行按照下述提示啓動MySQL客戶端(用shell>表示):

shell> MySQL -h host_name -u user_name -pyour_pass

-h, -u和-p選項還能夠採用形式--host=host_name、--user=user_name和--password=your_pass。請注意在-p或--password=和後面的密碼之間沒有空格

若是你使用-p或--password選項但沒有指定密碼值,客戶端程序提示你輸入密碼。當你輸入密碼時並不顯示密碼。這比在在命令行輸入密碼要安全得多。系統上的任何用戶能夠經過命令ps auxww在命令行中指定密碼。參見5.8.6節,「使你的密碼安全」

若是沒有指定鏈接參數,MySQL客戶端程序使用默認值:

  • 默認主機名是localhost。
  • 默認用戶名在Windows中是ODBC,在Unix中是你的Unix登陸名。

·         若是沒有-p,則不提供密碼。

這樣, 對Unix用戶joe,下列命令是等價的:

shell> MySQL -h localhost -u joe
shell> MySQL -h localhost
shell> MySQL -u joe
shell> MySQL

其它MySQL客戶端程序相似。

當進行鏈接時,你能夠指定要使用的不一樣的默認值,這樣沒必要每次在你調用客戶端程序是在命令行上輸入它們。這能夠有不少方法作到:

  • 你能夠在選項文件的[client]小節裏指定鏈接參數。文件的相關小節看上去可能像這樣:
·                [client]
·                host=host_name
·                user=user_name
·                password=your_pass

4.3.2節,「使用選項文件」中詳細討論了選項文件。

5.7.5. 訪問控制, 階段1:鏈接覈實

當你試圖鏈接MySQL服務器時,服務器基於你的身份以及你是否能經過供應正確的密碼驗證身份來接受或拒絕鏈接。若是不是,服務器徹底拒絕你的訪問,不然,服務器接受鏈接,而後進入階段2而且等待請求。

你的身份基於2個信息:

  • 你從那個主機鏈接
  • 你的MySQL用戶名

身份檢查使用3個user表(Host, User和Password)範圍列執行。服務器只有在user表記錄的Host和User列匹配客戶端主機名和用戶名而且提供了正確的密碼時才接受鏈接。

在user表Host值的指定方法:

  • Host值能夠是主機名或IP號,或'localhost'指出本地主機。
  • 你能夠在Host列值使用通配符字符「%」「_」
  • Host值'%'匹配任何主機名,空Host值等價於'%'。它們的含義與LIKE操做符的模式匹配操做相同。例如,'%'的Host值與全部主機名匹配,而'%.mysql.com'匹配mysql.com域的全部主機。

·         對於指定爲IP號的Host值,你能夠指定一個網絡掩碼,說明使用多少位地址位來評比網絡號。例如:

·                mysql> GRANT ALL PRIVILEGES ON db.*
·                    -> -> TO david@'192.58.197.0/255.255.255.0';

容許david從任何客戶端用IP號client_ip來鏈接,下面的條件爲真:

client_ip & netmask = host_ip

That is, for the GRANT statement just shown:

client_ip & 255.255.255.0 = 192.58.197.0

知足該條件並能夠鏈接MySQL服務器的IP號的範圍爲192.58.197.0到192.58.197.255。

·         註釋:網絡掩碼只用來告訴服務器使用八、1六、24或32位地址,例如:

·                192.0.0.0/255.0.0.0(192 A類網絡的任何地址)
·                192.168.0.0/255.255.0.0(192.168 A類網絡的任何地址)
·                192.168.1.0/255.255.255.0(192.168.1 C類網絡的任何地址)
·                192.168.1.1(只有該IP)

下面的網絡掩碼(28 位)無效:

192.168.0.1/255.255.255.240

·         db表記錄中的空Host值表示它的權限應結合匹配客戶端名的host表中的行使用。經過AND(相與)而不是或(聯合)操做將權限組合到一塊兒。你能夠從5.7.6節,「訪問控制, 階段2:請求覈實」找到關於host表的詳細信息。

其它grant表的空Host值與'%'相同。

既然你能在Host字段使用IP通配符值(例如,'144.155.166.%'匹配在一個子網上的每臺主機),有可能某人可能企圖探究這種能力,經過命名一臺主機爲144.155.166.somewhere.com。爲了阻止這樣的企圖,MySQL不容許匹配以數字和一個點起始的主機名,這樣,若是你用一個命名爲相似1.2.foo.com的主機,它的名字決不會匹配受權表中的Host列。只有一個IP數字能匹配IP通配符值。

通配符字符在User列中不容許,可是你能指定空的值,它匹配任何名字。若是user表匹配的鏈接有一個空用戶名,用戶被認爲是匿名用戶(沒有名字的用戶),而非客戶端實際指定的名字。這意味着一個空的用戶名被用於在鏈接期間的進一步的訪問檢查(即,在階段2期間)。

Password列能夠是空的。這不是通配符,也不意味着匹配任何密碼,它意味着用戶必須不指定一個密碼進行鏈接。

user表中的非空Password值表明加密的密碼。MySQL不以任何人能夠看的明文文本格式存儲密碼,相反,正在試圖聯接的用戶提供的密碼被加密(使用PASSWORD( )函數),在鏈接過程當中使用加密的密碼檢查密碼是否正確。(加密後的密碼未經過鏈接便可實現)。從MySQL角度,加密的密碼是實際密碼,所以你不該讓其它人訪問它!特別是,絕對不要讓非管理用戶讀mysql數據庫中的表!

MySQL 5.1使用強鑑定方法(最早在MySQL 4.1中適用)在前面的版本中在鏈接進程中的密碼保護較好。即便TCP/IP包被截取或mysql數據庫 被捕獲也很安全。5.7.9節,「MySQL 4.1中的密碼哈希處理」中詳細討論了密碼加密。

下面的例子顯示出各類user表中Host和User值的組合如何應用於到來的鏈接:

Host

User

被條目匹配的鏈接

'thomas.loc.gov'

'fred'

fred, 從thomas.loc.gov 鏈接

'thomas.loc.gov'

''

任何用戶, 從thomas.loc.gov鏈接

'%'

'fred'

fred, 從任何主機鏈接

'%'

''

任何用戶, 從任何主機鏈接

'%.loc.gov'

'fred'

fred, 從在loc.gov域的任何主機鏈接

'x.y.%'

'fred'

fred, 從x.y.net、x.y.com,x.y.edu等聯接。(這或許無用)

'144.155.166.177'

'fred'

fred, 從有144.155.166.177 IP地址的主機鏈接

'144.155.166.%'

'fred'

fred, 從144.155.166 C類子網的任何主機鏈接

到來的鏈接中的客戶端名和用戶名可能與user表中的多行匹配。例如,由fred從thomas.loc.gov的鏈接匹配多個條目如上所述。

若是有多個匹配,服務器必須選擇使用哪一個條目。按照下述方法解決問題:

l        服務器在啓動時讀入user表後進行排序。

l        而後當用戶試圖鏈接時,以排序的順序瀏覽條目

l        服務器使用與客戶端和用戶名匹配的第一行。

user表排序工做以下,假定user表看起來像這樣:

+-----------+----------+-
| Host      | User     | …
+-----------+----------+-
| %         | root     | …
| %         | jeffrey  | …
| localhost | root     | …
| localhost |          | …
+-----------+----------+-

當服務器讀取表時,它首先以最具體的Host值排序。主機名和IP號是最具體的。'%'意味着「任何主機」而且是最不特定的。有相同Host值的條目首先以最具體的User值排序(空User值意味着「任何用戶」而且是最不特定的)。最終排序的user表看起來像這樣:

+-----------+----------+-
| Host      | User     | …
+-----------+----------+-
| localhost | root     | … ...
| localhost |          | … ...
| %         | jeffrey  | … ...
| %         | root     | … ...
+-----------+----------+-

當客戶端試圖鏈接時,服務器瀏覽排序的條目並使用找到的第一匹配。對於由jeffrey從localhost的鏈接,表內有兩個條目匹配:Host和User值爲'localhost'和''的條目,和值爲'%'和'jeffrey'的條目。'localhost'條目首先匹配,服務器能夠使用。

還有一個例子。假定user表看起來像這樣:

+----------------+----------+-
| Host           | User     | …
+----------------+----------+-
| %              | jeffrey  | …
| thomas.loc.gov |          | …
+----------------+----------+-

排序後的表看起來像這樣:

+----------------+----------+-
| Host           | User     | …
+----------------+----------+-
| thomas.loc.gov |          | …
| %              | jeffrey  | …
+----------------+----------+-

由jeffrey從thomas.loc.gov的鏈接與第一行匹配,而由jeffrey從whitehouse.gov的鏈接被第二個匹配。

廣泛的誤解是認爲,對給定的用戶名,當服務器試圖對鏈接尋找匹配時,明確命名那個用戶的全部條目將首先被使用。這明顯不符合事實。先前的例子說明了這點,在那裏由jeffrey從thomas.loc.gov的鏈接沒被包含'jeffrey'做爲User列值的行匹配,可是由沒有用戶名的題目匹配!結果是,jeffrey被鑑定爲匿名用戶,即便他鏈接時指定了用戶名。

若是你可以鏈接服務器,但你的權限不是你指望的,你可能被鑑定爲其它帳戶。要想找出服務器用來鑑定你的帳戶,使用CURRENT_USER()函數。它返回user_name@host_name格式的值,說明User和Host 值匹配user表記錄。假定jeffrey鏈接併發出下面的查詢:

mysql> SELECT CURRENT_USER();
+----------------+
| CURRENT_USER() |
+----------------+
| @localhost     |
+----------------+

這兒顯示的結果說明user錶行有空的User列值。換句話說,服務器將jeffrey視爲匿名用戶。

診斷鑑定問題的另外一個方法是打印出user表而且手動排序它看看第一個匹配在哪兒進行。又見12.9.3節,「信息函數」

5.7.6. 訪問控制, 階段2:請求覈實

一旦你創建了鏈接,服務器進入訪問控制的階段2。對在此鏈接上進來的每一個請求,服務器檢查你想執行什麼操做,而後檢查是否有足夠的權限來執行它。這正是在受權表中的權限列發揮做用的地方。這些權限能夠來自user、db、host、tables_priv或columns_priv表。(你會發現參考5.7.2節,「權限系統工做原理」頗有幫助,它列出了每一個 受權表中呈現的列。)

user表在全局基礎上授予賦予你的權限,該權限無論當前的數據庫是什麼均適用。例如,若是user表授予你DELETE權限, 你能夠刪除在服務器主機上從任何數據庫刪除行!換句話說,user表權限是超級用戶權限。只把user表的權限授予超級用戶如服務器或數據庫主管是明智的。對其餘用戶,你應該把在user表中的權限設成'N'而且僅在特定數據庫的基礎上受權。你能夠爲特定的數據庫、表或列受權。

db和host表授予數據庫特定的權限。在這些表中的範圍列的值能夠採用如下方式:

  • 通配符字符「%」「_」可用於兩個表的Host和Db列。它們與用LIKE操做符執行的模式匹配操做具備相同的含義。若是受權時你想使用某個字符,必須使用反斜現引用。例如,要想在數據庫名中包括下劃線(‘_’),在GRANT語句中用‘\_’來指定。
  • 在db表的'%'Host值意味着「任何主機」,在db表中空Host值意味着「對進一步的信息諮詢host表」(本節後面將描述的一個過程)。
  • 在host表的'%'或空Host值意味着「任何主機」。
  • 在兩個表中的'%'或空Db值意味着「任何數據庫」。
  • 在兩個表中的空User值匹配匿名用戶。

db和host表在服務器啓動時被讀取並排序(同時它讀user表)。db表在Host、Db和User範圍列上排序,而且host表在Host和Db範圍列上排序。對於user表,首先根據最具體的值最後根據最不具體的值排序,而且當服務器尋找匹配條目時,它使用它找到的第一匹配。

tables_priv和columns_priv表授予表和列特定的權限。這些表的範圍列的值能夠以下被指定:

  • 通配符「%」「_」可用在使用在兩個表的Host列。
  • 在兩個表中的'%'或空Host意味着「任何主機」。
  • 在兩個表中的Db、Table_name和Column_name列不能包含通配符或空。

tables_priv和columns_priv表根據Host、Db和User列被排序。這相似於db表的排序,由於只有Host列能夠包含通配符,排序更簡單。

請求證明進程在下面描述。(若是你熟悉訪問檢查的源碼,你會注意到這裏的描述與在代碼使用的算法略有不一樣。描述等價於代碼實際作的東西;不一樣處只是使解釋更簡單。)

對須要管理權限的請求(SHUTDOWN、RELOAD等等),服務器僅檢查user表條目,由於那是惟一指定管理權限的表。若是行許可請求的操做,訪問被受權,不然拒絕。例如,若是你想要執行mysqladmin shutdown,可是因爲user錶行沒有爲你授予HUTDOWN權限,甚至不用檢查db或host表就拒絕你的訪問。(由於它們不包含hutdown_priv行列,沒有這樣作的必要。)

對數據庫有關的請求(INSERT、UPDATE等等),服務器首先經過查找user錶行來檢查用戶的全局(超級用戶)權限。若是行容許請求的操做,訪問被受權。若是在user表中全局權限不夠,服務器經過檢查db和host表肯定特定的用戶數據庫權限:

  1. 服務器在db表的Host、Db和User列上查找匹配。Host和User對應鏈接用戶的主機名和MySQL用戶名。Db列對應用戶想要訪問的數據庫。若是沒有Host和User的行,訪問被拒絕。
  2. 若是db表中有匹配的行並且它的Host列不是空的,該行定義用戶的數據庫特定的權限。
  3. 若是匹配的db表的行的Host列是空的,它表示host表列舉被容許訪問數據庫的主機。在這種狀況下,在host表中做進一步查找以發現Host和Db列上的匹配。若是沒有host錶行匹配,訪問被拒絕。若是有匹配,用戶數據庫特定的權限以在db和host表的行的權限,即在兩個行都是'Y'的權限的交集(而不是並集!)計算。(這樣你能夠授予在db錶行中的通常權限,而後用host錶行按主機主機爲基礎有選擇地限制它們。)

在肯定了由db和host錶行授予的數據庫特定的權限後,服務器把他們加到由user表授予的全局權限中。若是結果容許請求的操做,訪問被受權。不然,服務器檢查在tables_priv和columns_priv表中的用戶的表和列權限並把它們加到用戶權限中。基於此結果容許或拒絕訪問。

用布爾術語表示,前面關於用戶權限如何計算的描述能夠這樣總結:

global privileges
OR (database privileges AND host privileges)
OR table privileges
OR column privileges

它可能不明顯,爲何呢,若是全局user行的權限最初發現對請求的操做不夠,服務器之後把這些權限加到數據庫、表並列的特定權限。緣由是請求可能要求超過一種類型的權限。例如,若是你執行INSERT INTO ... SELECT語句,你就須要INSERT和SELECT權限。你的權限必須是user錶行授予一個權限而db錶行授予另外一個權限。在這種狀況下,你有必要的權限執行請求,可是服務器不能本身把兩個表區別開來;兩個行授予的權限必須組合起來。

host表不受GRANT或REVOKE語句的影響,所以在大多數MySQL安裝中沒有使用。若是你直接修改它,你能夠用於某種專門目的,例如用來維護安全服務器列表。例如,在TcX,host表包含在本地網絡上全部的機器的表。這些表被授予全部的權限。

你也能夠使用host表指定安全的主機。假定你有一臺機器public.your.domain,它位於你認爲不安全的公共區域,你能夠用下列的host表條目容許除了那臺機器外的網絡上全部主機的訪問:

+--------------------+----+-
| Host               | Db | ...
+--------------------+----+-
| public.your.domain | %  | ... (all privileges set to 'N')
| %.your.domain      | %  | ... (all privileges set to 'Y')
+--------------------+----+-

固然,必定要測試受權表中的行(例如,使用SHOW GRANTS或mysqlaccess),確保你的訪問權限實際按你指望的方式被設置。

5.7.7. 權限更改什麼時候生效

當mysqld啓動時,全部受權表的內容被讀進內存而且今後時生效。

當服務器注意到受權表被改變了時,現存的客戶端鏈接有以下影響:

  • 表和列權限在客戶端的下一次請求時生效。
  • 數據庫權限改變在下一個USE db_name命令生效。

·         全局權限的改變和密碼改變在下一次客戶端鏈接時生效。

若是用GRANT、REVOKE或SET PASSWORD對受權表進行修改,服務器會注意到並當即從新將受權表載入內存。

若是你手動地修改受權表(使用INSERT、UPDATE或DELETE等等),你應該執行mysqladmin flush-privilegesmysqladmin reload告訴服務器再裝載受權表,不然你的更改將不會生效,除非你重啓服務器。

若是你直接更改了受權表但忘記重載,重啓服務器後你的更改方生效。這樣可能讓你迷惑爲何你的更改沒有什麼變化!

5.7.8. 拒絕訪問錯誤的緣由

當你試着聯接MySQL服務器時,若是碰到問題,下面各項能夠幫助你糾正問題:

·         確保服務器在運行。若是服務器沒有運行,則你不能鏈接服務器。若是你視圖鏈接服務器並看到下述消息,多是服務器沒有運行:

·                shell> mysql
·                ERROR 2003: Can't connect to MySQL server on 'host_name' (111)
·                shell> mysql
·                ERROR 2002: Can't connect to local MySQL server through socket
·                '/tmp/mysql.sock' (111)

也可能服務器正在運行,但你可能使用與服務器上偵聽的不同的TCP/IP端口、命名管道或Unix套接字文件。你能夠調用客戶端程序,指定端口選項來指示正確的端口或套接字選項來指示正確的命名管道或Unix套接字文件。要找出套接字文件的地點,應:

shell> netstat -ln | grep mysql
  • 必須正確設置受權表,以便服務器能夠使用它們進行訪問控制。對於某些分發版類型(例如Windows中的二進制分發版或Linux中的RPM分發版),安裝過程初始化包含 受權表的mysql數據庫。若是分發版沒有這樣作,你必須運行mysql_install_db腳原本手動初始化受權表。詳細內容參見2.9.2節,「Unix下安裝後的過程」

肯定是否要初始化受權表的一個方法是尋找數據目錄下的mysql目錄(數據目錄名一般爲data或var,位於MySQL安裝目錄下)。應保證MySQL數據庫目錄有文件user.MYD。不然,執行mysql_install_db腳本。運行並重啓服務器後,執行該命令來測試初始權限:

shell> mysql -u root test

服務器應該讓你無誤地鏈接。

  • 在新的安裝之後,你應該鏈接服務器而且設置你的用戶及其訪問許可:
·                shell> mysql -u root mysql

服務器應該讓你鏈接,由於MySQL root用戶初始時沒有密碼。那也是安全風險,當你正在設置其餘MySQL用戶時,也應設定root密碼是一件重要的事請。關於設置初始密碼的說明,參見2.9.3節,「使初始MySQL帳戶安全」

  • 若是你將一個現存的MySQL安裝升級到較新的版本,運行了mysql_fix_privilege_tables腳本嗎?若是沒有,運行它。增長新功能後,受權表的結構可能會改變,所以更新後應確保表的結構隨之更新。相關說明參見2.10.2節,「升級受權表」

·         若是客戶端程序試圖鏈接時收到如下錯誤信息,說明服務器須要新格式的密碼,而客戶端不能生成:

·                shell> mysql
·                Client does not support authentication protocol requested
·                by server; consider upgrading MySQL client

關於如何處理的詳細信息,參見5.7.9節,「MySQL 4.1中的密碼哈希處理」A.2.3節,「客戶端不支持鑑定協議」

  • 若是你做爲root試試鏈接而且獲得這個錯誤,這意味着,你沒有行在user表中的User列值爲'root'而且mysqld不能爲你的客戶端解析主機名:
  • Access denied for user ''@'unknown' to database mysql

在這種狀況下,你必須用--skip-grant-tables選項重啓服務器而且編輯/etc/hosts\windows\hosts文件爲你的主機增長行。

  • 若是你從3.22.11之前的版本更新現存的MySQL安裝到3.22.11版或之後版本,你運行了mysql_fix_privilege_tables腳本嗎?若是沒有,運行它。在GRANT語句變得能工做時,受權表的結構用MySQL 3.22.11修改 。

·         記住客戶端程序使用選項文件或環境變量中指定的鏈接參數。若是客戶端程序發送不正確的默認鏈接參數,而你沒有在命令行中指定,檢查環境變量和適用的選項文件。例如,當你不用任何選項運行客戶端程序,獲得Access denied錯誤,確保你沒有在選項文件中指定舊密碼!

你能夠經過使用--no-defaults選項調用客戶端程序來禁用選項文件。例如:

shell> mysqladmin --no-defaults -u root version

客戶端使用的選項文件見4.3.2節,「使用選項文件」。環境變量列於附錄F:環境變量

·         若是遇到下述錯誤,說明root密碼錯誤:

·                shell> mysqladmin -u root -pxxxx ver
·                Access denied for user 'root'@'localhost' (using password: YES)

若是你未指定密碼時出現前面的錯誤,說明某個選項文件中的密碼不正確。試試前面所說的--no-defaults選項。

關於密碼更改的信息參見5.8.5節,「設置帳戶密碼」

若是你丟失或忘記root密碼,你能夠用--skip-grant-tables重啓 mysqld來更改密碼。參見A.4.1節,「如何復位根用戶密碼」.

·         若是你使用SET PASSWORD、INSERT或UPDATE更改密碼,你必須使用  PASSWORD()函數加密密碼。若是你不使用PASSWORD()函數,密碼不工做。例如,下面的語句設置密碼,但沒能加密,所以用戶後面不能鏈接:

·                mysql> SET PASSWORD FOR 'abe'@'host_name' = 'eagle';

相反,應這樣設置密碼:

mysql> SET PASSWORD FOR 'abe'@'host_name' = PASSWORD('eagle');

當你使用GRANT或CREATE USER語句或mysqladmin password命令指定密碼時,不須要PASSWORD()函數,它們會自動使用PASSWORD()來加密密碼。參見5.8.5節,「設置帳戶密碼」13.5.1.1節,「CREATE USER語法」

·         localhost是你本地主機名的一個同義詞,而且也是若是你不明確地指定主機而客戶端嘗試鏈接的默認主機。

要想在這種系統上避免該問題,你能夠使用--host=127.0.0.1選項來明確命名服務器主機。這樣將經過TCP/IP協議來鏈接本地mysqld服務器。你還能夠指定--host選項使用TCP/IP,使用實際的本機主機名。在這種狀況下,主機名必須指定爲服務器主機上的user錶行,即便你在服務器上運行客戶端程序。

·         當嘗試用mysql -u user_name與數據庫鏈接時,若是你獲得一個Access denied錯誤,可能會遇到與user表有關的問題,經過執行mysql -u root mysql而且執行下面的SQL語句進行檢查:

·                mysql> SELECT * FROM user;

結果應該包含一個有Host和User列的行匹配你的計算機主機名和你的MySQL用戶名。

  • Access denied錯誤消息將告訴你,你正在用哪一個用戶嘗試登陸,你正在試圖鏈接哪一個主機,是否使用了密碼。一般,你應該在user表中有一行,正確地匹配在錯誤消息給出的主機名和用戶名。例如,若是遇到包含using password: NO的錯誤信息,說明你登陸時沒有密碼。

·         若是當你試着從一個不是MySQL服務器正在運行的主機上鍊接時,遇到下列錯誤,那麼在user表中沒有匹配那臺主機的行:

·                Host ... is not allowed to connect to this MySQL server

能夠經過組合你正在試圖鏈接的用戶/主機名設置一個帳戶來修正它。若是你不知道正鏈接的機器的IP號或主機名,應該把一個'%'行做爲Host列值放在user表中。在試圖從客戶端器鏈接之後,經過SELECT USER()查詢顯示你如何真正進行鏈接。(而後用在日誌文件上面顯示出的實際的主機名代替user表中的'%'行。不然,你將獲得一個不安全的系統,由於它容許從任何主機上以任何用戶名鏈接。)

在Linux中,發生該錯誤的另外一個緣由多是你正使用於你所使用版本的glibc庫不一樣版本的庫編譯的二進制MySQL版本。在這種狀況下,你應升級操做系統或glibc,或下載MySQL版本的源碼分發版並本身編譯。源碼RPM通常很容易編譯並安裝,所以不是大問題。

·         若是你鏈接時指定主機名,但獲得錯誤消息主機名未顯示或爲IP號,表示當MySQL服務器將IP號解析爲客戶端來名時遇到錯誤:

·                shell> mysqladmin -u root -pxxxx -h some-hostname ver
·                Access denied for user 'root'@'' (using password: YES)

這表示DNS問題。要想修復,執行mysqladmin flush-hosts來重設內部 DNS主機名緩存。參見7.5.6節,「MySQL如何使用DNS」

一些經常使用的解決方案包括:

o        試試找出DNS服務器的錯誤並修復。

o        在MySQL受權表中指定IP號而不是主機名。

o        在/etc/hosts中放入客戶端名。

o        用--skip-name-resolve選項啓動mysqld

o        用--skip-host-cache選項啓動mysqld

o        在Unix中,若是你在同一臺機器上運行服務器和客戶端,鏈接到localhost。鏈接到的localhost的Unix鏈接使用Unix套接字文件而不是TCP/IP。

o        在Windows中,你在同一臺機器上運行服務器和客戶端而且服務器支持命名管道鏈接,鏈接主機名(週期)。鏈接使用命名管道而不是TCP/IP。

  • 若是mysql -u root test工做可是mysql -h your_hostname -u root test致使Access denied(your_hostname是本地機的實際主機名),那麼在user表中可能沒有你的主機的正確名字。這裏的一個廣泛的問題是在user錶行中的Host值指定一個惟一的主機名,可是你係統的名字解析例程返回一個徹底正規的域名(或相反)。例如,若是你在user表中有一個主機是'tcx'的行,可是你的DNS告訴MySQL你的主機名是'tcx.subnet.se',行將不工做。嘗試把一個行加到user表中,它包含你主機的IP號做爲Host列的值。(另外,你能夠把一個行加到user表中,它有包含一個通配符如'tcx.%'的Host值。然而,使用以「%」結尾的主機名是不安全的而且推薦!)
  • 若是mysql -u user_name test工做可是mysql -u user_name other_db_name不工做,你沒有爲給定的用戶授予other_db_name數據庫的訪問權限。
  • 當在服務器上執行mysql -u user_name時,它工做,可是在其它遠程客戶端上執mysql -h host_name -u user_name時,它卻不工做,你沒有爲給定的用戶授予從遠程主機訪問服務器的權限。
  • 若是你不能弄明白你爲何獲得Access denied,從user表中刪除全部Host包含通配符值的行(包含「%」「_」的條目)。一個很廣泛的錯誤是用Host='%'和User='some_user'插入一個新行,認爲這將容許你指定localhost從同一臺機器進行鏈接。它不工做的緣由是 默認權限包括一個有Host='localhost'和User=''的行,由於那個行的Host值'localhost'比'%'更具體,當從localhost鏈接時,它用於指向新行!正確的步驟是插入Host='localhost'和User='some_user'的第2個行,或刪除Host='localhost'和User=''行。刪除條目後,記住用FLUSH PRIVILEGES語句重載受權表。

·         若是你獲得下列錯誤,能夠與db或host表有關:

·                Access to database denied

若是從db表中選擇了在Host列有空值的條目,保證在host表中有一個或多個相應的條目,指定db表中的條目適用哪些主機。

·         若是你可以鏈接MySQL服務器,但若是在使用命令SELECT ... INTO OUTFILE或LOAD DATA INFILE語句時,你獲得Access denied錯誤,在user表中的條目可能沒有啓用FILE權限。

·         若是你直接更改受權表(例如,使用INSERT、UPDATE或DELETE語句)而且你的更改好像被忽略了,記住你必須執行FLUSH PRIVILEGES語句或mysqladmin flush-privileges命令讓服務器來重讀受權表。不然,直到服務器下次重啓,你的更改方有效。記住用UPDATE命令更改root密碼後,在清空權限前,你不須要指定新密碼,由於服務器還不知道你已經更改了密碼!

·         若是你的權限彷佛在一個會話過程當中改變了,多是一個超級用戶改變了他們。再次裝入受權表會影響新客戶端鏈接,可是它也影響現存的鏈接,如5.7.7節,「權限更改什麼時候生效」小節所述。

·         若是你有Perl、Python或ODBC程序的存取問題,試着用mysql -u user_name db_name或mysql -u user_name -pyour_pass db_name與服務器鏈接。若是你能用mysql客戶端進行鏈接,這是程序的一個問題而不是訪問權限的問題。(注意在-p和密碼之間沒有空格;也能夠使用--password=your_pass語法指定密碼。若是使用-p選項,MySQL提示你輸入密碼。)

·         爲了測試,用--skip-grant-tables選項啓動mysqld守護進程,而後你能夠改變MySQL受權表而且使用mysqlaccess腳本檢查你的修改是否有如期的效果。當你對你的改變滿意時,執行mysqladmin flush-privileges告訴mysqld服務器開始使用新的 受權表。(再次裝入受權表覆蓋了--skip-grant-tables選項。這容許你告訴服務器開始使用受權表,而不用停掉並重啓它)。

·         若是任何其它事情失敗,用調試選項(例如,--debug=d,general,query)啓動mysqld服務器。這將打印有關嘗試鏈接的主機和用戶信息,和發出的每一個命令的信息。請參見E.1.2節,「建立跟蹤文件」

·         若是你有任何與MySQL受權表的其它問題,並且以爲你必須將這個問題發送到郵件表,必定要提供一個MySQL受權表的傾倒副本(dump)。你可用mysqldump mysql命令複製數據庫表。象平時同樣,用mysqlbug腳本郵寄你的問題。參見1.7.1.3節,「如何通報缺陷和問題」。在一些狀況下能夠用--skip-grant-tables重啓mysqld以便能運行mysqldump


 

5.7.9. MySQL 4.1中的密碼哈希處理

MySQL用戶帳戶列於mysql數據庫中的user表內。每一個MySQL帳戶指定一個密碼,儘管保存在user表Password列的密碼不是明文,但哈希值是從表中的記錄計算的。用PASSWORD()函數來計算密碼的哈希值。

MySQL在客戶端/服務器通訊的兩個階段使用密碼:

·         若是客戶端試圖鏈接服務器,有一個初始鑑定步驟,客戶必須提供一個密碼,而且必須與客戶想要使用的帳戶在user表保存的哈希值匹配。

·         客戶端鏈接後,它能夠(若是有充分的權限) 設置或更改user表內所列的帳戶的密碼哈希值值。客戶端能夠經過PASSWORD()函數來生成密碼哈希值,或使用GRANT或SET PASSWORD語句。

換句話說,當客戶端首次試圖鏈接時,服務器使用哈希值進行鑑定。若是鏈接的客戶端調用PASSWORD()函數或使用GRANT或SET語句來設置或更改密碼,則服務器產生哈希值。

在MySQL 4.1中密碼哈希算法已經更新,提供了更好的安全性並下降了密碼被截取的風險。可是,該新機制只能在MySQL 4.1(和更新版本的)服務器和客戶端中使用,會產生一些兼容性問題。4.1或新客戶端能夠鏈接4.1以前的服務器,由於客戶端能夠同時理解舊的和新的密碼哈希機制。可是,4.1以前的客戶端試圖鏈接4.1版或更新版的服務器時會遇到困難。例如,3.23版mysql客戶端試圖鏈接5.1服務器時會失敗並出現下面的錯誤消息:

shell> mysql -h localhost -u root
Client does not support authentication protocol requested
by server; consider upgrading MySQL client

出現該問題的另外一個普通例子是在升級到MySQL 4.1或更新版後,試圖使用舊版本的PHP mysql擴展名。(參見25.3.1節,「使用MySQL和PHP的常見問題」)。

下面討論了新、舊密碼機制之間的差異,以及若是你升級了服務器但須要爲4.1版之前的客戶端保持向後兼容性該怎樣作。A.2.3節,「客戶端不支持鑑定協議」中有更詳細的信息。該信息將MySQL數據庫從4.0版本或更低版升級到4.1版或更高版的PHP編程人員特別重要。

釋:該討論對比了4.1版的行爲和4.1前的行爲,這兒描述的4.1中的行爲實際上從4.1.1開始。MySQL 4.1.0是一個「舊」的發佈,由於它的實施機制與4.1.1版和更新版中的稍有不一樣。在MySQL 5.0 參考手冊中詳細描述了4.1.0和最新版之間的差異。

在MySQL 4.1以前,用PASSWORD()函數計算的密碼哈希值有16個字節長。應爲:

mysql> SELECT PASSWORD('mypass');
+--------------------+
| PASSWORD('mypass') |
+--------------------+
| 6f8c114b58f2ce9e   |
+--------------------+

在MySQL 4.1以前,user表的Password列(保存了哈希值)也是16字節長。

在MySQL 4.1中,已經對PASSWORD()函數進行了修改,能夠生成41字節的哈希值:

mysql> SELECT PASSWORD('mypass');
+-------------------------------------------+
| PASSWORD('mypass')                        |
+-------------------------------------------+
| *6C8989366EAF75BB670AD8EA7A7FC1176A95CEF4 |
+-------------------------------------------+

一樣,user表的Password列必須有41字節長來保存這些值:

·         若是你新安裝MySQL 5.1, Password列自動爲41字節長。

·         從MySQL 4.1(4.1.1或4.1系列的更新版)升級到MySQL 5.1,應不會出現相關問題,由於兩個版本使用相同的密碼哈希機制。若是你想要將更早版本的MySQL升級到MySQL5.1,你應先升級到4.1,而後將4.1升級到5.1。

加寬的Password列能夠同時保存新、舊格式的密碼哈希值。能夠有兩種方式肯定任何給定格式的密碼哈希值:

·         明顯的不一樣之處是長度(16字節和41字節)。

·         第2個不一樣之處是新格式的密碼哈希值都以‘*’字符開頭,而舊格式的密碼絕對不是。

 長密碼哈希值具備更好的加密屬性,而且客戶端根據長哈希值進行鑑定比舊的短哈希值更加安全。

短密碼哈希值和長密碼哈希值之間的不一樣之處與服務器如何使用密碼進行鑑定以及如何爲執行密碼更改操做的鏈接的客戶端生成密碼哈希值都有關。

服務器使用密碼哈希值進行鑑定的方式受Password列的寬度影響:

·         若是列較短,只用短哈希鑑定。

·         若是列較長,能夠有短或長哈希值,而且服務器能夠使用任何一種格式:

o        4.1以前的客戶端能夠鏈接,它們只能夠使用舊的哈希機制,它們能夠只鑑定有短哈希的帳戶。

o        4.1及之後版本的客戶端能夠鑑定有短哈希或長哈希的帳戶。

對於短哈希帳戶的鑑定過程,4.1和之後版本的客戶端比爲舊版本的客戶端實際要安全得多。從安全性角度,從最低安全到最安全的梯度爲:

·         4.1以前的客戶端用短密碼哈希值進行鑑定

·         4.1或之後版本的客戶端用短密碼哈希值進行鑑定

·         4.1或之後版本的客戶端用長密碼哈希值進行鑑定

服務器爲鏈接的客戶端生成密碼哈希值的方式受Password列寬度和--old-passwords選項的影響。4.1或更新版本的服務器只有知足某個條件才生成長哈希:Password列必須足夠寬以容納長哈希值而且未給定--old-passwords選項。這些條件適合:

·         Password列必須足夠寬以容納長哈希(41字節)值。若是列沒有更新,仍然爲4.1以前的16字節寬,當客戶端使用PASSWORD()、GRANT或SET PASSWORD執行密碼更改操做時,服務器注意到長哈希不適合,只生成短哈希。若是你已經升級到4.1但尚未運行 mysql_fix_privilege_tables腳原本擴寬Password列時會出現這種行爲。

·         若是Password列足夠寬,則能夠保存短或長密碼哈希值。在這種狀況下,PASSWORD()、GRANT或SET PASSWORD生成長哈希,除非 用--old-passwords選項啓動服務器。該選項強制服務器生成短密碼哈希值。

--old-passwords選項的目的是當服務器生成長密碼哈希值時,容許你維持同4.1以前的客戶端的向後兼容性。該選項不影響鑑定(4.1和之後版本的客戶端仍然能夠使用有長密碼哈希值的帳戶),但它防止在密碼更改操做中在user表中建立長密碼哈希值。在這種狀況下,該帳戶不能再用於4.1以前的客戶端。沒有--old-passwords選項,可能會出現下面的不指望的狀況:

·         舊客戶端鏈接有短密碼哈希值的帳戶。

·         客戶更改本身的密碼。沒有--old-passwords,能夠爲該帳戶生成長密碼哈希值。

·         下次舊客戶試圖鏈接帳戶時不能鏈接上,由於帳戶有長密碼哈希值,須要新的哈希機制進行鑑定。(一旦帳戶user表中爲長密碼哈希值,只有4.1和之後版本的客戶端能夠鑑定它,由於4.1以前的客戶端不理解長哈希)。

該場景說明,若是你必須支持舊的4.1以前的客戶端,不使用--old-passwords選項運行4.1或更新版本的服務器很危險。用--old-passwords運行服務器,密碼更改操做不會生成長密碼哈希值,這樣舊客戶端也能夠訪問帳戶。(這些客戶端不能意外地因更改了密碼將本身鎖出去,並留下長密碼哈希值)。

--old-passwords選項的不利之處是你建立或更改的密碼使用短哈希,甚至對於4.1客戶端也如此。這樣,你丟失了長密碼哈希值提供的安全性。若是你想要建立有長哈希的帳戶(例如,爲4.1客戶端),你必須不使用--old-passwords來運行服務器。

下面的場景可用於運行4.1或之後的服務器,包括MySQL 5.1:

場景1:user表中的短Password列:

·         只有短哈希能夠保存到Password列。

·         服務器只使用短哈希進行客戶端鑑定。

·         對於鏈接的客戶端,調用PASSWORD()、GRANT或SET PASSWORD的密碼哈希生成操做專使用短哈希。對帳戶的任何更改均會生成短密碼哈希值。

·          --old-passwords選項能夠使用可是多餘,由於Password列較短,服務器只生成短密碼哈希值。

場景2:長Password列;沒有用--old-passwords選項啓動服務器:

·         短或長哈希能夠保存到Password列。

·         4.1和之後版本的客戶端(包括5.1客戶端)能夠鑑定有短或長哈希的帳戶。

·         4.1以前的客戶端只能鑑定有短哈希的帳戶。

·         對於鏈接的客戶端,調用PASSWORD()、GRANT或SET PASSWORD的密碼哈希生成操做專使用短哈希。對帳戶的任何更改均會生成短密碼哈希值。

如前面所示,該場景的危險性在於4.1以前的客戶端可能不能訪問有短密碼哈希值的帳戶。經過PASSWORD()、GRANT或SET PASSWORDA對這些帳戶密碼的更改會產生長的密碼哈希值。從該點看,4.1以前的客戶端升級到4.1以前不能鑑定該帳戶。

要處理該問題,能夠用特殊方法更改密碼。例如,通常狀況你能夠使用SET PASSWORD按照下面的方法更改帳戶密碼:

mysql> SET PASSWORD FOR 'some_user'@'some_host' = PASSWORD('mypass');

要想更改密碼但建立短哈希,使用OLD_PASSWORD()函數:

mysql> SET PASSWORD FOR 'some_user'@'some_host' = OLD_PASSWORD('mypass');

當你想明顯生成短哈希時,OLD_PASSWORD()頗有用。

場景3:長Password列;用--old-passwords選項啓動4.1或新版本的服務器:

·         短或長哈希能夠保存到Password列。

·         4.1和之後版本的客戶端能夠鑑定有短或長哈希的帳戶(請注意只有不使用--old-passwords選項啓動服務器,方能夠建立長哈希)。

·         4.1以前的客戶端只能夠鑑定短哈希帳戶。

·         對於鏈接的客戶端,調用PASSWORD()、GRANT或SET PASSWORD的密碼哈希生成操做專使用短哈希。對帳戶的任何更改均會生成短密碼哈希值。

在該場景中,你不能建立長密碼哈希值的帳戶,由於--old-passwords選項防止生成長哈希。而且,若是你在使用--old-passwords選項前建立長哈希帳戶,當--old-passwords有時更改帳戶密碼,結果會使帳戶的密碼爲短密碼,安全性較長哈希要下降。

這些場景的不利之處能夠歸納爲:

在場景1中,你不能利用長哈希提供更安全的鑑定。

在場景2中, 若是你沒有顯式使用OLD_PASSWORD()來更改密碼,則4.1以前的客戶端不能再訪問短哈希帳戶。

在場景3中,--old-passwords防止短哈希帳戶不可訪問,但密碼更改操做使帳戶的長哈希轉換爲短哈希,當--old-passwords有效時不能將它改回長哈希。

5.7.9.1. 更改應用程序密碼哈希值的含義

升級到MySQL4.1或更新版本後,使用PASSWORD()爲本身的目的生成密碼的應用程序會出現兼容性問題。應用程序實際不該這樣作,由於PASSWORD()只應用來管理MySQL帳戶的密碼。但一些應用程序使用PASSWORD()用於本身的目的。

若是你從MySQL 4.1以前的版本升級到4.1或之後版本,並在生成長密碼哈希值的條件下運行服務器,應用程序使用PASSWORD()破解本身的密碼。這種狀況下推薦的方法是修改應用程序,使用其它函數,例如SHA1()或MD5(),來產生哈希值。若是不行,你能夠使用OLD_PASSWORD()函數,該函數用來提供舊格式的短哈希。可是,請注意OLD_PASSWORD()可能有一天再也不被支持。

若是服務器運行在生成短哈希的條件下,能夠使用 OLD_PASSWORD()但與PASSWORD()等同。

將MySQL數據庫從4.0或更低版本移植到4.1或更高版本的PHP編程人員應參閱舊客戶端

5.8. MySQL用戶帳戶管理

本節描述如何爲MySQL服務器的客戶端設置帳戶。討論了下面的主題:

·         MySQL使用的帳戶名和密碼的含義,以及如何比較你的操做系統所使用的帳戶名和密碼

·         如何設置新帳戶並移除已有帳戶

·         如何更改密碼

·         安全使用密碼指導

·         如何使用安全SSL鏈接

5.8.1. MySQL用戶名和密碼

用用戶名和客戶端或主機定義MySQL帳戶,用戶能夠根據這些名稱來鏈接服務器。帳戶也有密碼。MySQL和操做系統使用用戶名和密碼的方式有幾處區別:

·         MySQL用於鑑定目的用戶名與Windows或Unix使用的用戶名(登陸名)沒有關係。在Unix中,大多數MySQL客戶端默認試圖使用當前Unix的用戶名做爲MySQL用戶名來登陸,但這樣只是爲了方便。 默認值能夠很容易被覆蓋,由於客戶端程序容許用-u或--user選項來指定用戶名。由於這表示任何人能夠試圖使用任何用戶名來鏈接服務器,除非全部MySQL帳戶有密碼,不然你不能使數據庫保持安全。經過爲沒有密碼的帳戶指定用戶名,任何人可以成功鏈接服務器。

·         MySQL用戶名最大客達16字符長。這樣能夠限制MySQL服務器和客戶端之間的硬編碼,而且防止經過修改mysql數據庫中表的定義來偷竊密碼。

:你應絕對不要以任何方式修改mysql數據庫中的任何表,只能運行MySQL分發中專爲此目的提供的腳本。將MySQL系統表從新定義爲其它方式會致使未定義的(和不支持的!)行爲

操做系統用戶名與MySQL用戶名徹底不相關,甚至最大長度可能不一樣。例如, Unix用戶名限制爲8個字符。

·         MySQL密碼與登陸到你的操做系統的密碼沒有關係。不須要將你用來登陸Windows或Unix機器的密碼和你用來訪問該機器上的MySQL服務器的密碼關聯起來。

·         MySQL的加密密碼使用本身的算法。該加密算法不一樣於Unix登陸過程使用的算法。MySQL密碼加密與PASSWORD()SQL函數的方法相同。Unix密碼加密與ENCRYPT()SQL函數的方法相同。PASSWORD()和ENCRYPT()函數的描述參見12.9.2節,「加密函數」。從版本4.1 起,MySQL使用更強的鑑定方法,同之前的版本相比能夠在鏈接過程當中提供更好的密碼保護。即便TCP/IP包被截取或mysql數據庫被捕獲也很安全。(在前面的版本中,即便密碼以加密形式保存到user表中,仍能夠經過加密密碼值來鏈接MySQL服務器)。

當安裝MySQL時,受權表裝載時有一系列初使帳戶。這些帳戶的名稱和訪問權限見2.9.3節,「使初始MySQL帳戶安全」,其中還討論瞭如何未這些帳戶賦予密碼。所以,你通常應使用GRANT和REVOKE語句來設置、修改和移除MySQL帳戶。參見13.5.1.3節,「GRANT和REVOKE語法」

當用命令行客戶端鏈接MySQL服務器時,你應爲想要使用的帳戶指定用戶名和密碼:

shell> mysql --user=monty --password=guess db_name

若是你想用較短的選項,命令應爲:

shell> mysql -u monty -pguess db_name

-p選項和後面的密碼值之間絕對不能有空格。參見5.7.4節,「與MySQL服務器鏈接」

前面的命令包括命令行中的密碼值,會很危險。參見5.8.6節,「使你的密碼安全」。要想避免,指定--password或-p選項後面不跟任何密碼值:

shell> mysql --user=monty --password db_name
shell> mysql -u monty -p db_name

而後客戶端程序輸出提示符並等待你輸入密碼。(在這些示例中,db_name並不爲密碼,由於用空格將它同前面的密碼項隔離開了)。

在一些系統中,MySQL用來提示輸入密碼的庫調用自動將密碼限制到8個字符。這是系統庫的問題,而不是MySQL的問題。MySQL自己並不限制密碼的長度。要解決該問題,將MySQL密碼改成8個字符和更少字符的值,或將密碼放入選項文件中。

5.8.2. 向MySQL增長新用戶帳戶

能夠用兩種方式建立MySQL帳戶:

·         使用GRANT語句

·         直接操做MySQL受權表

最好的方法是使用GRANT語句,由於這樣更精確,錯誤少。從MySQL 3.22.11起提供了GRANT;其語法見13.5.1.3節,「GRANT和REVOKE語法」

建立帳戶的其它方法是使用MySQL帳戶管理功能的第三方程序。phpMyAdmin便是一個程序。

下面的示例說明如何使用MySQL客戶端程序來設置新用戶。假定按照2.9.3節,「使初始MySQL帳戶安全」描述的 默認值來設置權限。這說明爲了更改,你必須以MySQL root用戶鏈接MySQL服務器,而且root帳戶必須有mysql數據庫的INSERT權限和RELOAD管理權限。

首先,使用MySQL程序以MySQL root用戶來鏈接服務器:

shell> MySQL --user=root MySQL

若是你爲root帳戶指定了密碼,還須要爲該MySQL命令和本節中的其它命令提供--password或-p選項。

以root鏈接到服務器上後,能夠添加新帳戶。下面的語句使用GRANT來設置四個新帳戶:

mysql> GRANT ALL PRIVILEGES ON *.* TO 'monty'@'localhost'
    ->     IDENTIFIED BY 'some_pass' WITH GRANT OPTION;
mysql> GRANT ALL PRIVILEGES ON *.* TO 'monty'@'%'
    ->     IDENTIFIED BY 'some_pass' WITH GRANT OPTION;
mysql> GRANT RELOAD,PROCESS ON *.* TO 'admin'@'localhost';
mysql> GRANT USAGE ON *.* TO 'dummy'@'localhost';

用GRANT語句建立的帳戶有下面的屬性:

·         其中兩個帳戶有相同的用戶名monty和密碼some_pass。兩個帳戶均爲超級用戶帳戶,具備徹底的權限能夠作任何事情。一個帳戶 ('monty'@'localhost')只用於從本機鏈接時。另外一個帳戶('monty'@'%')可用於從其它主機鏈接。請注意monty的兩個帳戶必須能從任何主機以monty鏈接。沒有localhost帳戶,當monty從本機鏈接時,mysql_install_db建立的localhost的匿名用戶帳戶將佔先。結果是,monty將被視爲匿名用戶。緣由是匿名用戶帳戶的Host列值比'monty'@'%'帳戶更具體,這樣在user表排序順序中排在前面。(user表排序的討論參見5.7.5節,「訪問控制, 階段1:鏈接覈實」)。

·         一個帳戶有用戶名admin,沒有密碼。該帳戶只用於從本機鏈接。授予了RELOAD和PROCESS管理權限。這些權限容許admin用戶執行mysqladmin reloadmysqladmin refreshmysqladmin flush-xxx命令,以及mysqladmin processlist。未授予訪問數據庫的權限。你能夠經過GRANT語句添加此類權限。

·         一個帳戶有用戶名dummy,沒有密碼。該帳戶只用於從本機鏈接。未授予權限。經過GRANT語句中的USAGE權限,你能夠建立帳戶而不授予任何權限。它能夠將全部全局權限設爲'N'。假定你將在之後將具體權限授予該帳戶。

除了GRANT,你能夠直接用INSERT語句建立相同的帳戶,而後使用FLUSH PRIVILEGES告訴服務器重載受權表:

shell> mysql --user=root mysql
mysql> INSERT INTO user
    ->     VALUES('localhost','monty',PASSWORD('some_pass'),
    ->     'Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y');
mysql> INSERT INTO user
    ->     VALUES('%','monty',PASSWORD('some_pass'),
    ->     'Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y');
mysql> INSERT INTO user SET Host='localhost',User='admin',
    ->     Reload_priv='Y', Process_priv='Y';
mysql> INSERT INTO user (Host,User,Password)
    ->     VALUES('localhost','dummy','');
mysql> FLUSH PRIVILEGES;

當你用INSERT建立帳戶時使用FLUSH PRIVILEGES的緣由是告訴服務器重讀受權表。不然,只有重啓服務器後更改方會被注意到。使用 GRANT,則不須要使用FLUSH PRIVILEGES。

用INSERT使用PASSWORD()函數是爲了加密密碼。GRANT語句爲你加密密碼,所以不須要PASSWORD()。

'Y'值啓用帳戶權限。對於admin帳戶,還能夠使用更加可讀的INSERT擴充的語法(使用SET)。

在爲dummy帳戶的INSERT語句中,只有user表中的Host、User和Password列記錄爲指定的值。沒有一個權限列爲顯式設置,所以MySQL將它們均指定爲 默認值'N'。這樣等同於GRANT USAGE的操做。

請注意要設置超級用戶帳戶,只須要建立一個權限列設置爲'Y'的user表條目。user表權限爲全局權限,所以其它 受權表再也不須要條目。

下面的例子建立3個帳戶,容許它們訪問專用數據庫。每一個帳戶的用戶名爲custom,密碼爲obscure。

要想用GRANT建立帳戶,使用下面的語句:

shell> MySQL --user=root MySQL
shell> mysql --user=root mysql
mysql> GRANT SELECT,INSERT,UPDATE,DELETE,CREATE,DROP
    ->     ON bankaccount.*
    ->     TO 'custom'@'localhost'
    ->     IDENTIFIED BY 'obscure';
mysql> GRANT SELECT,INSERT,UPDATE,DELETE,CREATE,DROP
    ->     ON expenses.*
    ->     TO 'custom'@'whitehouse.gov'
    ->     IDENTIFIED BY 'obscure';
mysql> GRANT SELECT,INSERT,UPDATE,DELETE,CREATE,DROP
    ->     ON customer.*
    ->     TO 'custom'@'server.domain'
    ->     IDENTIFIED BY 'obscure';

這3個帳戶能夠用於:

·         第1個帳戶能夠訪問bankaccount數據庫,但只能從本機訪問。

·         第2個帳戶能夠訪問expenses數據庫,但只能從主機whitehouse.gov訪問。

·         第3個帳戶能夠訪問customer數據庫,但只能從主機server.domain訪問。

要想不用GRANT設置custom帳戶,使用INSERT語句直接修改 受權表:

shell> mysql --user=root mysql
mysql> INSERT INTO user (Host,User,Password)
    ->     VALUES('localhost','custom',PASSWORD('obscure'));
mysql> INSERT INTO user (Host,User,Password)
    ->     VALUES('whitehouse.gov','custom',PASSWORD('obscure'));
mysql> INSERT INTO user (Host,User,Password)
    ->     VALUES('server.domain','custom',PASSWORD('obscure'));
mysql> INSERT INTO db
    ->     (Host,Db,User,Select_priv,Insert_priv,
    ->     Update_priv,Delete_priv,Create_priv,Drop_priv)
    ->     VALUES('localhost','bankaccount','custom',
    ->     'Y','Y','Y','Y','Y','Y');
mysql> INSERT INTO db
    ->     (Host,Db,User,Select_priv,Insert_priv,
    ->     Update_priv,Delete_priv,Create_priv,Drop_priv)
    ->     VALUES('whitehouse.gov','expenses','custom',
    ->     'Y','Y','Y','Y','Y','Y');
mysql> INSERT INTO db
    ->     (Host,Db,User,Select_priv,Insert_priv,
    ->     Update_priv,Delete_priv,Create_priv,Drop_priv)
    ->     VALUES('server.domain','customer','custom',
    ->     'Y','Y','Y','Y','Y','Y');
mysql> FLUSH PRIVILEGES;
 

前3個INSERT語句在user表中加入條目,容許用戶custom從各類主機用給定的密碼進行鏈接,但不授予全局權限(全部權限設置爲 默認值'N')。後面3個INSERT語句在user表中加入條目,爲custom授予bankaccount、expenses和customer數據庫權限,但只能從合適的主機訪問。一般若直接修改 受權表,則應告訴服務器用FLUSH PRIVILEGES重載受權表,使權限更改生效。

若是你想要讓某個用戶從給定域的全部機器訪問(例如,mydomain.com),你能夠在帳戶名的主機部分使用含‘%’通配符的GRANT語句:

mysql> GRANT ...
    ->     ON *.*
    ->     TO 'myname'@'%.mydomain.com'
    ->     IDENTIFIED BY 'mypass';

要想經過直接修改受權表來實現:

mysql> INSERT INTO user (Host,User,Password,...)
    ->     VALUES('%.mydomain.com','myname',PASSWORD('mypass'),...);

mysql> FLUSH PRIVILEGES;

5.8.3. 從MySQL刪除用戶帳戶

要想移除帳戶,應使用DROP USER語句,請參見13.5.1.2節,「DROP USER語法」

5.8.4. 限制帳戶資源

限制MySQL服務器資源使用的一個方法是將max_user_connections系統變量設置爲非零值。可是,該方法嚴格限於全局,不容許管理具體帳戶。而且,它只限制使用單一帳戶同時鏈接的數量,而不是客戶端鏈接後的操做。許多MySQL管理員對兩種類型的控制均感興趣,特別是Internet服務提供者。

在MySQL 5.1中,你能夠爲具體帳戶限制下面的服務器資源:

·         帳戶每小時能夠發出的查詢數

·         帳戶每小時能夠發出的更新數

·         帳戶每小時能夠鏈接服務器的次數

客戶端能夠執行的語句根據查詢限制來記數。只有修改數據庫或表的語句根據更新限制來記數。

還能夠限制每一個帳戶的同時鏈接服務器的鏈接數。

本文中的帳戶爲user表中的單個記錄。根據User和Host列值惟一識別每一個帳戶。

作爲使用該特性的先決條件,mysql數據庫的user表必須包含資源相關的列。資源限制保存在max_questions、max_updates、max_connections和max_user_connections列內。若是user表沒有這些列,必須對它進行升級;參見2.10.2節,「升級受權表」

要想用GRANT語句設置資源限制,使WITH子句來命名每一個要限制的資源和根據每小時記數的限制值。例如,要想只以限制方式建立能夠訪問customer數據庫的新帳戶,執行該語句:

mysql> GRANT ALL ON customer.* TO 'francis'@'localhost'
    ->     IDENTIFIED BY 'frank'
    ->     WITH MAX_QUERIES_PER_HOUR 20
    ->          MAX_UPDATES_PER_HOUR 10
    ->          MAX_CONNECTIONS_PER_HOUR 5
    ->          MAX_USER_CONNECTIONS 2;

限制類型不須要所有在WITH子句中命名,但已經命名的能夠按任何順序。每一個每小時限制值均應爲整數,表明每小時的記數。若是GRANT語句沒有WITH子句,則每一個限制值設置爲 默認值零(即沒有限制)。對於MAX_USER_CONNECTIONS,限制爲整數,表示帳戶一次能夠同時鏈接的最大鏈接數。若是限制設置爲 默認值零,則根據MAX_USER_CONNECTIONS系統變量肯定該帳戶能夠同時鏈接的數量。

要想設置或更改已有帳戶的限制,在全局級別使用GRANT USAGE語句(在*.*)。下面的語句能夠將francis的查詢限制更改成100:

mysql> GRANT USAGE ON *.* TO 'francis'@'localhost'
    ->     WITH MAX_QUERIES_PER_HOUR 100;

該語句沒有改變帳戶的已有權限,只修改了指定的限制值。

要想取消已有限制,將該值設置爲零。例如,要想取消francis每小時能夠鏈接的次數的限制,使用該語句:

mysql> GRANT USAGE ON *.* TO 'francis'@'localhost'
    ->     WITH MAX_CONNECTIONS_PER_HOUR 0;

當帳戶使用資源時若是有非零限制,則對資源使用進行記數。

服務器運行時,它統計每一個帳戶使用資源的次數。若是帳戶在最後一個小時的鏈接次數達到限制,該帳戶的進一步的鏈接被拒絕。相似地,若是帳戶達到查詢或更新次數的限制,進一步的查詢或更新被拒絕。在這種狀況下,會給出相關錯誤消息。

根據每一個帳戶進行資源計算,而不是根據每一個客戶端。例如,若是你的帳戶的查詢限制爲50,你不能經過兩個客戶端同時鏈接服務器將限制增長到100。兩個鏈接的查詢被計算到一塊兒。

能夠爲全部帳戶從全局重設當前的每小時資源使用記數,或單獨重設給定的帳戶:

·         要想將全部帳戶當前的記數重設爲零,能夠執行FLUSH USER_RESOURCES語句。還能夠經過重載受權表來重設記數(例如,使用FLUSH PRIVILEGES語句或mysqladmin reload命令)。

·         將具體帳戶的限制從新授予任何值,能夠將它設置爲零。要想實現,按照前面所述使用GRANT USAGE,並將限制值指定爲該帳戶當前的限制值。

計數器重設不影響MAX_USER_CONNECTIONS限制。

當服務器啓動時全部記數從零開始。

5.8.5. 設置帳戶密碼

  • 能夠用mysqladmin命令在命令行指定密碼:
    shell> mysqladmin -u user_name -h host_name password "newpwd"

    該命令重設密碼的帳戶爲user表內匹配User列的user_name和Host列你發起鏈接的客戶端的記錄。

    爲帳戶賦予密碼的另外一種方法是執行SET PASSWORD語句:

    mysql> SET PASSWORD FOR 'jeffrey'@'%' = PASSWORD('biscuit');

    只有root等能夠更新mysql數據庫的用戶能夠更改其它用戶的密碼。若是你沒有以匿名用戶鏈接,省略FOR子句即可以更改本身的密碼:

    mysql> SET PASSWORD = PASSWORD('biscuit');

    你還能夠在全局級別使用GRANT USAGE語句(在*.*)來指定某個帳戶的密碼而不影響帳戶當前的權限:

    mysql> GRANT USAGE ON *.* TO 'jeffrey'@'%' IDENTIFIED BY 'biscuit';

    通常狀況下最好使用上述方法來指定密碼,你還能夠直接修改user表:

    ·         要想在建立新帳戶時創建密碼,在Password列提供一個值:

    ·                shell> mysql -u root mysql
    ·                mysql> INSERT INTO user (Host,User,Password)
    ·                     -> VALUES('%','jeffrey',PASSWORD('biscuit'));
    ·                mysql> FLUSH PRIVILEGES;
    ·                 

    ·         要想更改已有帳戶的密碼,使用UPDATE來設置Password列值:

    ·                shell> mysql -u root mysql
    ·                 mysql> UPDATE user SET Password = PASSWORD('bagel')
    ·                       -> WHERE Host = '%' AND User = 'francis';
    ·                mysql> FLUSH PRIVILEGES;

    當你使用SET PASSWORD、INSERT或UPDATE指定帳戶的密碼時,必須用PASSWORD()函數對它進行加密。(惟一的特例是若是密碼爲空,你不須要使用PASSWORD())。須要使用PASSWORD()是由於user表以加密方式保存密碼,而不是明文。若是你忘記了,你可能會象這樣設置密碼:

    shell> mysql -u root mysql
    mysql> INSERT INTO user (Host,User,Password)
        -> VALUES('%','jeffrey','biscuit');
    mysql> FLUSH PRIVILEGES;
     

    結果是密碼'biscuit'保存到user表後沒有加密。當jeffrey使用該密碼鏈接服務器時,值被加密並同保存在user表中的進行比較。可是,保存的值爲字符串'biscuit',所以比較將失敗,服務器拒絕鏈接:

    shell> mysql -u jeffrey -pbiscuit test
    Access denied

    若是你使用GRANT ... IDENTIFIED BY語句或mysqladmin password命令設置密碼,它們均會加密密碼。在這種狀況下,不須要使用 PASSWORD()函數。

    釋:PASSWORD()加密不一樣於Unix密碼加密。參見5.8.1節,「MySQL用戶名和密碼」

5.8.6. 使你的密碼安全

在管理級別,你決不能將mysql.user表的訪問權限授予任何非管理帳戶。

當你運行客戶端程序鏈接MySQL服務器時,以一種暴露的可被其餘用戶發現的方式指定你的密碼是不穩當的。當你運行客戶端程序時,你能夠使用下列方法指定你的密碼,還有每一個方法的風險評估:

·         使用一個在命令行上-pyour_pass或--password=your_pass的選項。例如:

·                shell> mysql -u francis -pfrank db_name

這很方便可是不安全,由於你的密碼對系統狀態程序(例如ps)變得可見,它能夠被其餘的用戶調用來顯示命令行。通常MySQL客戶在他們的初始化順序期間用零覆蓋命令行參數,可是仍然有一個短暫間隔時間內參數值可見的。

·         使用一個-p或--password選項(沒有指定密碼)。在這種狀況下,客戶端程序請求來自終端的密碼:

·                shell> mysql -u francis -p db_name
·                Enter password: ********

 「*」字符指示輸入密碼的地方。輸入密碼時密碼看不見。

由於它對其餘用戶不可見,與在命令行上指定它相比,這樣進入你的密碼更安全。然而,這個輸入一個密碼的方法僅僅爲你交互式運行程序是合適的。若是你想要從非交互式運行的一個腳本調用一個客戶端,就沒有從終端輸入入密碼的機會。在某些系統中,你甚至會發現腳本的第一行被(錯誤地)讀並解釋爲你的密碼!

·         在一個配置文件中存儲你的密碼。例如,在Unix中,你可在主目錄的「.my.cnf」文件中的[client]節列出你的密碼:

·                [client]
·                password=your_pass

若是你在「.my.cnf」裏面存儲密碼,除了你本人其它人不能訪問該文件。保證文件的訪問模式是400或600。例如:

shell> chmod 600 .my.cnf

關於選項文件的詳細討論參見4.3.2節,「使用選項文件」

·         你可在MYSQL_PWD環境變量中存儲密碼。可是這種指定MySQL密碼的方法是極不安全的,不該該使用。ps的某些版本包括顯示運行進程的環境的選項;若是你設定MYSQL_PWD,你的密碼將被運行ps的全部人看見,甚至在沒有這樣一個版本的ps的系統上,沒有其它方法觀察到進程環境的假設是不明智的。參見附錄F:環境變量

總之,最安全的方法是讓客戶端程序提示輸入密碼或在適當保護的選項文件中指定密碼。

5.8.7. 使用安全鏈接

MySQL支持MySQL客戶端和服務器之間的安全(加密的)鏈接所使用的安全套接字層(SSL)協議。本節討論如何使用SSL鏈接。還描述了在Windows中設置SSH的方法。

MySQL的標準配置傾向於儘量快,所以默認狀況不使用加密鏈接。使用該協議會使客戶端/服務器協議慢得多。對數據進行加密很是耗CPU,須要計算機多作許多工做,會延遲MySQL的其它任務。對於須要經過加密鏈接提供安全的應用程序,能夠保證額外的計算。

MySQL容許在鏈接前啓用加密。你能夠根據具體應用程序的需求選擇普通未加密鏈接或安全加密SSL鏈接。

5.8.7.1. SSL基本概念

要想理解MySQL如何使用SSL,須要解釋一些基本SSL和X509概念。熟悉的人們能夠跳過該部分。

默認狀況下,MySQL在客戶端和服務器之間使用未加密的鏈接。這說明能夠訪問網絡的部分人能夠看到你的通訊,並看到發送和接收的數據。他們甚至能夠更改在客戶端和服務器之間傳遞的數據。要想提升安全性,當調用客戶端程序時,你能夠經過--compress選項壓縮客戶端/服務器之間的通訊。可是,這樣並不能阻擋住頑固的攻擊者。

當你須要以安全方式在網絡中傳遞信息時,未加密的鏈接是不可接受的。加密是使任何數據不可讀的方法。事實上,今天的許多慣例須要加密算法提供更加安全的要素。它們應能抵抗各類已知的攻擊,例如更改加密消息的順序或兩次重放數據。

SSL是一種使用不一樣的加密算法確保從公用網接收到的數據是可信的協議。它具備檢測數據更改、丟失或重放的機制。SSL還包括使用 X509標準提供身份認證的算法。

使用X509,能夠識別Internet上的某些人。一般用於電子商務應用程序中。按照基本概念,應有某種稱之爲「認證機構」(或CA)的機構,能夠向請求者分發電子證書。證書依賴非對稱加密算法,有兩個加密密鑰(公共密鑰和私人密鑰)。認證持有者能夠向其它方出示證書來證實身份。證書包括持有者的公共密鑰。只能使用對應的私人密鑰對含該公共密鑰的加密數據進行解密,私人密鑰由證書持有者擁有。

若是你須要關於SSL、X50九、或加密的詳細信息,使用Internet搜索引擎來搜索你感興趣的關鍵字。

5.8.7.2. 需求(OpenSSL)

要想在MySQL服務器和客戶端程序之間使用SSL鏈接,系統必須可以支持OpenSSL。若是用支持內嵌式yaSSL的MySQL版本,不要讀該節,但應閱讀5.8.7.3節,「使用yaSSL」

要想得到安全的MySQL鏈接,必須:

1.    安裝OpenSSL庫。咱們已經測試了帶OpenSSL 0.9.6的MySQL。若是你須要OpenSSL,請訪問http://www.openssl.org

2.    配置MySQL,用--with-vio和--with-openssl選項運行configure腳本。

3.    確保升級了受權表,使mysql.user表內包含SSL相關列。若是 受權表是從MySQL 4.0.0以前的版本升級,這很重要。升級過程見2.10.2節,「升級受權表」

4.    要想檢查是否運行的mysqld服務器支持OpenSSL,應檢查have_openssl系統變量的值:

5.            mysql> SHOW VARIABLES LIKE 'have_openssl';
6.            +---------------+-------+
7.            | Variable_name | Value |
8.            +---------------+-------+
9.            | have_openssl  | YES   |
10.        +---------------+-------+

若是值爲YES,服務器支持OpenSSL鏈接。

5.8.7.3. 使用yaSSL

使用MySQL的內嵌式yaSSL支持,能夠很容易地使用安全鏈接。不須要安裝OpenSSL和執行5.8.7.2節,「需求(OpenSSL)」中的步驟。而且,MySQL和yaSSL使用相同的許可模型。

當前,在如下平臺上支持yaSSL:

·         Linux/x86-64 Red Hat Enterprise 3.0

·         Linux RHAS21 Itanium-2,帶gcc,靜態連接

·         Linux Itanium-2,帶gcc

·         Windows

當從源碼構建MySQL時若是你想要啓用yaSSL,應這樣配置MySQL:

./configure --with-yassl=yes

要想啓動MySQL服務器支持yaSSL,使用支持OpenSSL的相同的選項,並識別創建安全鏈接須要的證書:

shell> mysqld --ssl-ca=cacert.pem \
       --ssl-cert=server-cert.pem \
       --ssl-key=server-key.pem

·         --ssl-ca識別認證機構證書。

·         --ssl-cert識別服務器證書。

·         --ssl-key識別客戶證書。

要想用yaSSL支持創建與MySQL服務器的安全鏈接,應這樣啓動客戶端:

shell> mysql --ssl-ca=cacert.pem \
       --ssl-cert=server-cert.pem \
       --ssl-key=server-key.pem

換句話說,選項與服務器的相同,而且認證機構證書必須相同。

要想從應用程序創建安全鏈接,調用mysql_real_connect()以前,應使用mysql_ssl_set()API函數來設置相應認證選項。參見25.2.3.64節,「mysql_ssl_set()」

5.8.7.4. 爲MySQL設置SSL證書

下面是一個爲MySQ設置SSL證書的例子:
DIR=`pwd`/openssl
PRIV=$DIR/private
 
mkdir $DIR $PRIV $DIR/newcerts
cp /usr/share/ssl/openssl.cnf $DIR
replace ./demoCA $DIR -- $DIR/openssl.cnf
 
# Create necessary files: $database, $serial and $new_certs_dir
# directory (optional)
 
touch $DIR/index.txt
echo "01" > $DIR/serial
 
#
# Generation of Certificate Authority(CA)
#
 
openssl req -new -x509 -keyout $PRIV/cakey.pem -out $DIR/cacert.pem \
    -config $DIR/openssl.cnf
 
# Sample output:
# Using configuration from /home/monty/openssl/openssl.cnf
# Generating a 1024 bit RSA private key
# ................++++++
# .........++++++
# writing new private key to '/home/monty/openssl/private/cakey.pem'
# Enter PEM pass phrase:
# Verifying password - Enter PEM pass phrase:
# -----
# You are about to be asked to enter information that will be
# incorporated into your certificate request.
# What you are about to enter is what is called a Distinguished Name
# or a DN.
# There are quite a few fields but you can leave some blank
# For some fields there will be a default value,
# If you enter '.', the field will be left blank.
# -----
# Country Name (2 letter code) [AU]:FI
# State or Province Name (full name) [Some-State]:.
# Locality Name (eg, city) []:
# Organization Name (eg, company) [Internet Widgits Pty Ltd]:MySQL AB
# Organizational Unit Name (eg, section) []:
# Common Name (eg, YOUR name) []:MySQL admin
# Email Address []:
 
#
# Create server request and key
#
openssl req -new -keyout $DIR/server-key.pem -out \
    $DIR/server-req.pem -days 3600 -config $DIR/openssl.cnf
 
# Sample output:
# Using configuration from /home/monty/openssl/openssl.cnf
# Generating a 1024 bit RSA private key
# ..++++++
# ..........++++++
# writing new private key to '/home/monty/openssl/server-key.pem'
# Enter PEM pass phrase:
# Verifying password - Enter PEM pass phrase:
# -----
# You are about to be asked to enter information that will be
# incorporated into your certificate request.
# What you are about to enter is what is called a Distinguished Name
# or a DN.
# There are quite a few fields but you can leave some blank
# For some fields there will be a default value,
# If you enter '.', the field will be left blank.
# -----
# Country Name (2 letter code) [AU]:FI
# State or Province Name (full name) [Some-State]:.
# Locality Name (eg, city) []:
# Organization Name (eg, company) [Internet Widgits Pty Ltd]:MySQL AB
# Organizational Unit Name (eg, section) []:
# Common Name (eg, YOUR name) []:MySQL server
# Email Address []:
#
# Please enter the following 'extra' attributes
# to be sent with your certificate request
# A challenge password []:
# An optional company name []:
 
#
# Remove the passphrase from the key (optional)
#
 
openssl rsa -in $DIR/server-key.pem -out $DIR/server-key.pem
 
#
# Sign server cert
#
openssl ca  -policy policy_anything -out $DIR/server-cert.pem \
    -config $DIR/openssl.cnf -infiles $DIR/server-req.pem
 
# Sample output:
# Using configuration from /home/monty/openssl/openssl.cnf
# Enter PEM pass phrase:
# Check that the request matches the signature
# Signature ok
# The Subjects Distinguished Name is as follows
# countryName           :PRINTABLE:'FI'
# organizationName      :PRINTABLE:'MySQL AB'
# commonName            :PRINTABLE:'MySQL admin'
# Certificate is to be certified until Sep 13 14:22:46 2003 GMT
# (365 days)
# Sign the certificate? [y/n]:y
#
#
# 1 out of 1 certificate requests certified, commit? [y/n]y
# Write out database with 1 new entries
# Data Base Updated
 
#
# Create client request and key
#
openssl req -new -keyout $DIR/client-key.pem -out \
    $DIR/client-req.pem -days 3600 -config $DIR/openssl.cnf
 
# Sample output:
# Using configuration from /home/monty/openssl/openssl.cnf
# Generating a 1024 bit RSA private key
# .....................................++++++
# .............................................++++++
# writing new private key to '/home/monty/openssl/client-key.pem'
# Enter PEM pass phrase:
# Verifying password - Enter PEM pass phrase:
# -----
# You are about to be asked to enter information that will be
# incorporated into your certificate request.
# What you are about to enter is what is called a Distinguished Name
# or a DN.
# There are quite a few fields but you can leave some blank
# For some fields there will be a default value,
# If you enter '.', the field will be left blank.
# -----
# Country Name (2 letter code) [AU]:FI
# State or Province Name (full name) [Some-State]:.
# Locality Name (eg, city) []:
# Organization Name (eg, company) [Internet Widgits Pty Ltd]:MySQL AB
# Organizational Unit Name (eg, section) []:
# Common Name (eg, YOUR name) []:MySQL user
# Email Address []:
#
# Please enter the following 'extra' attributes
# to be sent with your certificate request
# A challenge password []:
# An optional company name []:
 
#
# Remove a passphrase from the key (optional)
#
openssl rsa -in $DIR/client-key.pem -out $DIR/client-key.pem
 
#
# Sign client cert
#
 
openssl ca  -policy policy_anything -out $DIR/client-cert.pem \
    -config $DIR/openssl.cnf -infiles $DIR/client-req.pem
 
# Sample output:
# Using configuration from /home/monty/openssl/openssl.cnf
# Enter PEM pass phrase:
# Check that the request matches the signature
# Signature ok
# The Subjects Distinguished Name is as follows
# countryName           :PRINTABLE:'FI'
# organizationName      :PRINTABLE:'MySQL AB'
# commonName            :PRINTABLE:'MySQL user'
# Certificate is to be certified until Sep 13 16:45:17 2003 GMT
# (365 days)
# Sign the certificate? [y/n]:y
#
#
# 1 out of 1 certificate requests certified, commit? [y/n]y
# Write out database with 1 new entries
# Data Base Updated
 
#
# Create a my.cnf file that you can use to test the certificates
#
 
cnf=""
cnf="$cnf [client]"
cnf="$cnf ssl-ca=$DIR/cacert.pem"
cnf="$cnf ssl-cert=$DIR/client-cert.pem"
cnf="$cnf ssl-key=$DIR/client-key.pem"
cnf="$cnf [mysqld]"
cnf="$cnf ssl-ca=$DIR/cacert.pem"
cnf="$cnf ssl-cert=$DIR/server-cert.pem"
cnf="$cnf ssl-key=$DIR/server-key.pem"
echo $cnf | replace " " '
' > $DIR/my.cnf

 

要想測試SSL鏈接,按下面方法啓動服務器,其中$DIR是示例my.cnf選項文件安裝的路徑名:

shell> MySQLd --defaults-file=$DIR/my.cnf &

而後使用相同的選項文件調用客戶端程序:

shell> MySQL --defaults-file=$DIR/my.cnf

若是你有MySQL源碼分發版,還能夠修改前面的my.cnf文件來指向SSL目錄中的示範證書和密鑰文件來測試你的設置。

5.8.7.5. SSL GRANT 選項

MySQL能夠檢查X509證書的屬性和基於用戶名和密碼的通用鑑定方法。要想爲MySQL帳戶指定SSL相關選項,使用GRANT語句的REQUIRE子句。參見13.5.1.3節,「GRANT和REVOKE語法」

有多種可能來限制一個帳戶的鏈接類型:

·         若是帳戶沒有SSL或X509需求,若是用戶名和密碼合法,容許未加密的鏈接。可是,若是客戶有正確的證書和密鑰文件,在客戶選項中能夠使用加密鏈接。

·         REQUIRE SSL選項限制服務器只容許該帳戶的SSL加密鏈接。請注意若是有ACL記錄容許非SSL鏈接,該選項會被忽略。

·                  mysql> GRANT ALL PRIVILEGES ON test.* TO 'root'@'localhost'
·                     -> IDENTIFIED BY 'goodsecret' REQUIRE SSL;

·         REQUIRE X509表示客戶必須有合法證書但確切的證書、分發者和主體不重要。惟一的需求是應能夠被某個CA認證機構驗證它的簽名。

·                mysql> GRANT ALL PRIVILEGES ON test.* TO 'root'@'localhost'
·                    -> IDENTIFIED BY 'goodsecret' REQUIRE X509;

·         REQUIRE ISSUER 'issuer'限制鏈接企圖,即客戶必須出示CA 'issuer'簽發的合法X509證書。若是客戶出示了一個合法證書,可是是由不一樣的分發者簽發,服務器拒絕鏈接。使用X509證書表示要加密,所以不須要SSL選項。

·                mysql> GRANT ALL PRIVILEGES ON test.* TO 'root'@'localhost'
·                    -> IDENTIFIED BY 'goodsecret'
·                    -> REQUIRE ISSUER '/C=FI/ST=Some-State/L=Helsinki/
·                       O=MySQL Finland AB/CN=Tonu Samuel/Email=tonu@example.com';

請注意ISSUER值應作爲單一字符串輸入。

·         REQUIRE SUBJECT 'subject' 限制鏈接企圖,即客戶必須出示主題爲'subject'的合法X509證書。若是客戶出示了一個合法證書,可是有不一樣的主題,服務器拒絕鏈接。

·                mysql> GRANT ALL PRIVILEGES ON test.* TO 'root'@'localhost'
·                    -> IDENTIFIED BY 'goodsecret'
·                    -> REQUIRE SUBJECT '/C=EE/ST=Some-State/L=Tallinn/
·                       O=MySQL demo client certificate/
       CN=Tonu Samuel/Email=tonu@example.com';

請注意SUBJECT值應作爲單一字符串輸入。

·         REQUIRE CIPHER 'cipher'用來確保使用足夠強的密碼和密鑰長度。若是使用舊的短加密密鑰算法,SSL自己可能很弱。使用該選項,咱們能夠索取確切的加密方法來鏈接。

·                mysql> GRANT ALL PRIVILEGES ON test.* TO 'root'@'localhost'
·                    -> IDENTIFIED BY 'goodsecret'
    -> REQUIRE CIPHER 'EDH-RSA-DES-CBC3-SHA';

在REQUIRE子句中,能夠結合使用SUBJECT、ISSUER和CIPHER選項:

mysql> GRANT ALL PRIVILEGES ON test.* TO 'root'@'localhost'
    -> IDENTIFIED BY 'goodsecret'
    -> REQUIRE SUBJECT '/C=EE/ST=Some-State/L=Tallinn/
       O=MySQL demo client certificate/
       CN=Tonu Samuel/Email=tonu@example.com'
    -> AND ISSUER '/C=FI/ST=Some-State/L=Helsinki/
       O=MySQL Finland AB/CN=Tonu Samuel/Email=tonu@example.com'
    -> AND CIPHER 'EDH-RSA-DES-CBC3-SHA';

請注意SUBJECT和ISSUER值應作爲單一字符串輸入。

在MySQL 5.1中,在REQUIRE選項之間能夠選用AND關鍵字。

選項的順序不重要,但任何選項不能用兩次。

5.8.7.6. SSL命令行選項

下面列出了規定SSL、證書文件和密鑰文件使用的選項。它們能夠位於命令行中或選項文件中。

·         --ssl

對於服務器,該選項規定該服務器容許SSL鏈接。對於客戶端程序,它容許客戶使用SSL鏈接服務器。單單該選項不足以使用SSL鏈接。還必須指定--ssl-ca、--ssl-cert和--ssl-key選項。

一般從反向使用該選項表示不該使用SSL。要想實現,將選項指定爲--skip-ssl或--ssl=0。

請注意使用--ssl不須要SSL鏈接。例如,若是編譯的服務器或客戶不支持SSL,則使用普通的未加密的鏈接。

確保使用SSL鏈接的安全方式是使用含REQUIRE SSL子句的GRANT語句在服務器上建立一個帳戶。而後使用該帳戶來鏈接服務器,服務器和客戶端均應啓用SSL支持。

·         --ssl-ca=file_name

含可信SSL CA的清單的文件的路徑。

·         --ssl-capath=directory_name

包含pem格式的可信SSL CA證書的目錄的路徑。

·         --ssl-cert=file_name

SSL證書文件名,用於創建安全鏈接。

·         --ssl-cipher=cipher_list

容許的用於SSL加密的密碼的清單。cipher_list的格式與OpenSSL ciphers命令相同。

示例:--ssl-cipher=ALL:-AES:-EXP

·         --ssl-key=file_name

SSL密鑰文件名,用於創建安全鏈接。

5.8.7.7. 用SSH以遠程方式從Windows鏈接到MySQL

本節說明如何用SSH安全鏈接到遠程MySQL服務器(David Carlson < dcarlson@mplcomm。com>):

1.    在Windows主機上安裝SSH客戶端。做爲用戶,我所發現的最好的非免費客戶端來自http://www.vandyke.com/的SecureCRT。另外一個選則是http://www.f-secure.com/的f-secure。你還能夠從http://directory.google.com/Top/Computers/Security/Products_and_Tools/Cryptography/SSH/Clients/Windows/ 的Google找到一些免費客戶端。

2.    啓動Windows SSH客戶端。設置Host_Name = yourmysqlserver_URL_or_IP。設置userid=your_userid以便登陸服務器。此userid值能夠與你的MySQL帳戶的用戶名不相同。

3.    設置端口映射。能夠進行遠程映射(設置local_port: 3306, remote_host: yourmysqlservername_or_ip, remote_port: 3306)或本地映射(設置port: 3306, host: localhost, remote port: 3306)。

4.    進行保存,不然下次須要重設。

5.    剛建立的SSH會話登陸服務器。

6.    在Windows機器上啓動相應ODBC應用程序(例如Access)。

7.    在Windows中建立一個新的文件按照經常使用方法經過ODBC驅動程序連接MySQL,不一樣的是要爲MySQL服務器輸入localhost,而不是yourmysqlservername。

你應有使用SSH加密的ODBC鏈接到MySQL。

5.9. 備份與恢復

本節討論如何進行數據庫備份(徹底備份和增量備份),以及如何執行表的維護。本節描述的SQL語句語法參見第5章:數據庫管理。此處提供的大多數信息主要適合MyISAM表。InnoDB備份程序參見15.2.8節,「InnoDB數據庫的備份和恢復

5.9.1. 數據庫備份

由於MySQL表保存爲文件方式,很容易備份。要想保持備份的一致性,對相關表執行LOCK TABLES操做,而後對錶執行FLUSH TABLES。參見13.4.5節,「LOCK TABLES和UNLOCK TABLES語法」13.5.5.2節,「FLUSH語法」。你只須要讀鎖定;這樣當你複製數據庫目錄中的文件時,容許其它客戶繼續查詢表。須要FLUSH TABLES語句來確保開始備份前將全部激活的索引頁寫入硬盤。

若是你想要進行SQL級別的表備份,你能夠使用SELECT INTO ...OUTFILE或BACKUP TABLE。對於SELECT INTO ...OUTFILE, 輸出的文件不能先存在。對於BACKUP TABLE也如此,由於覆蓋完整的文件會有安全風險。參見13.2.7節,「SELECT語法」13.5.2.2節,「BACKUP TABLE語法」

備份數據庫的另外一個技術是使用mysqldump程序或mysqlhotcopy腳本。參見8.8節,「mysqldump:數據庫備份程序」8.9節,「mysqlhotcopy:數據庫備份程序」

1.    徹底備份數據庫:

2.            shell> mysqldump --tab=/path/to/some/dir --opt db_name

或:

shell> mysqlhotcopy db_name /path/to/some/dir

只要服務器再也不進行更新,還能夠只複製全部表文件(*.frm、*.MYD和*.MYI文件)。mysqlhotcopy腳本使用該方法。(但請注意若是數據庫包含InnoDB表,這些方法不工做。InnoDB不將表的內容保存到數據庫目錄中,mysqlhotcopy只適合MyISAM表)。

3.    若是mysqld在運行則中止,而後用--log-bin[=file_name]選項來啓動。參見5.11.3節,「二進制日誌」。二進制日誌文件中提供了  執行mysqldump以後對數據庫的更改進行復制所須要的信息。

對於InnoDB表,能夠進行在線備份,不須要對錶進行鎖定;參見8.8節,「mysqldump:數據庫備份程序」

MySQL支持增量備份:須要用--log-bin選項來啓動服務器以便啓用二進制日誌;參見5.11.3節,「二進制日誌」。當想要進行增量備份時(包含上一次徹底備份或增量備份以後的全部更改),應使用FLUSH LOGS回滾二進制日誌。而後,你須要將從最後的徹底或增量備份的某個時刻到最後某個點的全部二進制日誌複製到備份位置。這些二進制日誌爲增量備份;恢復時,按照下面的解釋應用。下次進行徹底備份時,還應使用FLUSH LOGS或mysqlhotcopy --flushlogs回滾二進制日誌。參見8.8節,「mysqldump:數據庫備份程序」8.9節,「mysqlhotcopy:數據庫備份程序」

若是MySQL服務器爲從複製服務器,則不管選擇什麼備份方法,當備份從機數據時,還應備份master.info和relay-log.info文件。恢復了從機數據後,須要這些文件來繼續複製。若是從機執行復制LOAD DATA INFILE命令,你應還備份用--slave-load-tmpdir選項指定的目錄中的SQL_LOAD-*文件。(若是未指定,該位置默認爲tmpdir變量值)。從機須要這些文件來繼續複製中斷的LOAD DATA INFILE操做。

若是必須恢復MyISAM表,先使用REPAIR TABLE或myisamchk -r來恢復。99.9%的狀況下該方法能夠工做。若是myisamchk失敗,試試下面的方法。請注意只有用--log-bin選項啓動了MySQL從而啓用二進制日誌它才工做;參見5.11.3節,「二進制日誌」

1.    恢復原mysqldump備份,或二進制備份。

2.    執行下面的命令從新更新二進制日誌:

3.            shell> mysqlbinlog hostname-bin.[0-9]* | mysql

在某些狀況下,你可能只想要從某個位置從新運行某些二進制日誌。(一般你想要從恢復備份的日期從新運行全部二進制日誌,查詢不正確時例外)。關於mysqlbinlog工具和如何使用它的詳細信息參見8.6節,「mysqlbinlog:用於處理二進制日誌文件的實用工具」

還能夠對具體文件進行選擇備份:

·         要想複製表,使用SELECT * INTO OUTFILE 'file_name' FROM tbl_name

·         要想重載表,使用LOAD DATA INFILE 'file_name' REPLACE ...並恢復。要避免複製記錄,表必須有PRIMARY KEY或一個UNIQUE索引。當新記錄複製惟一鍵值的舊記錄時,REPLACE關鍵字能夠將舊記錄替換爲新記錄。

若是備份時遇到服務器性能問題,能夠有幫助的一個策略是在從服務器而不是主服務器上創建複製並執行備份。參見6.1節,「複製介紹」

若是使用Veritas文件系統,能夠這樣備份:

1.    從客戶端程序執行FLUSH TABLES WITH READ LOCK。

2.    從另外一個shell執行mount vxfs snapshot。

3.    從第一個客戶端執行UNLOCK TABLES。

4.    從快照複製文件。

5.    卸載快照。

5.9.2. 示例用備份與恢復策略

本節討論進行備份的程序,在出現崩潰後,能夠恢復數據:

·         操做系統崩潰

·         電源故障

·         文件系統崩潰

·         硬件問題(硬盤、母板等等)

該命令不包括mysqldumpmysql程序的--user和—password等選項。應包括必要的選項讓MySQL服務器容許你鏈接它。

咱們假定數據保存在MySQL的InnoDB存儲引擎中,支持事務和自動崩潰恢復。咱們假定崩潰時MySQL服務器帶負載。若是不帶負載,則不須要恢復。

出現操做系統崩潰或電源故障時,咱們能夠假定重啓後硬盤上的MySQLś數據仍可用。因爲崩潰,InnoDB數據文件中的數據可能再也不保持一致性,但InnoDB讀取它的日誌並會查到掛起的提交的和未提交的事務清單,它們沒有清空到數據文件中。InnoDB自動捲回未提交的事務,並清空到它的數據文件中。經過MySQL錯誤日誌將該恢復過程相關信息傳達給用戶。下面的例子爲日誌摘錄:

InnoDB: Database was not shut down normally.
InnoDB: Starting recovery from log files...
InnoDB: Starting log scan based on checkpoint at
InnoDB: log sequence number 0 13674004
InnoDB: Doing recovery: scanned up to log sequence number 0 13739520
InnoDB: Doing recovery: scanned up to log sequence number 0 13805056
InnoDB: Doing recovery: scanned up to log sequence number 0 13870592
InnoDB: Doing recovery: scanned up to log sequence number 0 13936128
...
InnoDB: Doing recovery: scanned up to log sequence number 0 20555264
InnoDB: Doing recovery: scanned up to log sequence number 0 20620800
InnoDB: Doing recovery: scanned up to log sequence number 0 20664692
InnoDB: 1 uncommitted transaction(s) which must be rolled back
InnoDB: Starting rollback of uncommitted transactions
InnoDB: Rolling back trx no 16745
InnoDB: Rolling back of trx no 16745 completed
InnoDB: Rollback of uncommitted transactions completed
InnoDB: Starting an apply batch of log records to the database...
InnoDB: Apply batch completed
InnoDB: Started
mysqld: ready for connections

若是文件系統崩潰或出現硬件問題,咱們能夠假定重啓後硬盤上的MySQLś數據不可用。這說明MySQL未能成功啓動,由於一些硬盤數據塊再也不可讀。在這種狀況下,須要從新格式化硬盤,安裝一個新的,或糾正問題。而後須要從備份中恢復MySQL數據,這說明咱們必須先作好備份。要想確保,應及時返回並設計備份策略。

5.9.2.1. 備份策略

咱們都知道必須按計劃按期進行備份。能夠用幾個工具徹底備份(在某個時間點的數據快照)MySQL。例如,InnoDB Hot Backup爲InnoDB數據文件提供在線非數據塊物理備份,mysqldump提供在線邏輯備份。這裏使用mysqldump

假定咱們在星期日下午1點進行了備份,此時負荷較低。下面的命令能夠徹底備份全部數據庫中的全部InnoDB表:

shell> mysqldump --single-transaction --all-databases > backup_sunday_1_PM.sql

這是在線非塊備份,不會干擾對錶的讀寫。咱們之前假定咱們的表爲InnoDB表,所以--single-transaction使用一致性地讀,而且保證mysqldump所看見的數據不會更改。(其它客戶端對InnoDB表進行的更改不會被mysqldump進程看見)。若是咱們還有其它類型的表,咱們必須假定在備份過程當中它們不會更改。例如,對於mysql數據庫中的MyISAM表,咱們必須假定在備份過程當中沒有對MySQL帳戶進行管理更改。

mysqldump命令產生的.sql文件包含一系列SQL INSERT語句,能夠用來重載轉儲的表。

須要進行徹底備份,但有時不方便。會產生大的備份文件並須要花時間來生成。從某個角度,徹底備份並不理想,由於每一個成功的徹底備份包括全部數據,甚至自從上一次徹底備份以來沒有更改的部分。完成了初使徹底備份後,進行增量備份會更有效。這樣備份文件要小得多,備份時間也較短。不利之處是,恢復時不能只重載徹底備份來恢復數據。還必需要用增量備份來恢復增量更改。

要想進行增量備份,咱們須要保存增量更改。應使用--log-bin選項啓動MySQL服務器,以便更新數據時將這些更改保存到文件中。該選項啓用二進制日誌,所以服務器寫將每一個更新數據的SQL語句寫入MySQL二進制日誌。讓咱們看看用--log-bin選項啓動的已經運行多日的MySQL服務器的數據目錄。咱們找到如下MySQL二進制日誌文件:

-rw-rw---- 1 guilhem  guilhem   1277324 Nov 10 23:59 gbichot2-bin.000001
-rw-rw---- 1 guilhem  guilhem         4 Nov 10 23:59 gbichot2-bin.000002
-rw-rw---- 1 guilhem  guilhem        79 Nov 11 11:06 gbichot2-bin.000003
-rw-rw---- 1 guilhem  guilhem       508 Nov 11 11:08 gbichot2-bin.000004
-rw-rw---- 1 guilhem  guilhem 220047446 Nov 12 16:47 gbichot2-bin.000005
-rw-rw---- 1 guilhem  guilhem    998412 Nov 14 10:08 gbichot2-bin.000006
-rw-rw---- 1 guilhem  guilhem       361 Nov 14 10:07 gbichot2-bin.index

每次重啓,MySQL服務器用序列中的下一個編號建立一個新的二進制日誌文件。當服務器運行時,你還能夠經過執行FLUSH LOGS SQL語句或mysqladmin flush-logs命令,告訴服務器關閉當前的二進制日誌文件並建立一個新文件。mysqldump也有一個選項來清空日誌。數據目錄中的.index文件包含該目錄下全部MySQL二進制日誌的清單。該文件用於複製。

恢復時MySQL二進制日誌很重要,由於它們是增量備份。若是進行徹底備份時確保清空了日誌,則後面建立的二進制日誌文件包含了備份後的全部數據更改。讓咱們稍稍修改前面的mysqldump命令,讓它在徹底備份時可以清空 MySQL二進制日誌,以便轉儲文件包含包含新的當前的二進制日誌:

shell> mysqldump --single-transaction --flush-logs --master-data=2
           --all-databases > backup_sunday_1_PM.sql

執行該命令後,數據目錄則包含新的二進制日誌文件,gbichot2-bin.000007。結果.sql文件包含下列行:

-- Position to start replication or point-in-time 恢復時y from
-- CHANGE MASTER TO MASTER_LOG_FILE='gbichot2-bin.000007',MASTER_LOG_POS=4;

由於mysqldump命令能夠執行徹底備份,這些行表示兩件事情:

·         .sql文件包含全部寫入gbichot2-bin.000007二進制日誌文件或最新的文件以前的更改。

·         備份後所記錄的全部數據更改不出如今.sql中,但出如今gbichot2-bin.000007二進制日誌文件或最新的文件中。

在星期一下午1點,咱們能夠清空日誌開始新的二進制日誌文件來建立增量備份。例如,執行mysqladmin flush-logs命令建立gbichot2-bin.000008。星期日下午1點的徹底備份和星期一下午1點之間的全部更改成文件gbichot2-bin.000007。該增量備份很重要,所以最好將它複製到安全的地方。(例如,備份到磁帶或DVD上,或複製到另外一臺機器上)。在星期二下午1點,執行另外一個mysqladmin flush-logs命令。星期一下午1點和星期二下午1點之間的全部全部更改成文件gbichot2-bin.000008(也應複製到某個安全的地方)。

MySQL二進制日誌佔據硬盤空間。要想釋放空間,應隨時清空。操做方法是刪掉再也不使用的二進制日誌,例如進行徹底備份時:

shell> mysqldump --single-transaction --flush-logs --master-data=2
           --all-databases --delete-master-logs > backup_sunday_1_PM.sql

釋:若是你的服務器爲複製主服務器,用mysqldump --delete-master-logs刪掉MySQL二進制日誌很危險,由於從服務器可能尚未徹底處理該二進制日誌的內容。

PURGE MASTER LOGS語句的描述中解釋了爲何在刪掉MySQL二進制日誌以前應進行確認。參見13.6.1.1節,「PURGE MASTER LOGS語法」

5.9.2.2. 爲恢復進行備份

如今假設在星期三上午8點出現了災難性崩潰,須要使用備份文件進行恢復。恢復時,咱們首先恢復最後的徹底備份(從星期日下午1點開始)。徹底備份文件是一系列SQL語句,所以恢復它很容易:

shell> mysql < backup_sunday_1_PM.sql

在該點,數據恢復到星期日下午1點的狀態。要想恢復從那時起的更改,咱們必須使用增量備份,也就是,gbichot2-bin.000007和gbichot2-bin.000008二進制日誌文件。根據須要從備份處取過這些文件,而後按下述方式處理:

shell> mysqlbinlog gbichot2-bin.000007 gbichot2-bin.000008 | mysql

咱們如今將數據恢復到星期二下午1點的狀態,可是從該時刻到崩潰之間的數據仍然有丟失。要想恢復,咱們須要MySQL服務器將MySQL二進制日誌保存到安全的位置(RAID disks, SAN, ...),應爲與數據文件的保存位置不一樣的地方,保證這些日誌不在毀壞的硬盤上。(也就是,咱們能夠用--log-bin選項啓動服務器,指定一個其它物理設備上的與數據目錄不一樣的位置。這樣,即便包含該目錄的設備丟失,日誌也不會丟失)。若是咱們執行了這些操做,咱們手頭上會有gbichot2-bin.000009文件,咱們能夠用它來恢復大部分最新的數據更改,而不會丟失到崩潰時的數據。

5.9.2.3. 備份策略摘要

出現操做系統崩潰或電源故障時,InnoDB本身能夠完成全部數據恢復工做。但爲了確保你能夠睡好覺,應聽從下面的指導:

·         必定用--log-bin或甚至--log-bin=log_name選項運行MySQL服務器,其中日誌文件名位於某個安全媒介上,不一樣於數據目錄所在驅動器。若是你有這樣的安全媒介,最好進行硬盤負載均衡(這樣可以提升性能)。

·         按期進行徹底備份,使用mysqldump命令進行在線非塊備份。

·         用FLUSH LOGS或mysqladmin flush-logs清空日誌進行按期增量備份。

5.9.3. 自動恢復

若是MySQL服務器啓用了二進制日誌,你能夠使用mysqlbinlog工具來恢復從指定的時間點開始 (例如,從你最後一次備份)直到如今或另外一個指定的時間點的數據。關於啓用二進制日誌的信息,參見5.11.3節,「二進制日誌」。對於mysqlbinlog的詳細信息,參見8.6節,「mysqlbinlog:用於處理二進制日誌文件的實用工具」

要想從二進制日誌恢復數據,你須要知道當前二進制日誌文件的路徑和文件名。通常能夠從選項文件(即my.cnf or my.ini,取決於你的系統)中找到路徑。若是未包含在選項文件中,當服務器啓動時,能夠在命令行中以選項的形式給出。啓用二進制日誌的選項爲--log-bin。要想肯定當前的二進制日誌文件的文件名,輸入下面的MySQL語句:

SHOW BINLOG EVENTS \G

你還能夠從命令行輸入下面的內容:

mysql --user=root -pmy_pwd -e 'SHOW BINLOG EVENTS \G'

將密碼my_pwd替換爲服務器的root密碼。

5.9.3.1. 指定恢復時間

對於MySQL 4.1.4,能夠在 mysqlbinlog語句中經過--start-date和--stop-date選項指定DATETIME格式的起止時間。舉例說明,假設在今天上午10:00(今天是2005年4月20日),執行SQL語句來刪除一個大表。要想恢復表和數據,你能夠恢復前晚上的備份,並輸入:
mysqlbinlog --stop-date="2005-04-20 9:59:59" /var/log/mysql/bin.123456 \
     | mysql -u root -pmypwd

該命令將恢復截止到在--stop-date選項中以DATETIME格式給出的日期和時間的全部數據。若是你沒有檢測到幾個小時後輸入的錯誤的SQL語句,可能你想要恢復後面發生的活動。根據這些,你能夠用起使日期和時間再次運行mysqlbinlog

mysqlbinlog --start-date="2005-04-20 10:01:00" /var/log/mysql/bin.123456 \
     | mysql -u root -pmypwd \

在該行中,從上午10:01登陸的SQL語句將運行。組合執行前夜的轉儲文件和mysqlbinlog的兩行能夠將全部數據恢復到上午10:00前一秒鐘。你應檢查日誌以確保時間確切。下一節介紹如何實現。

5.9.3.2. 指定恢復位置

也能夠不指定日期和時間,而使用 mysqlbinlog的選項--start-position和--stop-position來指定日誌位置。它們的做用與起止日選項相同,不一樣的是給出了從日誌起的位置號。使用日誌位置是更準確的恢復方法,特別是當因爲破壞性SQL語句同時發生許多事務的時候。要想肯定位置號,能夠運行 mysqlbinlog尋找執行了不指望的事務的時間範圍,但應將結果從新指向文本文件以便進行檢查。操做方法爲:
mysqlbinlog --start-date="2005-04-20 9:55:00" --stop-date="2005-04-20 10:05:00" \
      /var/log/mysql/bin.123456 > /tmp/mysql_restore.sql

該命令將在/tmp目錄建立小的文本文件,將顯示執行了錯誤的SQL語句時的SQL語句。你能夠用文本編輯器打開該文件,尋找你不要想重複的語句。若是二進制日誌中的位置號用於中止和繼續恢復操做,應進行註釋。用log_pos加一個數字來標記位置。使用位置號恢復了之前的備份文件後,你應從命令行輸入下面內容:

mysqlbinlog --stop-position="368312" /var/log/mysql/bin.123456 \
    | mysql -u root -pmypwd 
 
mysqlbinlog --start-position="368315" /var/log/mysql/bin.123456 \
    | mysql -u root -pmypwd \ 

上面的第1行將恢復到中止位置爲止的全部事務。下一行將恢復從給定的起始位置直到二進制日誌結束的全部事務。由於mysqlbinlog的輸出包括每一個SQL語句記錄以前的SET TIMESTAMP語句,恢復的數據和相關MySQL日誌將反應事務執行的原時間。

5.9.4. 表維護和崩潰恢復

後面幾節討論如何使用myisamchk來檢查或維護MyISAM表(對應.MYI和.MYD文件的表)。

你能夠使用myisamchk實用程序來得到有關你的數據庫表的信息或檢查、修復、優化他們。下列小節描述如何調用myisamchk(包括它的選項的描述),如何創建表的維護計劃,以及如何使用myisamchk執行各類功能。

儘管用myisamchk修復表很安全,在修復(或任何能夠大量更改表的維護操做)以前先進行備份也是很好的習慣

影響索引的myisamchk操做會使ULLTEXT索引用full-text參數重建,再也不與MySQL服務器使用的值兼容。要想避免,請閱讀5.9.5.1節,「用於myisamchk的通常選的說明。

在許多狀況下,你會發現使用SQL語句實現MyISAM表的維護比執行myisamchk操做要容易地多:

·         要想檢查或維護MyISAM表,使用CHECK TABLE或REPAIR TABLE。

·         要想優化MyISAM表,使用OPTIMIZE TABLE。

·         要想分析MyISAM表,使用ANALYZE TABLE。

能夠直接這些語句,或使用mysqlcheck客戶端程序,能夠提供命令行接口。

這些語句比myisamchk有利的地方是服務器能夠作任何工做。使用myisamchk,你必須確保服務器在同一時間不使用表。不然,myisamchk和服務器之間會出現不指望的相互干涉。

5.9.5. myisamchk:MyISAM表維護實用工具

能夠使用myisamchk實用程序來得到有關數據庫表的信息或檢查、修復、優化他們。myisamchk適用MyISAM表(對應.MYI和.MYD文件的表)。

調用myisamchk的方法:

shell> myisamchk [options] tbl_name ...

options指定你想讓myisamchk作什麼。在後面描述它們。還能夠經過調用myisamchk --help獲得選項列表。

tbl_name是你想要檢查或修復的數據庫表。若是你不在數據庫目錄的某處運行myisamchk,你必須指定數據庫目錄的路徑,由於myisamchk不知道你的數據庫位於哪兒。實際上,myisamchk不在意你正在操做的文件是否位於一個數據庫目錄;你能夠將對應於數據庫表的文件拷貝到別處而且在那裏執行恢復操做。

若是你願意,能夠用myisamchk命令行命名幾個表。還能夠經過命名索引文件(用「 .MYI」後綴)來指定一個表。它容許你經過使用模式「*.MYI」指定在一個目錄全部的表。例如,若是你在數據庫目錄,能夠這樣在目錄下檢查全部的MyISAM表:

shell> myisamchk *.MYI

若是你不在數據庫目錄下,可經過指定到目錄的路徑檢查全部在那裏的表:

shell> myisamchk /path/to/database_dir/*.MYI

你甚至能夠經過爲MySQL數據目錄的路徑指定一個通配符來檢查全部的數據庫中的全部表:

shell> myisamchk /path/to/datadir/*/*.MYI

推薦的快速檢查全部MyISAM表的方式是:

shell> myisamchk --silent --fast /path/to/datadir/*/*.MYI

若是你想要檢查全部MyISAM表並修復任何破壞的表,能夠使用下面的命令:

shell> myisamchk --silent --force --fast --update-state \
          -O key_buffer=64M -O sort_buffer=64M \
          -O read_buffer=1M -O write_buffer=1M \
          /path/to/datadir/*/*.MYI

該命令假定你有大於64MB的自由內存。關於用myisamchk分配內存的詳細信息,參見5.9.5.5節,「myisamchk內存使用」

當你運行myisamchk時,必須確保其它程序不使用表。不然,當你運行myisamchk時,會顯示下面的錯誤消息:

warning: clients are using or haven't closed the table properly

這說明你正嘗試檢查正被另外一個尚未關閉文件或已經終止而沒有正確地關閉文件的程序(例如mysqld服務器)更新的表。

若是mysqld正在運行,你必須經過FLUSH TABLES強制清空仍然在內存中的任何表修改。當你運行myisamchk時,必須確保其它程序不使用表。避免該問題的最容易的方法是使用CHECK TABLE而不用myisamchk來檢查表。

5.9.5.1. 用於myisamchk的通常選

本節描述的選項能夠用於用myisamchk執行的任何類型的表維護操做。本節後面的章節中描述的選項只適合具體操做,例如檢查或修復表。

·         --help,-?

顯示幫助消息並退出。

·         --debug=debug_options, -# debug_options

輸出調試記錄文件。debug_options字符串常常是'd:t:o,filename'。

·         --silent,-s

沉默模式。僅當發生錯誤時寫輸出。你能使用-s兩次(-ss)使myisamchk沉默。

·         --verbose,-v

冗長模式。打印更多的信息。這能與-d和-e一塊兒使用。爲了更冗長,使用-v屢次(-vv, -vvv)!

·         --version, -V

顯示版本信息並退出。

·         --wait, -w

若是表被鎖定,不是提示錯誤終止,而是在繼續前等待到表被解鎖。請注意若是用--skip-external-locking選項運行mysqld,只能用另外一個myisamchk命令鎖定表。

還能夠經過--var_name=value選項設置下面的變量:

變量

默認值

decode_bits

9

ft_max_word_len

取決於版本

ft_min_word_len

4

ft_stopword_file

內建列表

key_buffer_size

523264

myisam_block_size

1024

read_buffer_size

262136

sort_buffer_size

2097144

sort_key_blocks

16

stats_method

nulls_unequal

write_buffer_size

262136

能夠用myisamchk --help檢查myisamchk變量及其 默認值:

當用排序鍵值修復鍵值時使用sort_buffer_size,使用--recover時這是很普通的狀況。

當用--extend-check檢查表或經過一行一行地將鍵值插入表中(如同普通插入)來修改鍵值時使用Key_buffer_size。在如下狀況經過鍵值緩衝區進行修復:

·         使用--safe-recover。

·         當直接建立鍵值文件時,須要對鍵值排序的臨時文件有兩倍大。一般是當CHAR、VARCHAR、或TEXT列的鍵值較大的狀況,由於排序操做在處理過程當中須要保存所有鍵值。若是你有大量臨時空間,能夠經過排序強制使用myisamchk來修復,能夠使用--sort-recover選項。

經過鍵值緩衝區的修復佔用的硬盤空間比使用排序麼少,可是要慢。

若是想要快速修復,將key_buffer_size和sort_buffer_size變量設置到大約可用內存的25%。能夠將兩個變量設置爲較大的值,由於一個時間只使用一個變量。

myisam_block_size是用於索引塊的內存大小。

stats_method影響當給定--analyze選項時,如何爲索引統計蒐集處理NULL值。它如同myisam_stats_method系統變量。詳細信息參見5.3.3節,「服務器系統變量」7.4.7節,「MyISAM索引統計集合」的myisam_stats_method的描述。

ft_min_word_len和ft_max_word_len表示FULLTEXT索引的最小和最大字長。ft_stopword_file爲中止字文件的文件名。須要在如下環境中對其進行設置。

若是你使用myisamchk來修改表索引(例如修復或分析),使用最小和最大字長和中止字文件的 默認全文參數值(除非你另外指定)重建FULLTEXT索引。這樣會致使查詢失敗。

出現這些問題是由於只有服務器知道這些參數。它們沒有保存在MyISAM索引文件中。若是你修改了服務器中的最小或最大字長或中止字文件,要避免該問題,爲用於mysqldmyisamchk指定相同的ft_min_word_len,ft_max_word_len和ft_stopword_file值。例如,若是你將最小字長設置爲3,能夠這樣使用myisamchk來修復表:

shell> myisamchk --recover --ft_min_word_len=3 tbl_name.MYI

要想確保myisamchk和服務器使用相同的全文參數值,能夠將它們放入選項文件的[mysqld]和[myisamchk]小節:

[mysqld]
ft_min_word_len=3
 
[myisamchk]
ft_min_word_len=3

除了myisamchk,還能夠使用REPAIR TABLE、ANALYZE TABLE、OPTIMIZE TABLE或ALTER TABLE。這些語句由服務器執行,知道要使用的正確的全文參數值。

5.9.5.2. 用於myisamchk的檢查選項

myisamchk支持下面的表檢查操做選項:

·         --check, -c

檢查表的錯誤。若是你不明確指定操做類型選項,這就是默認操做。

·         --check-only-changed, -C

只檢查上次檢查後有變動的表。

·         --extend-check, -e

很是仔細地檢查表。若是表有許多索引將會至關慢。該選項只能用於極端狀況。通常狀況下,能夠使用myisamchkmyisamchk --medium-check來肯定表內是否有錯誤。

若是你使用了--extend-check而且有充分的內存,將key_buffer_size變量設置爲較大的值能夠使修復操做運行得更快。

·         --fast,-F

只檢查沒有正確關閉的表。

·         --force, -f

若是myisamchk發現表內有任何錯誤,則自動進行修復。維護類型與--repair或-r選項指定的相同。

·         --information, -i

打印所檢查表的統計信息。

·         --medium-check, -m

比--extend-check更快速地進行檢查。只能發現99.99%的錯誤,在大多數狀況下就足夠了。

·         --read-only, -T

不要將表標記爲已經檢查。若是你使用myisamchk來檢查正被其它應用程序使用而沒有鎖定的表頗有用,例如當用--skip-external-locking選項運行時運行mysqld

·         --update-state, -U

將信息保存在.MYI文件中,來表示表檢查的時間以及是否表崩潰了。該選項用來充分利用--check-only-changed選項,但若是mysqld服務器正使用表而且正用--skip-external-locking選項運行時不該使用該選項。

5.9.5.3. myisamchk的修復選項

myisamchk支持下面的表修復操做的選項:

·         --backup, -B

將.MYD文件備份爲file_name-time.BAK

·         --character-sets-dir=path

字符集安裝目錄。參見5.10.1節,「數據和排序用字符集」

·         --correct-checksum

糾正表的校驗和信息。

·         --data-file-length=len, -D len

數據文件的最大長度(當重建數據文件且爲「滿」時)。

·         --extend-check,-e

進行修復,試圖從數據文件恢復每一行。通常狀況會發現大量的垃圾行。不要使用該選項,除非你不顧後果。

·         --force, -f

覆蓋舊的中間文件(文件名相似tbl_name.TMD),而不是中斷。

·         --keys-used=val, -k val

對於myisamchk,該選項值爲位值,說明要更新的索引。選項值的每個二進制位對應表的一個索引,其中第一個索引對應位0。選項值0禁用對全部索引的更新,能夠保證快速插入。經過myisamchk -r能夠從新激活被禁用的索引。

·         --no-symlinks, -l

不跟隨符號鏈接。一般myisamchk修復一個符號鏈接所指的表。在MySQL 4.0中該選項不存在,由於從4.0開始的版本在修復過程當中不移除符號連接。

·         --parallel-recover, -p

與-r和-n的用法相同,但使用不一樣的線程並行建立全部鍵。這是alpha代碼。本身承擔風險!

·         --quick,-q

不修改數據文件,快速進行修復。出現複製鍵時,你能夠兩次指定該項以強制myisamchk修改原數據文件。

·         --recover, -r

能夠修復幾乎全部一切問題,除非惟一的鍵不惟一時(對於MyISAM表,這是很是不可能的狀況)。若是你想要恢復表,這是首先要嘗試的選項。若是myisamchk報告表不能用-r恢復,則只能嘗試-o。在不太可能的狀況下-r失敗,數據文件保持無缺)。

若是你有大量內存,你應增長sort_buffer_size的值。

·         --safe-recover, -o

使用一個老的恢復方法讀取,按順序讀取全部行,並根據找到的行更新全部索引樹。這比-r慢些,可是能處理-r不能處理的狀況。該恢復方法使用的硬盤空間比-r少。通常狀況,你應首先用-r維修,若是-r失敗則用-o。

若是你有大量內存,你應增長sort_buffer_size的值。

·         (OBSOLETE) --set-character-set=name

在MySQL 5.1中不使用。參見--set-collation。

·         --set-collation=name

更改用來排序表索引的校對規則。校對規則名的第一部分包含字符集名。

·         --sort-recover, -n

強制myisamchk經過排序來解析鍵值,即便臨時文件將可能很大。

·         --tmpdir=path, -t path

用於保存臨時文件的目錄的路徑。若是未設置,myisamchk使用TMPDIR環境變量的值。tmpdir能夠設置爲一系列目錄路徑,用於成功地以round-robin模式建立臨時文件。在Unix中,目錄名之間的間隔字符爲冒號(‘:’),在Windows、NetWare和OS/2中爲分號 (‘;’)。

·         --unpack,-u

將用myisampack打包的表解包。

5.9.5.4. 用於myisamchk的其它選項

myisamchk支持如下表檢查和修復以外的其它操做的選項:

·         --analyze,-a

分析鍵值的分佈。這經過讓聯結優化器更好地選擇表應該以什麼次序聯結和應該使用哪一個鍵來改進聯結性能。要想獲取分佈相關信息,使用myisamchk --description --verbose tbl_name命令或SHOW KEYS FROM tbl_name語句。

·         --description, -d

打印出關於表的描述性信息。

·         --set-auto-increment[=value], -A[value]

強制從給定值開始的新記錄使用AUTO_INCREMENT編號(或若是已經有AUTO_INCREMENT值大小的記錄,應使用更高值)。若是未指定value,新記錄的AUTO_INCREMENT編號應使用當前表的最大值加上1。

·         --sort-index, -S

以從高到低的順序排序索引樹塊。這將優化搜尋而且將使按鍵值的表掃描更快。

·         --sort-records=N, -R N

根據一個具體索引排序記錄。這使你的數據更局部化而且能夠加快在該鍵上的SELECT和ORDER BY的範圍搜索。(第一次作排序可能很慢!)爲了找出一張表的索引編號,使用SHOW INDEX,它以myisamchk看見他們的相同順序顯示一張表的索引。索引從1開始編號。

若是鍵沒有打包(PACK_KEYS=0),它們的長度相同,所以當myisamchk 排序並移動記錄時,只覆蓋索引中的記錄偏移量。若是鍵已經打包(PACK_KEYS=1),myisamchk必須先解開打包的鍵塊,而後從新建立索引並再次將鍵塊打包。(在這種狀況下,從新建立索引比更新每一個索引的偏移量要快)。

5.9.5.5. myisamchk內存使用

當你運行myisamchk時內存分配重要.MYIsamchk使用的內存大小不能超過用-O選項指定的。若是你想對每個大表使用myisamchk,你必須首先肯定你想使用多少內存。修復時能夠使用的 默認值只有3MB。使用更大的內存,可讓myisamchk工做得更快一些。例如,若是有大於32MB的RAM,能夠使用以下所示選項(除了你能夠指定的其它選項):

shell> myisamchk -O sort=16M -O key=16M -O read=1M -O write=1M ...

對於大多數狀況,使用-O sort=16M應該足夠了。

應記住myisamchk使用TMPDIR中的臨時文件。若是TMPDIR指向內存文件系統,你可能很容易獲得內存溢出的錯誤。若是發生,設定TMPDIR指向有更多空間的文件系統目錄而且重啓myisamchk

修復時myisamchk也須要大量硬盤空間:

·         將數據文件大小擴大一倍(原文件和複製文件)。若是你用--quick修復則不須要該空間;在這種狀況下,只從新建立了索引文件。在文件系統上須要的空間與原數據文件相同!(建立的複製文件位於原文件所在目錄)。

·         代替舊索引文件的新索引文件所佔空間。修復工做一開始,就對舊索引文件進行了刪減,所以你一般會忽略該空間。在文件系統上須要的該空間與原數據文件相同!

·         當使用--recover或---sort-recover(但不使用--safe-recover)時,須要排序緩衝區空間。須要的空間爲:

·                (largest_key + row_pointer_length) * number_of_rows * 2

能夠用myisamchk -dv tbl_name檢查鍵值和row_pointer_length的長度。在臨時目錄分配該空間(用TMPDIR或--tmpdir=path指定)。

若是在修復過程當中出現硬盤空間問題,能夠試試用--safe-recover代替--recover。

5.9.5.6. 將myisamchk用於崩潰恢

若是用--skip-external-locking運行mysqld(在某些系統上爲 默認設置,例如Linux),當mysqld使用某個表時,你不能可靠地使用myisamchk來檢查相同的表。當你運行myisamchk時若是能夠確保沒有人在經過mysqld訪問表,在開始檢查表前,你只須要運行mysqladmin flush-tables。若是你不能保證,則你檢查表時你必須中止mysqld。若是mysqld更新表時運行myisamchk,你可能會得到表被破壞的警告,即便事實並不是如此。

若是不使用--skip-external-locking,能夠隨時使用myisamchk來檢查表。當檢查表時,全部嘗試更新表的客戶端將等待,直到myisamchk準備好能夠繼續。

若是使用myisamchk來修復或優化表,必須確保mysqld服務器沒有在使用該表(若是你正使用--skip-external-locking選項也適用)。若是不關閉mysqld,在運行myisamchk以前至少應執行mysqladmin flush-tables。若是服務器和myisamchk同時訪問表,表可能會被破壞

本節描述如何檢查和處理MySQL數據庫中的數據破壞。若是表常常被破壞,你應盡力找到緣由。參見A.4.2節,「若是MySQL依然崩潰,應做些什麼」

關於MyISAM表怎樣會被破壞的解釋,參見15.1.4節,「MyISAM表方面的問題」

在執行崩潰恢復時,理解在一個數據庫中的每個MyISAM表tbl_name對應的在數據庫目錄中的3個文件是很重要的:

文件

目的

tbl_name.frm

定義(格式)文件

tbl_name.MYD

數據文件

tbl_name.MYI

索引文件

這3類文件的每一類均可能遭受不一樣形式的損壞,可是問題最常發生在數據文件和索引文件。

myisamchk經過一行一行地建立一個「.MYD」數據文件的副原本工做,它經過刪除舊的「.MYD 文件而且重命名新文件到原來的文件名結束脩復階段。若是你使用--quick,myisamchk不建立一個臨時「.MYD」文件,只是假定「.MYD」文件是正確的而且僅建立一個新的索引文件,不接觸「.MYD」文件,這是安全的,由於myisamchk自動檢測「.MYD」文件是否損壞而且在這種狀況下,放棄修復。你也能夠給myisamchk兩個--quick選項。在這種狀況下,myisamchk不會在一些錯誤上(象重複鍵)放棄,相反試圖經過修改「.MYD」文件解決它們。一般,只有在太少的空閒磁盤空間上實施正常修復,使用兩個--quick選項時纔有用。在這種狀況下,你至少應該在運行myisamchk前作進行備份。

5.9.5.7. 如何檢查MyISAM表的錯誤

要想檢查MyISAM表,應使用下面的命令:

·         myisamchk tbl_name

這樣能找出99.99%的錯誤。它不能找出的是僅僅涉及數據文件的損壞(這很不常見)。若是想要檢查一張表,一般應該沒有選項地運行myisamchk或用-s或--silent選項的任何一個。

·         myisamchk -m tbl_name

這樣能找出99.99%的錯誤。它首先檢查全部索引條目的錯誤並通讀全部行。它還計算行內全部鍵值的校驗和,並確認校驗和與索引樹內鍵的校驗和相匹配。

·         myisamchk -e tbl_name

能夠徹底完全地檢查數據(-e意思是「擴展檢查」)。它對每一行作每一個鍵的讀檢查以證明它們確實指向正確的行。這在一個有不少鍵的大表上可能花很長時間。myisamchk一般將在它發現第一個錯誤之後中止。若是你想要得到更多的信息,能夠增長--verbose(-v)選項。這使得myisamchk繼續一直到最多20個錯誤。

·         myisamchk -e -i tbl_name

象前面的命令同樣,可是-i選項告訴myisamchk還打印出一些統計信息。

在通常使用中,一個簡單的myisamchk(沒有除表名之外的參數)就足夠檢查表了。

5.9.5.8. 如何修復表

本節描述如何對MyISAM表使用myisamchk(擴展名.MYI和.MYD)。

你還能夠(而且應該,若是可能)使用CHECK TABLE和REPAIR TABLE語句來檢查和修復MyISAM表。參見13.5.2.3節,「CHECK TABLE語法」13.5.2.6節,「REPAIR TABLE語法」

一張損壞的表的症狀一般是查詢意外中斷而且能看到下述錯誤:

  • tbl_name.frm」被鎖定不能更改。
  • 不能找到文件tbl_name.MYI」(Errcode:nnn)。
  • 文件意外結束。
  • 記錄文件被毀壞。
  • 從表處理器獲得錯誤nnn

要想獲得錯誤相關的詳細信息,你能夠運行perror nnn,其中nnn爲錯誤編號。下面的示例顯示瞭如何使用perror來找到最經常使用錯誤編號(用表的方式指出問題)的含義:

shell> perror 126 127 132 134 135 136 141 144 145
126 = Index file is crashed / Wrong file format
127 = Record-file is crashed
132 = Old database file
134 = Record was already deleted (or record file crashed)
135 = No more room in record file
136 = No more room in index file
141 = Duplicate unique key or constraint on write or update
144 = Table is crashed and last repair failed

145 = Table was marked as crashed and should be repaired

請注意錯誤135(記錄文件中沒有更多的空間)和錯誤136(索引文件中沒有更多的空間)不是能夠經過簡單修復能夠修復的錯誤。在這種狀況下,必須使用ALTER TABLE來增長MAX_ROWS和AVG_ROW_LENGTH表選項值:

ALTER TABLE tbl_name MAX_ROWS=xxx AVG_ROW_LENGTH=yyy;

若是你不知道當前的表的選項值,使用SHOW CREATE TABLE或DESCRIBE來查詢。

對於其它的錯誤,你必須修復表。myisamchk一般能夠檢測和修復大多數問題。

修復過程包括四個階段,此處將進行描述。開始修復前,應進入數據庫目錄並檢查表文件的許可。在Unix中,確保它們對於運行mysqld的用戶可讀(你也應可讀,由於你須要訪問檢查的文件)。若是你須要修改文件,你還必須擁有寫訪問權限。

myisamchk修復表的選項的描述參見5.9.5節,「myisamchk:MyISAM表維護實用工具」的前幾節。

下面幾節列出了上述命令失敗或你想要使用myisamchk提供的擴展特性等狀況的例子。

若是你要經過命令行來修復表,必須首先中止mysqld服務器。請注意當你在遠程服務器上運行mysqladmin shutdown時,mysqladmin返回後,mysqld服務器將仍然運行一下子,直到中止全部查詢並將全部鍵清空到硬盤上。

階段1:檢查你的表

若是你有不少時間,運行myisamchk *.MYImyisamchk -e *.MYI。使用-s(沉默)選項禁止沒必要要的信息。

若是mysqld服務器處於宕機狀態,應使用--update-state選項來告訴myisamchk將表標記爲'檢查過的'。

你必須只修復那些myisamchk報告有錯誤的表。對這樣的表,繼續到階段2。

若是在檢查時,你獲得奇怪的錯誤(例如out of memory錯誤),或若是myisamchk崩潰,到階段3。

階段2:簡單安全的修復

註釋:若是想更快地進行修復,當運行myisamchk時,你應將sort_buffer_size和Key_buffer_size變量的值設置爲可用內存的大約25%。

首先,試試myisamchk -r -q tbl_name(-r -q意味着「快速恢復模式」)。這將試圖不接觸數據文件來修復索引文件。若是數據文件包含它應有的一切內容和指向數據文件內正確地點的刪除鏈接,這應該管用而且表可被修復。開始修復下一張表。不然,執行下列過程:

  1. 在繼續前對數據文件進行備份。
  2. 使用myisamchk -r tbl_name(-r意味着「恢復模式」)。這將從數據文件中刪除不正確的記錄和已被刪除的記錄並重建索引文件。
  3. 若是前面的步驟失敗,使用myisamchk --safe-recover tbl_name。安全恢復模式使用一個老的恢復方法,處理常規恢復模式不行的少數狀況(可是更慢)。

若是在修復時,你獲得奇怪的錯誤(例如out of memory錯誤),或若是myisamchk崩潰,到階段3。

階段3:困難的修復

只有在索引文件的第一個16K塊被破壞,或包含不正確的信息,或若是索引文件丟失,你才應該到這個階段。在這種狀況下,須要建立一個新的索引文件。按以下步驟操作:

  1. 把數據文件移到安全的地方。
  2. 使用表描述文件建立新的(空)數據文件和索引文件:
  3. shell> mysql db_name
  4. mysql> SET AUTOCOMMIT=1;
  5. mysql> TRUNCATE TABLE tbl_name;
  6. mysql> quit

若是你的MySQL版本沒有TRUNCATE TABLE,則使用DELETE FROM tbl_name

  1. 將老的數據文件拷貝到新建立的數據文件之中。(不要只是將老文件移回新文件之中;你要保留一個副本以防某些東西出錯。)

回到階段2。如今myisamchk -r -q應該工做了。(這不該該是一個無限循環)。

你還能夠使用REPAIR TABLE tbl_name USE_FRM,將自動執行整個程序。

階段4:很是困難的修復

只有.frm描述文件也破壞了,你才應該到達這個階段。這應該從未發生過,由於在表被建立之後,描述文件就再也不改變了。

  1. 從一個備份恢復描述文件而後回到階段3。你也能夠恢復索引文件而後回到階段2。對後者,你應該用myisamchk -r啓動。
  2. 若是你沒有進行備份可是確切地知道表是怎樣建立的,在另外一個數據庫中建立表的一個拷貝。刪除新的數據文件,而後從其餘數據庫將描述文件和索引文件移到破壞的數據庫中。這樣提供了新的描述和索引文件,可是讓.MYD數據文件獨自留下來了。回到階段2而且嘗試重建索引文件。

5.9.5.9. 表優化

爲了組合碎片記錄而且消除因爲刪除或更新記錄而浪費的空間,以恢復模式運行myisamchk

shell> myisamchk -r tbl_name

你能夠用SQL的OPTIMIZE TABLE語句使用的相同方式來優化表,OPTIMIZE TABLE能夠修復表並對鍵值進行分析,而且能夠對索引樹進行排序以便更快地查找鍵值。實用程序和服務器之間不可能交互操做,由於當你使用OPTIMIZE TABLE時,服務器作全部的工做。參見13.5.2.5節,「OPTIMIZE TABLE語法」

myisamchk還有不少其它可用來提升表的性能的選項:

·         -S, --sort-index

·         -R index_num, --sort-records=index_num

·         -a, --analyze

關於這些選項的完整的描述,參見5.9.5節,「myisamchk:MyISAM表維護實用工具」

5.9.6. 創建表維護計劃

按期對錶進行檢查而非等到問題出現後再檢查數據庫表是一個好主意。檢查和修復MyISAM表的一個方式是使用CHECK TABLE和REPAIR TABLE語句。參見13.5.2.3節,「CHECK TABLE語法」13.5.2.6節,「REPAIR TABLE語法」

檢查表的另外一個方法是使用myisamchk。爲維護目的,能夠使用myisamchk -s檢查表。-s選項(簡稱--silent)使myisamchk以沉默模式運行,只有當錯誤出現時纔打印消息。

在服務器啓動時檢查表是一個好主意。例如,不管什麼時候機器在更新當中從新啓動了,你一般須要檢查全部可能受影響的表。(即「預期的破壞了的表」)。要想自動檢查MyISAM表,用--myisam-recover選項啓動服務器。

一個更好的測試將是檢查最後修改時間比「.pid」文件新的表。

你還應該在正常系統操做期間按期檢查表。在MySQL AB,咱們運行一個cron任務,每週一次檢查全部重要的表,使用crontab文件中這樣的行:

35 0 * * 0 /path/to/myisamchk --fast --silent /path/to/datadir/*/*.MYI

能夠打印損壞的表的信息,以便咱們在須要時可以檢驗而且修復它們。

多年了咱們尚未發現(的確是真的)都沒有任何意外損壞的表時(因爲除硬件故障外的其它緣由形成損壞的表),每週一次對咱們是足夠了。

咱們建議如今開始,你對全部最後24小時內被更新了的表每晚都執行myisamchk -s,直到你變得象咱們那樣信任MySQL

通常狀況,MySQL表不多須要維護。若是你用動態大小的行更改MyISAM表(含VARCHAR、BLOB或TEXT列的表)或有刪除了許多行的表,你可能想要不時地(每個月一次)整理/組合表的空間。

能夠對有問題的表執行OPTIMIZE TABLE來優化。或者是,若是能夠停一會mysqld服務器,進入數據目錄,當服務器中止時使用該命令:

shell> myisamchk -r -s --sort-index -O sort_buffer_size=16M */*.MYI

5.9.7. 獲取關於表的信息

爲了得到關於一個表的描述或統計,使用下面的命令:

·         myisamchk -d tbl_name

以「描述模式」運行myisamchk,生成表的描述。若是用--skip-external-locking選項啓動MySQL服務器,myisamchk能夠報告運行的表被更新的錯誤。然而,既然在描述模式中myisamchk不更改表,沒有任何破壞數據的風險。

·         myisamchk -d -v tbl_name

爲了生成更多關於myisamchk正在作什麼的信息,加上-v告訴它以冗長模式運行。

·         myisamchk -eis tbl_name

僅顯示錶的最重要的信息。由於必須讀取整個表,該操做很慢。

·         myisamchk -eiv tbl_name

這相似 -eis,只是告訴你正在作什麼。

下面爲這些命令的輸出示例。它們基於含這些數據和索引文件大小的表:

-rw-rw-r--   1 monty    tcx     317235748 Jan 12 17:30 company.MYD
-rw-rw-r--   1 davida   tcx      96482304 Jan 12 18:35 company.MYM

myisamchk -d輸出示例:

MyISAM file:     company.MYI
Record format:   Fixed length
Data records:    1403698  Deleted blocks:         0
Recordlength:    226
 
table description:
Key Start Len Index   Type
1   2     8   unique  double
2   15    10  multip. text packed stripped
3   219   8   multip. double
4   63    10  multip. text packed stripped
5   167   2   multip. unsigned short
6   177   4   multip. unsigned long
7   155   4   multip. text
8   138   4   multip. unsigned long
9   177   4   multip. unsigned long
    193   1           text

myisamchk -d -v 輸出示例:

MyISAM file:         company
Record format:       Fixed length
File-version:        1
Creation time:       1999-10-30 12:12:51
Recover time:        1999-10-31 19:13:01
Status:              checked
Data records:            1403698  Deleted blocks:              0
Datafile parts:          1403698  Deleted data:                0
Datafile pointer (bytes):      3  Keyfile pointer (bytes):     3
Max datafile length:  3791650815  Max keyfile length: 4294967294
Recordlength:                226
 
table description:
Key Start Len Index   Type                  Rec/key     Root Blocksize
1   2     8   unique  double                      1 15845376      1024
2   15    10  multip. text packed stripped        2 25062400      1024
3   219   8   multip. double                     73 40907776      1024
4   63    10  multip. text packed stripped        5 48097280      1024
5   167   2   multip. unsigned short           4840 55200768      1024
6   177   4   multip. unsigned long            1346 65145856      1024
7   155   4   multip. text                     4995 75090944      1024
8   138   4   multip. unsigned long              87 85036032      1024
9   177   4   multip. unsigned long             178 96481280      1024
    193   1           text

myisamchk -eis 輸出示例:

Checking MyISAM file: company
Key:  1:  Keyblocks used:  97%  Packed:    0%  Max levels:  4
Key:  2:  Keyblocks used:  98%  Packed:   50%  Max levels:  4
Key:  3:  Keyblocks used:  97%  Packed:    0%  Max levels:  4
Key:  4:  Keyblocks used:  99%  Packed:   60%  Max levels:  3
Key:  5:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
Key:  6:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
Key:  7:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
Key:  8:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
Key:  9:  Keyblocks used:  98%  Packed:    0%  Max levels:  4
Total:    Keyblocks used:  98%  Packed:   17%
 
Records:          1403698    M.recordlength:     226
Packed:             0%
Recordspace used:     100%   Empty space:          0%
Blocks/Record:   1.00
Record blocks:    1403698    Delete blocks:        0
Recorddata:     317235748    Deleted data:         0
Lost space:             0    Linkdata:             0
 
User time 1626.51, System time 232.36
Maximum resident set size 0, Integral resident set size 0
Non physical pagefaults 0, Physical pagefaults 627, Swaps 0
Blocks in 0 out 0, Messages in 0 out 0, Signals 0
Voluntary context switches 639, Involuntary context switches 28966

myisamchk -eiv 輸出示例:

Checking MyISAM file: company
Data records: 1403698   Deleted blocks:       0
- check file-size
- check delete-chain
block_size 1024:
index  1:
index  2:
index  3:
index  4:
index  5:
index  6:
index  7:
index  8:
index  9:
No recordlinks
- check index reference
- check data record references index: 1
Key:  1:  Keyblocks used:  97%  Packed:    0%  Max levels:  4
- check data record references index: 2
Key:  2:  Keyblocks used:  98%  Packed:   50%  Max levels:  4
- check data record references index: 3
Key:  3:  Keyblocks used:  97%  Packed:    0%  Max levels:  4
- check data record references index: 4
Key:  4:  Keyblocks used:  99%  Packed:   60%  Max levels:  3
- check data record references index: 5
Key:  5:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
- check data record references index: 6
Key:  6:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
- check data record references index: 7
Key:  7:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
- check data record references index: 8
Key:  8:  Keyblocks used:  99%  Packed:    0%  Max levels:  3
- check data record references index: 9
Key:  9:  Keyblocks used:  98%  Packed:    0%  Max levels:  4
Total:    Keyblocks used:   9%  Packed:   17%
 
- check records and index references
[LOTS OF ROW NUMBERS DELETED]
 
Records:         1403698   M.recordlength:   226   Packed:           0%
Recordspace used:    100%  Empty space:        0%  Blocks/Record: 1.00
Record blocks:   1403698   Delete blocks:      0
Recorddata:    317235748   Deleted data:       0
Lost space:            0   Linkdata:           0
 
User time 1639.63, System time 251.61
Maximum resident set size 0, Integral resident set size 0
Non physical pagefaults 0, Physical pagefaults 10580, Swaps 0
Blocks in 4 out 0, Messages in 0 out 0, Signals 0
Voluntary context switches 10604, Involuntary context switches 122798

下面解釋myisamchk產生的信息的類型。「keyfile」是索引文件。「記錄」和「行」是同義詞。

·         MyISAM file

ISAM(索引)文件名。

·         File-version

ISAM格式的版本。當前老是2。

·         Creation time

數據文件建立的時間。

·         Recover time

索引/數據文件上次被重建的時間。

·         Data records

在表中有多少記錄。

·         Deleted blocks

有多少刪除的塊仍然保留着空間。你能夠優化表以使這個空間減到最小。參見第7章:優化

·         Datafile parts

對動態記錄格式,這指出有多少數據塊。對於一個沒有碎片的優化過的表,這與Data records相同。

·         Deleted data

不能回收的刪除數據有多少字節。你能夠優化表以使這個空間減到最小。參見第7章:優化

·         Datafile pointer

數據文件指針的大小,以字節計。它一般是二、三、4或5個字節。大多數表用2個字節管理,可是目前這還不能從MySQL控制。對固定表,這是一個記錄地址。對動態表,這是一個字節地址。

·         Keyfile pointer

索引文件指針的大小,以字節計。它一般是一、2或3個字節。大多數表用 2 個字節管理,可是它自動由MySQL計算。它老是一個塊地址。

·         Max datafile length

表的數據文件(.MYD文件)可以有多長,以字節計。

·         Max keyfile length

表的鍵值文件(.MYI文件)可以有多長,以字節計。

·           Recordlength

每一個記錄佔多少空間,以字節計。

·         Record format

用於存儲錶行的格式。上面的例子使用Fixed length。其餘可能的值是Compressed和Packed。

·         table description

在表中全部鍵值的列表。對每一個鍵,給出一些底層的信息:

o        Key

該鍵的編號。

o        Start

該索引部分從記錄的哪裏開始。

o        Len

該索引部分是多長。對於緊湊的數字,這應該老是列的全長。對字符串,它能夠比索引的列的全長短些,由於你可能會索引到字符串列的前綴。

o        Index

unique或multip(multiple)。代表一個值是否能在該索引中存在屢次。

o        Type

該索引部分有什麼數據類型。這是一個packed、stripped或empty選項的ISAM數據類型。

o        Root

根索引塊的地址。

o        Blocksize

每一個索引塊的大小。默認是1024,可是從源碼構建MySQL時,該值能夠在編譯時改變。

o        Rec/key

這是由優化器使用的統計值。它告訴對該鍵的每一個值有多少條記錄。惟一鍵老是有一個1值。在一個表被裝載後(或變動很大),能夠用myisamchk -a更新。若是根本沒被更新,給定一個30的默認值。

在上面例子的表中,第9個鍵有兩個table description行。者說明它是有2個部分的多部鍵。

·         Keyblocks used

鍵塊使用的百分比是什麼。當在例子中使用的表剛剛用myisamchk從新組織時,該值很是高(很接近理論上的最大值)。

·         Packed

MySQL試圖用一個通用後綴壓縮鍵。這隻能被用於CHAR/VARCHAR/DECIMAL列的鍵。對於左部分相似的長字符串,能顯著地減小使用空間。在上面的第3個例子中,第4個鍵是10個字符長,能夠減小60%的空間。

·         Max levels

對於該鍵的B樹有多深。有長鍵的大表有較高的值。

·         Records

表中有多少行。

·         M.recordlength

平均記錄長度。對於有定長記錄的表,這是準確的記錄長度,由於全部記錄的長度相同。

·         Packed

MySQL從字符串的結尾去掉空格。Packed值代表這樣作達到的節約的百分比。

·         Recordspace used

數據文件被使用的百分比。

·         Empty space

數據文件未被使用的百分比。

·         Blocks/Record

每一個記錄的平均塊數(即,一個碎片記錄由多少個鏈接組成)。對固定格式表,這老是1。該值應該儘量保持接近1.0。若是它變得太大,你能夠從新組織表。參見第7章:優化

·         Recordblocks

多少塊(連接)被使用。對固定格式,它與記錄的個數相同。

·         Deleteblocks

多少塊(連接)被刪除。

·         Recorddata

在數據文件中使用了多少字節。

·         Deleted data

在數據文件中多少字節被刪除(未使用)。

·         Lost space

若是一個記錄被更新爲更短的長度,就損失了一些空間。這是全部這樣的損失之和,以字節計。

·         Linkdata

當使用動態表格式,記錄碎片用指針鏈接(每一個4 ~ 7字節)。 Linkdata指這樣的指針使用的內存量之和。

若是一張表已經用myisampack壓縮了,myisamchk -d打印每一個表列的附加信息。對於它的一個例子及其含義的描述,參見8.2節,「myisampack:生成壓縮、只讀MyISAM表」

5.10. MySQL本地化和國際應用

本節描述如何配置服務器來使用不一樣的字符集。還討論如何設置服務器的時區並啓用各個鏈接的時區支持。

5.10.1. 數據和排序用字符集

默認狀況下,MySQL使用cp1252(Latin1)字符集根據Swedish/Finnish規則進行排序。這些 默認值適合美國和西歐大部分國家。

全部MySQL二進制分發版用--with-extra-charsets=complex編譯而成。能夠在全部標準程序中添加代碼,使它們能夠處理latin1和全部多字節二進制字符集。其它字符集根據須要從字符集定義文件載入。

字符集肯定在名稱中使用什麼字符。它還肯定如何用SELECT語句的ORDER BY和GROUP BY子句對字符串進行排序。

還能夠在啓動服務器時用--default-character-set選項更改字符集。字符集能夠用--with-charset=charset和--with-extra-charsets=list-of-charsets | complex | all | none選項來configure,字符集配置文件列於SHAREDIR/charsets/Index。參見2.8.2節,「典型配置選項」

還能夠在你啓動服務器時用--default-collation選項更改字符集 校對規則。校對規則必須是默認字符集的合法校對規則。(使用SHOW COLLATION語句來肯定每一個字符集使用哪一個校對規則)。 參見2.8.2節,「典型配置選項」

若是在運行MySQL時更改字符集,還會更改排序順序。結果是你必須對全部表運行myisamchk -r -q --set-character-set=charset ,或正確地對索引進行排序。

當客戶端鏈接MySQL服務器時,服務器告訴客戶端服務器的默認字符集是什麼。客戶端切換到該字符集進行鏈接。

當轉義SQL查詢的字符串時,你應使用mysql_real_escape_string()。mysql_real_escape_string()等價於舊的mysql_escape_string()函數,不一樣的是它使用MYSQL鏈接句柄做爲第一個參數,以便轉義字符時能夠使用相應的字符集。

若是客戶端的編譯路徑不是服務器的安裝目錄,而且配置MySQL時沒有包括MySQL二進制中的全部字符集,若是服務器運行時須要使用客戶端設置的字符集以外的其它字符集,你必須告訴客戶端從哪裏找到更多的字符集。

能夠指定--character-sets-dir選項來表示動態MySQL字符集所保存目錄的路徑。例如,能夠將下面的行放入選項文件中:

[client]
character-sets-dir=/usr/local/mysql/share/mysql/charsets

你能夠強制客戶端使用專用字符集:

[client]
default-character-set=charset

可是通常狀況不須要。

5.10.1.1. 使用德國字符集

在MySQL 5.1中,分別指定字符集和 校對規則。這說明若是你想使用German排序順序,你應選擇latin1 字符集和latin1_german1_ci或latin1_german2_ci校對規則。例如,要用latin1_german1_ci校對規則啓動服務器,應使用--character-set-server=latin1和--collation-server=latin1_german1_ci選項。

關於這兩種校對規則的不一樣之處,參見10.10.2節,「西歐字符集」

5.10.2. 設置錯誤消息語言

默認狀況下, mysqld用英語給出錯誤消息,但也能夠用如下語言顯示:Czech、Danish、Dutch、Estonian、French、German、Greek、Hungarian、Italian、Japanese、Korean、Norwegian、Norwegian-ny、Polish、Portuguese、Romanian、Russian、Slovak、Spanish或 Swedish。

要想在啓動mysqld後用具體語言顯示錯誤消息,使用--language或-L選項。選項值能夠爲語言名稱或錯誤消息文件的全路徑。例如:

shell> mysqld --language=swedish

或:

shell> mysqld --language=/usr/local/share/swedish

語言名應爲小寫。

語言文件位於(默認狀況下)MySQL基本目錄的share/LANGUAGE目錄下。

要想更改錯誤消息文件,應編輯errmsg.txt文件,而後執行下面的命令以生成errmsg.sys文件:

shell> comp_err errmsg.txt errmsg.sys

若是你升級到新版本的MySQL,記住使用新的errmsg.txt文件來從新更改。

5.10.3. 添加新的字符集

本節討論在MySQL中添加新字符集的程序。你必須有一個MySQL源碼分發版。

要選擇正確的程序,先肯定字符集是簡單字符集仍是複雜字符集:

·         若是字符集不須要使用特殊字符串校對規則程序進行排序,而且不須要多字節字符支持,則爲簡單字符集。

·         若是須要上述某個特性,則爲複雜字符集。

例如,latin1和danish爲簡單字符集,而big5和czech爲複雜字符集。

在下面的程序中,字符集名用MYSET表示。

對於簡單字符集,應:

1.    在sql/share/charsets/Index文件最後添加MYSET。並指定惟一的編號。

2.    建立文件sql/share/charsets/MYSET.conf。(你能夠使用sql/share/charsets/latin1.conf的備份文件做爲該文件的基礎)。

文件的語法很簡單:

·         註釋從‘#’字符開始,一直到該行末尾。

·         各字之間用任意數量的空格間隔開。

·         定義字符集時,每一個字必須爲十六進制格式的數字。

·         ctype數組佔據前257個字。to_lower[]、to_upper[]和sort_order[]數組依次佔據256個字。

參見5.10.4節,「字符定義數組」

3.    將字符集名添加到configurE.in的CHARSETS_AVAILABLE和COMPILED_CHARSETS列。

4.    從新配置、編譯並測試。

對於複雜字符集,應:

1.    在MySQL源碼分發版中建立文件strings/ctype-MYSET.c。

2.    在sql/share/charsets/Index文件最後添加MYSET。並指定惟一的編號。

3.    看看已有的ctype-*.c文件(例如strings/ctype-big5.c),看看須要定義什麼。請注意文件中的數組名必須爲ctype_MYSET、to_lower_MYSET等等。對應簡單字符集的數組。參見5.10.4節,「字符定義數組」

4.    在文件頂部,添加註釋:

5.            /*
6.            * This comment is parsed by configure to create ctype.c,
7.            * so don't change it unless you know what you are doing.
8.            *
9.            * .configure. number_MYSET=MYNUMBER
10.        * .configure. strxfrm_multiply_MYSET=N
11.        * .configure. mbmaxlen_MYSET=N
12.        */

configure程序使用該註釋自動將字符集包括進MySQL庫中。

在下面章節中解釋strxfrm_multiply和mbmaxlen 行。只有須要字符串比較函數或多字節字符集函數時,才須要單獨將它們包括進來。

13.而後你應建立下面的函數:

    • my_strncoll_MYSET()
    • my_strcoll_MYSET()
    • my_strxfrm_MYSET()
    • my_like_range_MYSET()

參見5.10.5節,「字符串比較支持」

14.將字符集名添加到configurE.in的CHARSETS_AVAILABLE和COMPILED_CHARSETS列。

15.從新配置、編譯並測試。

sql/share/charsets/README文件中包括詳細的說明。

若是你想要MySQL分發中的字符集,請向MySQL內部郵件系統發郵件。參見1.7.1.1節,「The MySQL郵件列表」

5.10.4. 字符定義數組

to_lower[]和to_upper[]是簡單數組,含有小寫和大寫字符,對應字符集的每一個成員。例如:

to_lower['A'] should contain 'a'
to_upper['a'] should contain 'A'

sort_order[]是一個映射,表示如何排列字符的順序,以便進行比較和排序。一般(但非對於全部字符集)與to_upper[]相同,說明排序對大小寫敏感。MySQL排序字符基於sort_order[]元素的值。對於更加複雜的排序規則,參見5.10.5節,「字符串比較支持」的字符串 校對規則討論。

ctype[]是一個位數組,每一個字符爲一個元素。(請注意字符值索引to_lower[]、to_upper[]和sort_order[],但用字符值+ 1索引ctype[]。這是傳統的轉換方法,可以處理EOF)。

m_ctype.h中有下面的位掩碼定義:

#define _U      01      /* Uppercase */
#define _L      02      /* Lowercase */
#define _N      04      /* Numeral (digit) */
#define _S      010     /* Spacing character */
#define _P      020     /* Punctuation */
#define _C      040     /* Control character */
#define _B      0100    /* Blank */
#define _X      0200    /* heXadecimal digit */

每一個字符的ctype[]條目應爲相應的描述字符的位掩碼值的聯合。例如,'A'是大寫字符(_U)以及十六進制整數(_X),所以ctype['A'+1]應包含 值:

_U + _X = 01 + 0200 = 0201

5.10.5. 字符串比較支持

若是語言的排序規則比較複雜,不能用簡單sort_order[]表來處理,須要使用字符串比較函數。

最好的文檔是已有字符集。以big五、czech、gbk、sjis和tis160字符集做爲例子。

你必須在文件頂部的特殊註釋處指定strxfrm_multiply_MYSET=N值。N應設置爲字符串在my_strxfrm_MYSET過程當中可能增加的最大比例(必須爲正整數)。

5.10.6. 多字節字符支持

若是你想要添加包括多字節字符的新字符集支持,須要使用多字節字符函數。

最好的文檔是已有字符集。以euc_kr、gb2312,gbk、sjis和ujis字符集做爲例子。這些字符集位於strings目錄的ctype-charset.c文件中。

必須在文件頂部的特殊註釋處指定mbmaxlen_MYSET=N值。N應設置爲字符集內最長字符的字節數。

5.10.7. 字符集問題

若是你想要使用沒有編譯爲二進制的字符集,可能會遇到下面的問題:

·         你的程序的字符集保存路徑不正確。(默認爲/usr/local/mysql/share/mysql/charsets)。能夠在運行有問題的程序時經過--character-sets-dir選項來修復。

·         字符集爲多字節字符集,不能動態載入。在這種狀況下,你必須從新編譯程序,以支持字符集。

·         字符集爲動態字符集,但你沒有對應的配置文件。在這種狀況下,你應重新MySQL分發安裝該字符集的配置文件。

·         若是Index文件沒有包含字符集名,程序將顯示下面的錯誤消息:

·                ERROR 1105: File '/usr/local/share/mysql/charsets/?.conf'
·                not found (Errcode:2)

在這種狀況下,你應得到新Index文件或在當前文件中手動添加字符集。

對於MyISAM表,能夠用myisamchk -dvv tbl_name檢查表的字符集名和編號。

5.10.8. MySQL服務器時區支持

 MySQL服務器有幾個時區設置:

·         系統時區。服務器啓動時便試圖肯定主機的時區,用它來設置system_time_zone系統變量。

·         服務器當前的時區。全局系統變量time_zone表示服務器當前使用的時區。初使值爲'SYSTEM',說明服務器時區與系統時區相同。能夠用--default-time-zone=timez選項顯式指定初使值。若是你有SUPER 權限,能夠用下面的語句在運行時設置全局變量值:

·                mysql> SET GLOBAL time_zone = timezone;

·         每一個鏈接的時區。每一個客戶端鏈接有本身的時區設置,用會話time_zone變量給出。其初使值與全局變量time_zone相同,但能夠用下面的語句重設:

·                mysql> SET time_zone = timezone;

能夠用下面的方法查詢當前的全局變量值和每一個鏈接的時區:

mysql> SELECT @@global.time_zone, @@session.time_zone;

timezone值爲字符串,表示UTC的偏移量,例如'+10:00'或'-6:00'。若是已經建立並裝入mysql數據庫中的時區相關表,你還能夠使用命名的時區,例如'Europe/Helsinki'、'US/Eastern'或'MET'。值'SYSTEM'說明該時區應與系統時區相同。時區名對大小寫不敏感。

MySQL安裝程序在mysql數據庫中建立時區表,但不裝載。你必須手動裝載。(若是你正從之前的版本升級到MySQL 4.1.3或更新版本,你應經過升級mysql數據庫來建立表。參見2.10.2節,「升級受權表」中的說明)。

若是你的系統有本身的時區信息數據庫(描述時區的一系列文件),應使用mysql_tzinfo_to_sql程序來填充時區表。示例系統如Linux、FreeBSD、Sun Solaris和Mac OS X。這些文件的可能位置爲/usr/share/zoneinfo目錄。若是你的系統沒有時區信息數據庫,能夠使用本節後面描述的下載的軟件包。

mysql_tzinfo_to_sql程序用來裝載時區表。在命令行中,將時區信息目錄路徑名傳遞到mysql_tzinfo_to_sql並輸出發送到mysql程序。例如:

shell> mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root mysql

mysql_tzinfo_to_sql讀取系統時區文件並生成SQL語句。mysql處理這些語句並裝載時區表。

mysql_tzinfo_to_sql還能夠用來裝載單個時區文件,並生成閏秒信息。

要想裝載對應時區tz_name的單個時區文件tz_file,應這樣調用mysql_tzinfo_to_sql

shell> mysql_tzinfo_to_sql tz_file tz_name | mysql -u root mysql

若是你的時區須要計算閏秒,按下面方法初使化閏秒信息,其中tz_file是時區文件名:

shell> mysql_tzinfo_to_sql --leap tz_file | mysql -u root mysql

若是你的系統沒有時區信息數據庫 (例如,Windows或HP-UX),你能夠從http://dev.mysql.com/downloads/timezones.html下載預構建時區表軟件包。該軟件包包含MyISAM時區表所用的.frm、.MYD和.MYI文件。這些表應屬於mysql數據庫,所以應將這些文件放到MySQL服務器數據目錄的mysql子目錄。操做時應關閉服務器。

警告!若是你的系統有時區信息數據庫,請不要使用下載的軟件包。而應使用mysql_tzinfo_to_sql實用工具!不然,MySQL和系統上其它應用程序處理日期時間的方法會有所不一樣。

關於在複製時時區設置相關請查閱6.7節,「複製特性和已知問題」

5.11. MySQL日誌文件

MySQL有幾個不一樣的日誌文件,能夠幫助你找出mysqld內部發生的事情:

日誌文件

記入文件中的信息類型

錯誤日誌

記錄啓動、運行或中止mysqld時出現的問題。

查詢日誌

記錄創建的客戶端鏈接和執行的語句。

更新日誌

記錄更改數據的語句。不同意使用該日誌。

二進制日誌

記錄全部更改數據的語句。還用於複製。

慢日誌

記錄全部執行時間超過long_query_time秒的全部查詢或不使用索引的查詢。

默認狀況下,全部日誌建立於mysqld數據目錄中。經過刷新日誌,你能夠強制 mysqld來關閉和從新打開日誌文件(或者在某些狀況下切換到一個新的日誌)。當你執行一個FLUSH LOGS語句或執行mysqladmin flush-logsmysqladmin refresh時,出現日誌刷新。參見13.5.5.2節,「FLUSH語法」

若是你正使用MySQL複製功能,從複製服務器將維護更多日誌文件,被稱爲接替日誌。相關討論參見第6章:MySQL中的複製

5.11.1. 錯誤日誌

錯誤日誌文件包含了當mysqld啓動和中止時,以及服務器在運行過程當中發生任何嚴重錯誤時的相關信息。

若是mysqld莫名其妙地死掉而且mysqld_safe須要從新啓動它,mysqld_safe在錯誤日誌中寫入一條restarted mysqld消息。若是mysqld注意到須要自動檢查或着修復一個表,則錯誤日誌中寫入一條消息。

在一些操做系統中,若是mysqld死掉,錯誤日誌包含堆棧跟蹤信息。跟蹤信息能夠用來肯定mysqld死掉的地方。參見E.1.4節,「使用堆棧跟蹤」

能夠用--log-error[=file_name]選項來指定mysqld保存錯誤日誌文件的位置。若是沒有給定file_name值,mysqld使用錯誤日誌名host_name.err 並在數據目錄中寫入日誌文件。若是你執行FLUSH LOGS,錯誤日誌用-old從新命名後綴而且mysqld建立一個新的空日誌文件。(若是未給出--log-error選項,則不會從新命名)。

若是不指定--log-error,或者(在Windows中)若是你使用--console選項,錯誤被寫入標準錯誤輸出stderr。一般標準輸出爲你的終端。

在Windows中,若是未給出--console選項,錯誤輸出老是寫入.err文件。

5.11.2. 通用查詢日誌

若是你想要知道 mysqld內部發生了什麼,你應該用--log[= file_name]或-l [ file_name]選項啓動它。若是沒有給定 file_name的值, 默認名是 host_name.log 全部鏈接和語句被記錄到日誌文件。當你懷疑在客戶端發生了錯誤並想確切地知道該客戶端發送給 mysqld的語句時,該日誌可能很是有用

mysqld按照它接收的順序記錄語句到查詢日誌。這可能與執行的順序不一樣。這與更新日誌和二進制日誌不一樣,它們在查詢執行後,可是任何一個鎖釋放以前記錄日誌。(查詢日誌還包含全部語句,而二進制日誌不包含只查詢數據的語句)。

服務器從新啓動和日誌刷新不會產生新的通常查詢日誌文件(儘管刷新關閉並從新打開通常查詢日誌文件)。在Unix中,你能夠經過下面的命令從新命名文件並建立一個新文件:

shell> mv hostname.log hostname-old.log
shell> mysqladmin flush-logs
shell> cp hostname-old.log to-backup-directory
shell> rm hostname-old.log

在Windows中,服務器打開日誌文件期間你不能從新命名日誌文件。你必須先中止服務器而後從新命名日誌文件。而後,重啓服務器來建立新的日誌文件。

5.11.3. 二進制日誌

二進制日誌以一種更有效的格式,而且是事務安全的方式包含更新日誌中可用的全部信息。

二進制日誌包含了全部更新了數據或者已經潛在更新了數據(例如,沒有匹配任何行的一個DELETE)的全部語句。語句以「事件」的形式保存,它描述數據更改。

釋:二進制日誌已經代替了老的更新日誌,更新日誌在MySQL 5.1中再也不使用。

二進制日誌還包含關於每一個更新數據庫的語句的執行時間信息。它不包含沒有修改任何數據的語句。若是你想要記錄全部語句(例如,爲了識別有問題的查詢),你應使用通常查詢日誌。參見5.11.2節,「通用查詢日誌」

二進制日誌的主要目的是在恢復使可以最大可能地更新數據庫,由於二進制日誌包含備份後進行的全部更新。

二進制日誌還用於在主複製服務器上記錄全部將發送給從服務器的語句。參見第6章:MySQL中的複製

運行服務器時若啓用二進制日誌則性能大約慢1%。可是,二進制日誌的好處,即用於恢復並容許設置複製超過了這個小小的性能損失。

當用--log-bin[=file_name]選項啓動時,mysqld寫入包含全部更新數據的SQL命令的日誌文件。若是未給出file_name值, 默認名爲-bin後面所跟的主機名。若是給出了文件名,但沒有包含路徑,則文件被寫入數據目錄。建議指定一個文件名,緣由參見A.8.1節,「MySQL中的打開事宜」

若是你在日誌名中提供了擴展名(例如,--log-bin=file_name.extension),則擴展名被悄悄除掉並忽略。

mysqld在每一個二進制日誌名後面添加一個數字擴展名。每次你啓動服務器或刷新日誌時該數字則增長。若是當前的日誌大小達到max_binlog_size,還會自動建立新的二進制日誌。若是你正使用大的事務,二進制日誌還會超過max_binlog_size:事務全寫入一個二進制日誌中,絕對不要寫入不一樣的二進制日誌中。

爲了可以知道還使用了哪一個不一樣的二進制日誌文件,mysqld還建立一個二進制日誌索引文件,包含全部使用的二進制日誌文件的文件名。默認狀況下與二進制日誌文件的文件名相同,擴展名爲'.index'。你能夠用--log-bin-index[=file_name]選項更改二進制日誌索引文件的文件名。當mysqld在運行時,不該手動編輯該文件;若是這樣作將會使mysqld變得混亂。

能夠用RESET MASTER語句刪除全部二進制日誌文件,或用PURGE MASTER LOGS只刪除部分二進制文件。參見13.5.5.5節,「RESET語法」13.6.1節,「用於控制主服務器的SQL語句」

二進制日誌格式有一些已知限制,會影響從備份恢復。參見6.7節,「複製特性和已知問題」

保存程序和觸發器的二進制日誌的描述參見20.4節,「存儲子程序和觸發程序的二進制日誌功能」

能夠使用下面的mysqld選項來影響記錄到二進制日誌知的內容。又見選項後面的討論。

·         --binlog-do-db=db_name

告訴主服務器,若是當前的數據庫(即USE選定的數據庫)是db_name,應將更新記錄到二進制日誌中。其它全部沒有明顯指定的數據庫  被忽略。若是使用該選項,你應確保只對當前的數據庫進行更新。

對於CREATE DATABASE、ALTER DATABASE和DROP DATABASE語句,有一個例外,即經過操做的數據庫來決定是否應記錄語句,而不是用當前的數據庫。

一個不能按照指望執行的例子:若是用binlog-do-db=sales啓動服務器,而且執行USE prices; UPDATE sales.january SET amount=amount+1000;,該語句不寫入二進制日誌。

·         --binlog-ignore-db=db_name

告訴主服務器,若是當前的數據庫(即USE選定的數據庫)是db_name,不該將更新保存到二進制日誌中。若是你使用該選項,你應確保只對當前的數據庫進行更新。

一個不能按照你指望的執行的例子:若是服務器用binlog-ignore-db=sales啓動,而且執行USE prices; UPDATE sales.january SET amount=amount+1000;,該語句不寫入二進制日誌。

相似於--binlog-do-db,對於CREATE DATABASE、ALTER DATABASE和DROP DATABASE語句,有一個例外,即經過操做的數據庫來決定是否應記錄語句,而不是用當前的數據庫。

要想記錄或忽視多個數據庫,使用多個選項,爲每一個數據庫指定相應的選項。

服務器根據下面的規則對選項進行評估,以便將更新記錄到二進制日誌中或忽視。請注意對於CREATE/ALTER/DROP DATABASE語句有一個例外。在這些狀況下,根據如下規則,所建立、修改或刪除的數據庫將代替當前的數據庫。

1.    是否有binlog-do-db或binlog-ignore-db規則?

·         沒有:將語句寫入二進制日誌並退出。

·         有:執行下一步。

2.    有一些規則(binlog-do-db或binlog-ignore-db或兩者都有)。當前有一個數據庫(USE是否選擇了數據庫?)?

·         沒有:不要寫入語句,並退出。

·         有:執行下一步。

3.    有當前的數據庫。是否有binlog-do-db規則?

·         有:當前的數據庫是否匹配binlog-do-db規則?

o        有:寫入語句並退出。

o        沒有:不要寫入語句,退出。

·         No:執行下一步。

4.    有一些binlog-ignore-db規則。當前的數據庫是否匹配binlog-ignore-db規則?

·         有:不要寫入語句,並退出。

·         沒有:寫入查詢並退出。

例如,只用binlog-do-db=sales運行的服務器不將當前數據庫不爲sales的語句寫入二進制日誌(換句話說,binlog-do-db有時能夠表示「忽視其它數據庫」)。

若是你正進行復制,應確保沒有從服務器在使用舊的二進制日誌文件,方可刪除它們。一種方法是天天一次執行mysqladmin flush-logs並刪除三天前的全部日誌。能夠手動刪除,或最好使用PURGE MASTER LOGS(參見13.6.1節,「用於控制主服務器的SQL語句」),該語句還會安全地更新二進制日誌索引文件(能夠採用日期參數)。

具備SUPER權限的客戶端能夠經過SET SQL_LOG_BIN=0語句禁止將本身的語句記入二進制記錄。參見13.5.3節,「SET語法」

你能夠用mysqlbinlog實用工具檢查二進制日誌文件。若是你想要從新處理日誌止的語句,這頗有用。例如,能夠從二進制日誌更新MySQL服務器,方法以下:

shell> mysqlbinlog log-file | mysql -h server_name

關於mysqlbinlog實用工具的詳細信息以及如何使用它,參見8.6節,「mysqlbinlog:用於處理二進制日誌文件的實用工具」

若是你正使用事務,必須使用MySQL二進制日誌進行備份,而不能使用舊的更新日誌。

查詢結束後、鎖定被釋放前或提交完成後則當即記入二進制日誌。這樣能夠確保按執行順序記入日誌。

對非事務表的更新執行完畢後當即保存到二進制日誌中。對於事務表,例如BDB或InnoDB表,全部更改表的更新(UPDATE、DELETE或INSERT) 被緩存起來,直到服務器接收到COMMIT語句。在該點,執行完COMMIT以前,mysqld將整個事務寫入二進制日誌。當處理事務的線程啓動時,它爲緩衝查詢分配binlog_cache_size大小的內存。若是語句大於該值,線程則打開臨時文件來保存事務。線程結束後臨時文件被刪除。

Binlog_cache_use狀態變量顯示了使用該緩衝區(也多是臨時文件)保存語句的事務的數量。Binlog_cache_disk_use狀態變量顯示了這些事務中實際上有多少必須使用臨時文件。這兩個變量能夠用於將binlog_cache_size調節到足夠大的值,以免使用臨時文件。

max_binlog_cache_size(默認4GB)能夠用來限制用來緩存多語句事務的緩衝區總大小。若是某個事務大於該值,將會失敗並 回滾。

若是你正使用更新日誌或二進制日誌,當使用CREATE ... SELECT or INSERT ... SELECT時,並行插入被轉換爲普通插入。這樣經過在備份時使用日誌能夠確保從新建立表的備份。

請注意MySQL 5.1值的二進制日誌格式與之前版本的MySQL不一樣,由於複製改進了。參見6.5節,「不一樣MySQL版本之間的複製兼容性」

默認狀況下,並非每次寫入時都將二進制日誌與硬盤同步。所以若是操做系統或機器(不只僅是MySQL服務器)崩潰,有可能二進制日誌中最後的語句丟失了。要想防止這種狀況,你能夠使用sync_binlog全局變量(1是最安全的值,但也是最慢的),使二進制日誌在每N次二進制日誌寫入後與硬盤同步。參見5.3.3節,「服務器系統變量」。即便sync_binlog設置爲1,出現崩潰時,也有可能表內容和二進制日誌內容之間存在不一致性。例如,若是使用InnoDB表,MySQL服務器處理COMMIT語句,它將整個事務寫入二進制日誌並將事務提交到InnoDB中。若是在兩次操做之間出現崩潰,重啓時,事務被InnoDB回滾,但仍然存在二進制日誌中。能夠用--innodb-safe-binlog選項解決該問題,能夠增長InnoDB表內容和二進制日誌之間的一致性。(註釋:在MySQL 5.1中不須要--innodb-safe-binlog;因爲引入了XA事務支持,該選項做廢了)。

該選項能夠提供更大程度的安全,還應對MySQL服務器進行配置,使每一個事務的二進制日誌(sync_binlog =1)和(默認狀況爲真)InnoDB日誌與硬盤同步。該選項的效果是崩潰後重啓時,在滾回事務後,MySQL服務器從二進制日誌剪切 回滾的InnoDB事務。這樣能夠確保二進制日誌反饋InnoDB表的確切數據等,並使從服務器保持與主服務器保持同步(不接收 回滾的語句)。

請注意即便MySQL服務器更新其它存儲引擎而不是InnoDB,也能夠使用--innodb-safe-binlog。在InnoDB崩潰恢復時,只從二進制日誌中刪除影響InnoDB表的語句/事務。若是崩潰恢復時MySQL服務器發現二進制日誌變短了(即至少缺乏一個成功提交的InnoDB事務),若是sync_binlog =1而且硬盤/文件系統的確能根據須要進行同步(有些不須要)則不會發生,則輸出錯誤消息 ("二進制日誌<名>比指望的要小")。在這種狀況下,二進制日誌不許確,複製應從主服務器的數據快照開始。

寫入二進制日誌文件和二進制日誌索引文件的方法與寫入MyISAM表相同。參見A.4.3節,「MySQL處理磁盤滿的方式」

5.11.4. 慢速查詢日誌

用--log-slow-queries[=file_name]選項啓動時,mysqld寫一個包含全部執行時間超過long_query_time秒的SQL語句的日誌文件。得到初使表鎖定的時間不算做執行時間。

若是沒有給出file_name值, 默認未主機名,後綴爲-slow.log。若是給出了文件名,但不是絕對路徑名,文件則寫入數據目錄。

語句執行完而且全部鎖釋放後記入慢查詢日誌。記錄順序能夠與執行順序不相同。

慢查詢日誌能夠用來找到執行時間長的查詢,能夠用於優化。可是,檢查又長又慢的查詢日誌會很困難。要想容易些,你能夠使用mysqldumpslow命令得到日誌中顯示的查詢摘要來處理慢查詢日誌。

在MySQL 5.1的慢查詢日誌中,不使用索引的慢查詢同使用索引的查詢同樣記錄。要想防止不使用索引的慢查詢記入慢查詢日誌,使用--log-short-format選項。參見5.3.1節,「mysqld命令行選項」

在MySQL 5.1中,經過--log-slow-admin-statements服務器選項,你能夠請求將慢管理語句,例如OPTIMIZE TABLE、ANALYZE TABLE和 ALTER TABLE寫入慢查詢日誌。

用查詢緩存處理的查詢不加到慢查詢日誌中,由於表有零行或一行而不能從索引中受益的查詢也不寫入慢查詢日誌。

5.11.5. 日誌文件維護

MySQL服務器能夠建立各類不一樣的日誌文件,從而能夠很容易地看見所進行的操做。參見5.11節,「MySQL日誌文件」。可是,你必須按期清理這些文件,確保日誌不會佔用太多的硬盤空間。

當啓用日誌使用MySQL時,你可能想要不時地備份並刪除舊的日誌文件,並告訴MySQL開始記入新文件。參見5.9.1節,「數據庫備份」

在 Linux (Redhat)的安裝上,你可爲此使用mysql-log-rotate腳本。若是你從RPM分發安裝MySQL,腳本應該自動被安裝了。

在其它系統上,你必須本身安裝短腳本,你可從cron等入手處理日誌文件。

你能夠經過mysqladmin flush-logs或SQL語句FLUSH LOGS來強制MySQL開始使用新的日誌文件。

日誌清空操做作下列事情:

  • 若是使用標準日誌(--log)或慢查詢日誌(--log-slow-queries),關閉並從新打開日誌文件。(默認爲mysql.log和`hostname`-slow.log)。
  • 若是使用更新日誌(--log-update)或二進制日誌(--log-bin),關閉日誌而且打開有更高序列號的新日誌文件。

若是你只使用更新日誌,你只須要從新命名日誌文件,而後在備份前清空日誌。例如,你能夠這樣作:

shell> cd mysql-data-directory
shell> mv mysql.log mysql.old
shell> mysqladmin flush-logs

而後作備份並刪除「mysql.old」

5.12. 在同一臺機器上運行多個MySQL服務器

在一些狀況下,你可能想要在同一臺機器上運行多個mysqld服務器。你可能想要測試一個新的MySQL發佈,同時不影響現有產品的設置。或者,你可能想使不一樣的用戶訪問來訪問不一樣的mysqld服務器以便他們本身來管理。(例如,你多是一個Internet服務提供商,但願爲不一樣的客戶來提供獨立的MySQL安裝)。

要想在一個單獨的機器上運行多個服務器,每一個服務器必須有惟一的各運行參數值。這些值能夠在命令行中設置或在選項文件中設置。參見4.3節,「指定程序選項」

至少下面的選項對每一個服務器必須是不一樣的:

·         --port=port_num

--port控制着TCP/IP鏈接的端口號。

·         --socket=path

--socket控制Unix中的Unix套接字文件路徑和在Windows中的命名管道名稱。在Windows中,只有支持命名管道鏈接的服務器才須要明確指定管道名稱。

·         --shared-memory-base-name=name

該選項當前只在Windows中使用。它指定Windows服務器使用的、容許客戶端經過共享內存來鏈接的共享內存名。

·         --pid-file=path

該選項只在Unix中使用。它指出服務器在其中寫入進程ID的文件名。

若是你使用下面的日誌文件選項,對於每一個服務器來講,它們必須是不一樣的:

·           --log=path

·         --log-bin=path

·         --log-update=path

·         --log-error=path

·         --bdb-logdir=path

日誌文件選項的描述參見5.11.5節,「日誌文件維護」

爲了提升性能,你能夠爲每一個服務器指定下面選項的不一樣的值,以便在物理磁盤之間平均分配負荷:

·         --tmpdir=path

·         --bdb-tmpdir=path

還推薦使用不一樣的臨時目錄,以便容易地肯定哪一個MySQL服務器建立了給定的臨時文件。

通常狀況,每一個服務器應還使用不一樣的數據目錄,能夠經過--datadir=path選項來指定。

警告:通常狀況,你決不要讓兩個服務器更新相同數據庫中的數據。不然,若是你的操做系統不支持故障排除系統鎖定,該可能會致使很是奇怪的結果。若是(不理會該警告)運行的多個服務器使用相同的數據目錄而且啓用了日誌記錄,你必須使用適當的選項來爲每一個服務器指定惟一的日誌文件名。不然,服務器嘗試用相同的文件來記錄日誌。請注意這種類型的設置只能在MyISAM和MERGE表上工做,對其它任何存儲引擎不起做用。

多個服務器共享一個數據目錄的警告也適用於NFS環境。容許多個MySQL服務器經過NFS訪問一個共同的數據目錄是一個很是很差的主義

·         主要問題是NFS存在速度瓶頸。它不是用於這種用途。

·         用NFS的另外一個冒險是你必須提出一個方法來確保兩個或多個服務器不會相互干擾。NFS文件的鎖定一般由lockd後臺程序處理,可是目前,沒有一個運行平臺可以在每種狀況下100%可靠地進行鎖定。

使你更加容易:忘記在服務器之間經過NFS共享數據目錄。一個較好的解決方案是使用包含幾個CPU而且和使用有效處理多線程的操做系統的機器。

若是在不一樣的位置有多個MySQL的安裝,通常狀況能夠用--basedir=path選項爲每一個服務器指定基本安裝目錄,使每一個服務器使用不一樣的數據目錄、日誌文件和PID文件。(全部這些值的 默認值相對於根目錄來肯定)。那樣的話, 你惟一須要指定的其它選項是--socket和--port選項。例如,假如使用tar文件二進制分發版安裝不一樣的MySQL版本。這些安裝在不一樣的位置,所以能夠使用各個安裝服務器相應的根目錄中的bin/mysqld_safe命令啓動服務器。mysqld_safe肯定正確的--basedir選項傳遞給mysqld,你僅須要爲mysqld_safe指定--socket和--port選項。

正以下面幾節所討論的那樣,能夠經過設置環境變量或用指定的命令行選項來啓動更多的服務器。可是,若是你須要在一個更穩定的基礎上運行多個服務器,一個更方便的方法是使用選項文件來爲每一個服務器指定那些選項值,它對每一個服務器必須是惟一的。

5.12.1. 在Windows下運行多個服務器

在Windows中,能夠從命令行手動啓動來運行多個服務器,每一個服務器使用合適的操做參數。在基於Windows NT的系統中,安裝幾個服務器時,你還有將多個服務器安裝爲Windows服務並運行的選項。關於從命令行運行MySQL服務器或做爲服務運行的通常說明在 2.3節,「在Windows上安裝MySQL」中給出。本節描述怎樣確保你用不一樣的啓動選項值(對於每一個服務器必須是惟一的,例如數據目錄)啓動各個服務器。這些選項的描述見5.12節,「在同一臺機器上運行多個MySQL服務器」

5.12.1.1. 在命令行中啓動多個Windows服務器

爲了從命令行手動啓動多個服務器,能夠在命令行中或在選項文件中指定適當的選項。把選項放在選項文件中比較方便,可是須要確保每一個服務器能夠得到本身的選項。爲了實現,爲每一個建立一個選項文件,而且運行服務時經過--defaults-file選項告訴服務器選項文件名。

假設你想要在端口3307使用數據目錄C:\mydata1運行mysqld,而且想在端口3308使用數據目錄C:\mydata1運行mysqld-max。(要想這樣作,啓動服務器以前要確保,每一個數據目錄存在而且有本身的mysql數據庫拷貝,它包含 受權表)。

而後建立兩個選項文件。例如,建立一個文件名爲C:\my-opts1.cnf的配置文件,它看起來象這個樣子:

[mysqld]
datadir = C:/mydata1
port = 3307

建立第二個文件名爲C:\my-opts1.cnf的配置文件,它看起來象這個樣子:

mysqld]
datadir = C:/mydata2
port = 3308

而後,用它們本身的選項文件啓動每一個服務器:

C:\> C:\mysql\bin\mysqld --defaults-file=C:\my-opts1.cnf
C:\> C:\mysql\bin\mysqld-max --defaults-file=C:\my-opts2.cnf

在NT中,每一個服務器在前臺啓動(服務器退出前,不會顯示新的提示符);須要在兩個控制檯窗口中執行這兩個命令。

要想關閉服務器,必須鏈接到相應的端口號:

C:\> C:\mysql\bin\mysqladmin --port=3307 shutdown

C:\> C:\mysql\bin\mysqladmin --port=3308 shutdown

如剛纔所討論的,服務器配置容許客戶端經過TCP/IP來鏈接。若是你的Windows版本支持命名管道而且你想容許命名管道鏈接,使用mysqld-ntmysqld-max-nt服務器並指定啓用命名管道而且指定管道名的選項。支持命名管道鏈接的每一個服務器必須使用一個惟一的管道名。例如,C:\my-opts1.cnf文件可能象這樣來書寫:

[mysqld]
datadir = C:/mydata1
port = 3307
enable-named-pipe
socket = mypipe1

而後,這樣啓動服務器:

C:\> C:\mysql\bin\mysqld-nt --defaults-file=C:\my-opts1.cnf

一樣修改第2個服務器使用的C:\my-opts2.cnf文件。

5.12.1.2. 作爲服務啓動多個Windows服務器

在基於NT的系統中,MySQL服務器能夠以Windows服務的方式來運行。安裝、控制和刪除單個MySQL服務的過程描述見2.3.12節,「以Windows服務方式啓動MySQL」

你還能夠以服務的方式安裝多個MySQL服務器。此時,除了全部參數對每一個服務器必須是惟一的,你還必須確保每一個服務器使用不一樣的服務名。

在下面的說明中,假設你想要運行mysqld-nt服務器的兩個不一樣的版本,它們分別安裝在C:\mysql-4.1.8和C:\mysql-5.1.2-alpha目錄中。(可能存在這種狀況,若是你正在運行版本4.1.8做爲你的產品服務器,還想使用5.1.2-alpha版原本進行測試)。

當用--install或--install-manual選項安裝一個MySQL服務時,應聽從如下原則:

·         若是你沒有指定服務名,服務器使用默認的MySQL服務名,從標準選項文件的[mysqld]組中讀取選項。

·         若是你在--install選項後指定了服務名,服務器忽略[mysqld]選項組,從具備相同名的組中讀取選項做爲服務名。服務器從標準選項文件中讀取選項。

·         若是你在服務名後面指定一個--defaults-file選項,服務器忽略標準選項文件,只從命名的文件的[mysqld]組讀取選項。

釋:MySQL 4.0.17以前,只有使用默認服務名(MySQL)安裝的一個服務器或使用服務名mysqld顯式安裝的一個服務器從標準選項文件讀[mysqld]組。到4.0.17時,若是服務器讀標準選項文件,則它們均讀[mysqld]組,即便它們安裝時使用了另外一個服務名。這樣容許你爲選項使用[mysqld]組,用於全部MySQL服務器,並將根據每一個服務器命名的選項組用於該服務器,即便用那個服務名安裝的服務器。

根據前面敘述,你能夠經過幾個方法來設置多個服務器。下面的說明描述了一些示例。在嘗試以前,應確保你首先關閉而且卸載了全部已有的MySQL服務器。

·         方法1:在一個標準選項文件中指定全部服務器選項。要想這樣作,爲每一個服務器使用不一樣的服務名。假設你想使用服務名mysqld1運行4.1.8版的mysqld-nt並使用服務名mysqld2運行5.1.2-alpha版的mysqld-nt。在這種狀況下,你能夠爲4.1.8使用[mysqld1]組,爲5.1.2-alpha使用[mysqld2]組。例如,你能夠象這樣創建 C:\my.cnf文件:

·                # options for mysqld1 service
·                [mysqld1]
·                basedir = C:/mysql-4.1.8
·                port = 3307
·                enable-named-pipe
·                socket = mypipe1
·                 
·                # options for mysqld2 service
·                [mysqld2]
·                basedir = C:/mysql-5.1.2-alpha
·                port = 3308
·                enable-named-pipe
·                socket = mypipe2

以下面所示安裝服務器,使用服務器的全路徑名來確保Windows爲每一個服務註冊正確的可執行程序:

C:\> C:\mysql-4.1.8\bin\mysqld-nt --install mysqld1
C:\> C:\mysql-5.1.2-alpha\bin\mysqld-nt --install mysqld2

爲了啓動服務器,使用服務管理器,或用帶有適當的服務名的NET START

C:\> NET START mysqld1

C:\> NET START mysqld2

要想中止服務,使用服務管理器,或用帶有適當的服務名的NET STOP

C:\> NET STOP mysqld1
C:\> NET STOP mysqld2

·         方法2:爲每一個服務器用不一樣的文件指定選項,當你安裝服務時使用--defaults-file告訴每一個服務器使用什麼文件。此時,每一個文件應用一個[mysqld]組列出選項。

使用這種方法爲4.1.8版本的mysqld-nt指定選項,應象這樣建立一個C:\my-opts1.cnf文件:

[mysqld]
basedir = C:/mysql-4.1.8
port = 3307
enable-named-pipe
socket = mypipe1

對於5.1.2-alpha版的mysqld-nt,象這樣建立一個C:\my-opts2.cnf文件:

[mysqld]
basedir = C:/mysql-5.1.2-alpha port = 3308
enable-named-pipe
socket = mypipe2

安裝服務以下(在一個單一行中輸入每一個命令):

C:\> C:\mysql-4.1.8\bin\mysqld-nt -- installmysqld1
           --defaults-file=C:\my-opts1.cnf
C:\> C:\mysql-5.1.2-alpha\bin\mysqld-nt -- installmysqld2
           --defaults-file=C:\my-opts2.cnf

當你做爲服務安裝一個MySQL服務器時,要想使用--defaults-file選項,你必須在此選項以前加服務名。

安裝服務後,按照與前面的示例相同的方法啓動和中止。

要想卸載多個服務,對每一個服務使用mysqld --remove,在--remove選項後指定服務名。若是服務名是 默認的(MySQL),你能夠不指定。

5.12.2. 在Unix中運行多個服務器

在Unix中運行多個服務器最容易的方法是使用不一樣的TCP/IP端口s和Unix套接字文件編譯,所以每一個實例在不一樣的網絡接口偵聽。另外,每一個安裝應在不一樣的基礎目錄中編譯,那將自動爲你的每一個服務器產生使用不一樣的編譯進來的數據目錄、日誌文件和PID文件位置。

假設一個現有的4.1.8版本服務器配置爲默認TCP/IP端口號(3306)和Unix套接字文件(/tmp/mysql.sock)。要想配置一個新的5.1.2-alpha版的服務器來使用不一樣的操做參數,使用一個configure命令,大概象這樣使用:

shell> ./configure --with-tcp-port=port_number \
             --with-unix-socket-path=file_name \
             --prefix=/usr/local/mysql-5.1.2-alpha

這裏,port_numberfile_name必須不一樣於默認TCP/IP端口號和Unix套接字文件路徑名,而且--prefix值應指定一個不一樣於現有MySQL安裝目錄的安裝目錄。

若是你有一個MySQL服務器正偵聽一個給定的端口號,你能夠使用下面的命令來找出針對一些重要配置變量它使用了那些操做參數,包括基礎目錄和Unix套接字文件名:

shell> mysqladmin --host=host_name --port=port_number variables

經過該命令顯示的信息,當配置其它服務器時,你能夠告訴服務器該選項沒有使用的值。

請注意,若是你指定localhost做爲一個主機名,mysqladmin默認使用Unix套接字文件鏈接,而不是TCP/IP。從 MySQL 4.1開始,經過--protocol= TCP | SOCKET | PIPE | MEMORY}選項,你能夠顯示地指定鏈接協議。

若是隻是用一個不一樣的Unix套接字文件和TCP/IP端口號啓動,沒必要編譯新的MySQL服務器。還能夠在運行時指定這些值。這樣作的一個方法是使用命令行選項:

shell> mysqld_safe --socket=file_name --port=port_number

要啓動第二個服務器,提供不一樣的--socket和--port選項值,而且傳遞一個--datadir=path選項給mysqld_safe,以便服務器使用一個不一樣的數據目錄。

達到類似效果的另外一個方法是使用環境變量來設置 Unix套接字文件名和TCP/IP端口號:

shell> MYSQL_UNIX_PORT=/tmp/mysqld-new.sock
shell> MYSQL_TCP_PORT=3307
shell> export MYSQL_UNIX_PORT MYSQL_TCP_PORT
shell> mysql_install_db --user=mysql
shell> mysqld_safe --datadir=/path/to/datadir &

這是一個快速啓動第二個服務器以用於測試的方法。該方法的最大好處是環境變量設定值適用於你從相同的shell調用的任何客戶端程序。於是,那些客戶端鏈接自動指向第二個服務器!

附錄F:環境變量包括你能夠使用的影響mysqld的其它環境變量列表

對於自動服務器啓動,對於每一個服務器,機器引導時執行的啓動腳本應執行下面的命令,每一個命令用一個相應的選項文件路徑:

mysqld_safe --defaults-file=path

每一個選項文件應包含一個給定服務器特定的選項值。

在Unix中,mysqld_multi腳本是啓動多個服務器的另外一個方法。參見5.1.5節,「mysqld_multi:管理多個MySQL服務器的程序」

5.12.3. 在多服務器環境中使用客戶端程序

當你想要用一個客戶端程序鏈接一個MySQL服務器時,該服務器偵聽不一樣的網絡接口,而不是編譯到你的客戶端的網絡接口,你能夠使用下面的方法:

·         啓動客戶端,用--host=host_name --port=port_number經過TCP/IP來鏈接一個遠程服務器,用--host=127.0.0.1 --port=port_number經過TCP/IP來鏈接一個本地服務器,或者用--host=localhost --socket=file_name經過一個Unix套接字文件或一個Windows命名管道來鏈接一個本地服務器。

·         從MySQL 4.1起,啓動客戶端時用--protocol=tcp經過TCP/IP來鏈接,用--protocol=socket經過一個Unix套接字文件來鏈接,用--protocol=pipe經過一個命名管道來鏈接,或用--protocol=memory經過共享內存來鏈接。對於TCP/IP鏈接,你可能還須要指定--host和--port選項。對於其它類型的鏈接,你可能須要指定一個--socket選項來指定一個Unix套接字文件或命名管道名,或者一個--shared-memory-base-name選項來指定共享內存名。共享內存鏈接僅在Windows中支持。

·         在Unix中,在你啓動客戶端以前,設置MYSQL_UNIX_PORT和MYSQL_TCP_PORT環境變量來指定Unix套接字文件和TCP/IP端口號。若是你常用具體的套接字文件或端口號,你能夠在.login文件中放置命令來設置環境變量以便你每次登陸時該命令起做用。參見附錄F:環境變量

·         在一個選項文件的[client]組中指定默認Unix套接字文件和TCP/IP端口號。例如,你能夠在Windows中使用C:\my.cnf文件,或在Unix中主目錄內使用.my.cnf文件。參見4.3.2節,「使用選項文件」

·         在C程序中,在mysql_real_connect()調用時,你能夠指定套接字文件或端口號參數。經過調用mysql_options(),你還能夠有程序讀選項文件。參見25.2.3節,「C API函數描述」

·         若是你正在使用Perl DBD::mysql模塊,你能夠從MySQL選項文件中讀取選項。例如:

·                $dsn = "DBI:mysql:test;mysql_read_default_group=client;"
·                        . "mysql_read_default_file=/usr/local/mysql/data/my.cnf";
·                    $dbh = DBI->connect($dsn, $user, $password);

參見25.4節,「MySQL Perl API」

其它程序接口能夠爲讀選項文件提供類似的功能。

5.13. MySQL查詢高速緩衝

查詢緩存存儲SELECT查詢的文本以及發送給客戶端的相應結果。若是隨後收到一個相同的查詢,服務器從查詢緩存中從新獲得查詢結果,而再也不須要解析和執行查詢。

若是你有一個不常常改變的表而且服務器收到該表的大量相同查詢,查詢緩存在這樣的應用環境中十分有用。對於許多Web服務器來講存在這種典型狀況,它根據數據庫內容生成大量的動態頁面。

釋:查詢緩存不返回舊的數據。當表更改後,查詢緩存值的相關條目被清空。

釋:若是你有許多mysqld服務器更新相同的MyISAM表,在這種狀況下查詢緩存不起做用。

釋:查詢緩存不適用於服務器方編寫的語句。若是正在使用服務器方編寫的語句,要考慮到這些語句將不會應用查詢緩存。參見 25.2.4節,「C API預處理語句」

下面是查詢緩存的一些性能數據。這些結果是在Linux Alpha 2 x 500MHz系統(2GB RAM,64MB查詢緩存)上運行MySQL基準組件產生的。

·         若是執行的全部查詢是簡單的(如從只有一行數據的表中選取一行),但查詢是不一樣的,查詢不能被緩存,查詢緩存激活率是13%。這能夠看做是最壞的情形。在實際應用中,查詢要複雜得多,所以,查詢緩存使用率通常會很低。

·         從只有一行的表中查找一行數據時,使用查詢緩存比不使用速度快238%。這能夠看做查詢使用緩存時速度提升最小的狀況。

服務器啓動時要禁用查詢緩存,設置query_cache_size系統變量爲0。禁用查詢緩存代碼後,沒有明顯的速度提升。編譯MySQL時,經過在configure中使用--without-query-cache選項,能夠從服務器中完全去除查詢緩存能力。

5.13.1. 查詢高速緩衝如何工做

本節描述查詢緩存的工做原理。5.13.3節,「查詢高速緩衝配置」描述了怎樣控制是否使用查詢緩存。

查詢解析以前進行比較,所以下面的兩個查詢被查詢緩存認爲是不相同的:

SELECT * FROM tbl_name
Select * from tbl_name

查詢必須是徹底相同的(逐字節相同)纔可以被認爲是相同的。另外,一樣的查詢字符串因爲其它緣由可能認爲是不一樣的。使用不一樣的數據庫、不一樣的協議版本或者不一樣 默認字符集的查詢被認爲是不一樣的查詢而且分別進行緩存。

從查詢緩存中提取一個查詢以前,MySQL檢查用戶對全部相關數據庫和表的SELECT權限。若是沒有權限,不使用緩存結果。

若是從查詢緩存中返回一個查詢結果,服務器把Qcache_hits狀態變量的值加一,而不是Com_select變量。參見5.13.4節,「查詢高速緩衝狀態和維護」

若是一個表被更改了,那麼使用那個表的全部緩衝查詢將再也不有效,而且從緩衝區中移出。這包括那些映射到改變了的表的使用MERGE表的查詢。一個表能夠被許多類型的語句更改,例如INSERT、UPDATE、DELETE、TRUNCATE、ALTER TABLE、DROP TABLE或DROP DATABASE。

COMMIT執行完後,被更改的事務InnoDB表再也不有效。

使用InnoDB表時,查詢緩存也在事務中工做,使用該表的版本號來檢測其內容是否仍舊是當前的。

在MySQL 5.1中,視圖產生的查詢被緩存。

SELECT SQL_CALC_FOUND_ROWS ...和SELECT FOUND_ROWS() type類型的查詢使用查詢緩存。即便因建立的行數也被保存在緩衝區內,前面的查詢從緩存中提取,FOUND_ROWS()也返回正確的值。

若是一個查詢包含下面函數中的任何一個,它不會被緩存:

BENCHMARK()

CONNECTION_ID()

CURDATE()

CURRENT_DATE()

CURRENT_TIME()

CURRENT_TIMESTAMP()

CURTIME()

DATABASE()

帶一個參數的ENCRYPT()

FOUND_ROWS()

GET_LOCK()

LAST_INSERT_ID()

LOAD_FILE()

MASTER_POS_WAIT()

NOW()

RAND()

RELEASE_LOCK()

SYSDATE()

不帶參數的UNIX_TIMESTAMP()

USER()

 

在下面的這些條件下,查詢也不會被緩存:

·         引用自定義函數(UDFs)。

·         引用自定義變量。

·         引用mysql系統數據庫中的表。

·         下面方式中的任何一種:

SELECT ...IN SHARE MODE
SELECT ...FOR UPDATE
SELECT ...INTO OUTFILE ...
SELECT ...INTO DUMPFILE ...
SELECT * FROM ...WHERE autoincrement_col IS NULL

最後一種方式不能被緩存是由於它被用做爲ODBC工做區來獲取最近插入的ID值。參見26.1.14.1節,「如何在ODBC中獲取AUTO_INCREMENT列的值

·          被做爲編寫好的語句,即便沒有使用佔位符。例如,下面使用的查詢:

char *my_sql_stmt = "SELECT a,b FROM table_c";
   /* ...*/
mysql_stmt_prepare(stmt,my_sql_stmt,strlen(my_sql_stmt));

不被緩存。參見25.2.4節,「C API預處理語句」

·         使用TEMPORARY表。

·         不使用任何表。

·         用戶有某個表的列級權限。

5.13.2. 查詢高速緩衝SELECT選項

能夠在SELECT語句中指定查詢緩存相關選項:

·          SQL_CACHE

若是query_cache_type系統變量的值是ON或DEMAND,查詢結果被緩存。

·          SQL_NO_CACHE

查詢結果不被緩存。

示例:

SELECT SQL_CACHE id, name FROM customer;
SELECT SQL_NO_CACHE id, name FROM customer;

5.13.3. 查詢高速緩衝配置

經過have_query_cache服務器系統變量指示查詢緩存是否可用:

mysql> SHOW VARIABLES LIKE 'have_query_cache';
+------------------+-------+
| Variable_name    | Value |
+------------------+-------+
| have_query_cache | YES   |
+------------------+-------+

即便禁用查詢緩存,當使用標準 MySQL二進制時,這個值老是YES。

其它幾個系統變量控制查詢緩存操做。當啓動mysqld時,這些變量能夠在選項文件或者命令行中設置。全部查詢緩存系統變量名以query_cache_ 開頭。它們的詳細描述見5.3.3節,「服務器系統變量」,還給出了額外的配置信息。

爲了設置查詢緩存大小,設置query_cache_size系統變量。設置爲0表示禁用查詢緩存。 默認緩存大小設置爲0;也就是禁用查詢緩存。

當設置query_cache_size變量爲非零值時,應記住查詢緩存至少大約須要40KB來分配其數據結構。(具體大小取決於系統結構)。若是你把該值設置的過小,將會獲得一個警告,如本例所示:

mysql> SET GLOBAL query_cache_size = 40000;

Query OK, 0 rows affected, 1 warning (0.00 sec)

 

mysql> SHOW WARNINGS\G

*************************** 1. row ***************************

  Level: Warning

   Code: 1282

Message: Query cache failed to set size 39936; new query cache size is 0

 

mysql> SET GLOBAL query_cache_size = 41984;

Query OK, 0 rows affected (0.00 sec)

 

mysql> SHOW VARIABLES LIKE 'query_cache_size';

+------------------+-------+

| Variable_name    | Value |

+------------------+-------+

| query_cache_size | 41984 |

+------------------+-------+

若是查詢緩存大小設置爲大於0,query_cache_type變量影響其工做方式。這個變量能夠設置爲下面的值:

·         0或OFF將阻止緩存或查詢緩存結果。

·         1或ON將容許緩存,以SELECT SQL_NO_CACHE開始的查詢語句除外。

·         2或DEMAND,僅對以SELECT SQL_CACHE開始的那些查詢語句啓用緩存。

設置query_cache_type變量的GLOBAL值將決定更改後全部鏈接客戶端的緩存行爲。具體客戶端能夠經過設置query_cache_type變量的會話值控制它們自己鏈接的緩存行爲。例如,一個客戶能夠禁用本身的查詢緩存,方法以下:

mysql> SET SESSION query_cache_type = OFF;

要控制能夠被緩存的具體查詢結果的最大值,應設置query_cache_limit變量。 默認值是1MB。

當一個查詢結果(返回給客戶端的數據)從查詢緩衝中提取期間,它在查詢緩存中排序。所以,數據一般不在大的數據塊中處理。查詢緩存根據數據排序要求分配數據塊,所以,當一個數據塊用完後分配一個新的數據塊。由於內存分配操做是昂貴的(費時的),因此經過query_cache_min_res_unit系統變量給查詢緩存分配最小值。當查詢執行時,最新的結果數據塊根據實際數據大小來肯定,所以能夠釋放不使用的內存。根據你的服務器執行查詢的類型,你會發現調整query_cache_min_res_unit變量的值是有用的:

·         query_cache_min_res_unit默認值是4KB。這應該適合大部分狀況。

·         若是你有大量返回小結果數據的查詢,默認數據塊大小可能會致使內存碎片,顯示爲大量空閒內存塊。因爲缺乏內存,內存碎片會強制查詢緩存從緩存內存中修整(刪除)查詢。這時,你應該減小query_cache_min_res_unit變量的值。空閒塊和因爲修整而移出的查詢的數量經過Qcache_free_blocks和Qcache_lowmem_prunes變量的值給出。

·          若是大量查詢返回大結果(檢查 Qcache_total_blocks和Qcache_queries_in_cache狀態變量),你能夠經過增長query_cache_min_res_unit變量的值來提升性能。可是,注意不要使它變得太大(參見前面的條目)。

5.13.4. 查詢高速緩衝狀態和維護

能夠使用下面的語句檢查MySQL服務器是否提供查詢緩存功能:

mysql> SHOW VARIABLES LIKE 'have_query_cache';

+------------------+-------+

| Variable_name    | Value |

+------------------+-------+

| have_query_cache | YES   |

+------------------+-------+

能夠使用FLUSH QUERY CACHE語句來清理查詢緩存碎片以提升內存使用性能。該語句不從緩存中移出任何查詢。

RESET QUERY CACHE語句從查詢緩存中移出全部查詢。FLUSH TABLES語句也執行一樣的工做。

爲了監視查詢緩存性能,使用SHOW STATUS查看緩存狀態變量:

mysql> SHOW STATUS LIKE 'Qcache%';
+-------------------------+--------+
|變量名                   |值 |
+-------------------------+--------+
| Qcache_free_blocks      | 36     |
| Qcache_free_memory      | 138488 |
| Qcache_hits             | 79570  |
| Qcache_inserts          | 27087  |
| Qcache_lowmem_prunes    | 3114   |
| Qcache_not_cached       | 22989  |
| Qcache_queries_in_cache | 415    |
| Qcache_total_blocks     | 912    |
+-------------------------+--------+

這些變量的描述見5.3.4節,「服務器狀態變量」。這裏描述它們的一些應用。

SELECT查詢的總數量等價於:

Com_select
+ Qcache_hits
+ queries with errors found by parser

Com_select的值等價於:

Qcache_inserts
+ Qcache_not_cached
+ queries with errors found during columns/rights check

查詢緩存使用長度可變塊,所以Qcache_total_blocks和Qcache_free_blocks能夠顯示查詢緩存內存碎片。執行FLUSH QUERY CACHE後,只保留一個空閒塊。

每一個緩存查詢至少須要兩個塊(一個塊用於查詢文本,一個或多個塊用於查詢結果)。而且,每個查詢使用的每一個表須要一個塊。可是,若是兩個或多個查詢使用相同的表,僅須要分配一個塊。

Qcache_lowmem_prunes狀態變量提供的信息可以幫助你你調整查詢緩存的大小。它計算爲了緩存新的查詢而從查詢緩衝區中移出到自由內存中的查詢的數目。查詢緩衝區使用最近最少使用(LRU)策略來肯定哪些查詢從緩衝區中移出。調整信息在5.13.3節,「查詢高速緩衝配置」中給出。


這是MySQL參考手冊的翻譯版本,關於MySQL參考手冊,請訪問dev.mysql.com。 原始參考手冊爲英文版,與英文版參考手冊相比,本翻譯版可能不是最新的。

相關文章
相關標籤/搜索