【原創】MySQLProxy-內部結構
在 MySQL Proxy 的指令碼元素中有一些基本的內部結構需要知道。其中最主要的結構就是 proxy ,其提供了訪問貫穿指令碼中的許多公共結構的介面,例如連線列表和配置的 backend server 。其他結構,例如來自客戶端的包和返回的結果集等,只有在具體的指令碼函式的上下文環境中才是可以訪問的。
下表中描述了 MySQL proxy 指令碼元素的公共屬性。
Attribute | Description |
---|---|
connection | A structure containing the active client connections. For a list of attributes, seeproxy.connection. |
servers | A structure containing the list of configured backend servers. For a list of attributes, seeproxy.global.backends. |
queries | A structure containing the queue of queries that will be sent to the server during a single client query. For a list of attributes, see proxy.queries. |
PROXY_VERSION | The version number of MySQL Proxy, encoded in hex. You can use this to check that the version number supports a particular option from within the Lua script. Note that the value is encoded as a hex value, so to check the version is at least 0.5.1 you compare against0x00501. |
proxy.connection
proxy.connection 物件是隻讀的,提供了關於當前連線的資訊,其內容被分成了客戶端和伺服器兩張表。這樣就允許你可以既檢查來自於客戶端到 proxy 的連線資訊(儲存在client中),又可以檢查 proxy 到伺服器的連線資訊(儲存在server中)。
下表描述了 proxy.connection 物件中客戶端和伺服器屬性。
Attribute | Description |
---|---|
client.default_db | Default database requested by the client |
client.username | User name used to authenticate |
client.scrambled_password | The scrambled version of the password used to authenticate |
client.dst.name | The combined address:port of the Proxy port used by this client (should match the –proxy-address configuration parameter) |
client.dst.address | The IP address of the of the Proxy port used by this client |
client.dst.port | The port number of the of the Proxy port used by this client |
client.src.name | The combined address:port of the client (originating) TCP/IP endpoint |
client.src.address | The IP address of the client (originating) TCP/IP port |
client.src.port | The port of the client (originating) TCP/IP endpoint |
server.scramble_buffer | The scramble buffer used to scramble the password |
server.mysqld_version | The MySQL version number of the server |
server.thread_id | The ID of the thread handling the connection to the current server |
server.dst.name | The combined address:port for the backend server for the current connection (i.e. the connection to the MySQL server) |
server.dst.address | The address for the backend server |
server.dst.port | The port for the backend server |
server.src.name | The combined address:port for the TCP/IP endpoint used by the Proxy to connect to the backend server |
server.src.address | The address of the endpoint for the proxy-side connection to the MySQL server |
server.src.port | The port of the endpoint for the proxy-side connection to the MySQL server |
proxy.global.backends
proxy.global.backends 表示部分可寫的,並且其以陣列的形式包含了所有的已配置 backend server 和伺服器後設資料(IP地址,狀態等)的資訊。你可以通過 proxy.connection[“backend_ndx”] 的方式指定當前連線的陣列索引值,backend_ndx 是被有效連線使用了的 backend server 表的索引值。
下表描述了表 proxy.global.backends 中的每一個入口的屬性值。
Attribute | Description |
---|---|
dst.name | The combined address:port of the backend server. |
dst.address | The IP address of the backend server. |
dst.port | The port of the backend server. |
connected_clients | The number of clients currently connected. |
state | The status of the backend server. See Backend State/Type Constants. |
type | The type of the backend server. You can use this to identify whether the backed was configured as a standard read/write backend, or a read-only backend. You can compare this value to the proxy.BACKEND_TYPE_RW andproxy.BACKEND_TYPE_RO. |
proxy.queries
proxy.queries 物件是一個佇列,用於儲存將要傳送到伺服器的的 query 列表。該佇列不會被自動填入(populated),故如果你不顯式地向該佇列填入內容,query 將會被不做任何修改的傳送到 backend server,同樣,如果你不手動將 query 新增到佇列中,read_query_result() 函式將不會被觸發。
下面的函式可以用於對 proxy.queries 物件進行操作。
Function | Description |
---|---|
append(id,packet,[options]) | Appends a query to the end of the query queue. The id is an integer identifier that you can use to recognize the query results when they are returned by the server. The packet should be a properly formatted query packet. The optional options should be a table containing the options specific to this packet. |
prepend(id,packet) | Prepends a query to the query queue. The id is an identifier that you can use to recognize the query results when they are returned by the server. The packet should be a properly formatted query packet. |
reset() | Empties the query queue. |
len() | Returns the number of query packets in the queue. |
例如,你可以通過使用函式 append() 將一個 query 包附加到 proxy.queries 佇列的尾部:
proxy.queries:append(1,packet)
函式 append() 的可選的第三個引數應該包含針對當前包的一些選項設定。為了能夠在函式 read_query_result() 中訪問結果集,需要設定選項 resultset_is_needed 為 true :
proxy.queries:append( 1, packet, { resultset_is_needed = true } )
如果該選項設定為 false(預設設定),proxy 將:
- 在收到結果集時立刻將其傳送給客戶端
- 減少記憶體使用(因為結果集不需要為處理在proxy內部儲存)
- 減少返回結果給客戶端的延遲
- 從伺服器到客戶端的傳輸資料不作改變
由此可知,如果你僅僅想要監控被髮送的 query 和基本的統計資訊,那麼在預設模式下速度會更快,也更要求。
為了在返回資料上進行任何形式的操作,都必須將 resultset_is_needed 設定為 true ,設定後:
- proxy 會儲存結果集以備後續處理使用
- 使能將結果集返回給客戶端前可以進行修改的能力
- 使能將結果集返回給客戶端前可以丟棄結果集的能力
proxy.response
proxy.response 結構被用於在你打算返回你自己的 MySQL response 的情況下,而不返回給客戶端來自伺服器的應答包。該結構中包含了 response 的型別資訊,一個可選的錯誤資訊,以及(行/列)結果集。
下表描述了 proxy.response 結構的屬性值。
Attribute | Description |
---|---|
type | The type of the response. The type must be either MYSQLD_PACKET_OK orMYSQLD_PACKET_ERR. If the MYSQLD_PACKET_ERR, you should set the value of themysql.response.errmsg with a suitable error message. |
errmsg | A string containing the error message that will be returned to the client. |
resultset | A structure containing the result set information (columns and rows), identical to what would be returned when returning a results from a SELECT query. |
當使用 proxy.response 時,或者你設定 proxy.response.type 的值為 proxy.MYSQLD_PACKET_OK ,並構建包含要返回的結果的自定義結果集;或者你設定 proxy.response.type 的值為 proxy.MYSQLD_PACKET_ERR ,並設定 proxy.response.errmsg 值為表示錯誤訊息內容的字串。為了傳送完整的結果集或者錯誤訊息,你應該返回 proxy.PROXY_SEND_RESULT 以觸發在函式中構建內容的返回。
上述說明的一個具體例子可以參閱 MySQL Proxy 原始碼包中 tutorial-resultset.lua 指令碼:
if string.lower(command) == "show" and string.lower(option) == "querycounter" then --- -- proxy.PROXY_SEND_RESULT requires -- -- proxy.response.type to be either -- * proxy.MYSQLD_PACKET_OK or -- * proxy.MYSQLD_PACKET_ERR -- -- for proxy.MYSQLD_PACKET_OK you need a resultset -- * fields -- * rows -- -- for proxy.MYSQLD_PACKET_ERR -- * errmsg proxy.response.type = proxy.MYSQLD_PACKET_OK proxy.response.resultset = { fields = { { type = proxy.MYSQL_TYPE_LONG, name = "global_query_counter", }, { type = proxy.MYSQL_TYPE_LONG, name = "query_counter", }, }, rows = { { proxy.global.query_counter, query_counter } } } -- we have our result, send it back return proxy.PROXY_SEND_RESULT elseif string.lower(command) == "show" and string.lower(option) == "myerror" then proxy.response.type = proxy.MYSQLD_PACKET_ERR proxy.response.errmsg = "my first error" return proxy.PROXY_SEND_RESULT
proxy.response.resultset
proxy.response.resultset 結構應該被填入返回資料的 row 和 column 資訊。該結構中包含了整個結果集的資訊,其中涉及到的單獨的元素在下面表述。
下表中描述了 proxy.response.resultset 結構的屬性值。
Attribute | Description |
---|---|
fields | The definition of the columns being returned. This should be a dictionary structure with thetype specifying the MySQL data type, and the name specifying the column name. Columns should be listed in the order of the column data that will be returned. |
flags | A number of flags related to the result set. Valid flags include auto_commit (whether an automatic commit was triggered), no_good_index_used (the query executed without using an appropriate index), and no_index_used (the query executed without using any index). |
rows | The actual row data. The information should be returned as an array of arrays. Each inner array should contain the column data, with the outer array making up the entire result set. |
warning_count | The number of warnings for this result set. |
affected_rows | The number of rows affected by the original statement. |
insert_id | The last insert ID for an auto-incremented column in a table. |
query_status | The status of the query operation. You can use the MYSQLD_PACKET_OK orMYSQLD_PACKET_ERR constants to populate this parameter. |
================ 下面是一些常量定義 ===================
[[Proxy Return State Constants]]
下表中給出的是被 proxy 在內部使用的常量值定義,用於標識傳送到客戶端和伺服器的應答包。所有的常量都在 proxy 表中以常量值的形式可見。
Constant | Description |
---|---|
PROXY_SEND_QUERY | Causes the proxy to send the current contents of the queries queue to the server. |
PROXY_SEND_RESULT | Causes the proxy to send a result set back to the client. |
PROXY_IGNORE_RESULT | Causes the proxy to drop the result set (nothing is returned to the client). |
作為常量值,這些實體在 Lua 指令碼中是無條件的可用。例如,在函式 read_query_result() 的結尾,你可能返回常量 PROXY_IGNORE_RESULT :
return proxy.PROXY_IGNORE_RESULT
[[Packet State Constants]]
下面的狀態值用於定義網路包的狀態資訊。這些值也存在於 proxy 表中。
Constant | Description |
---|---|
MYSQLD_PACKET_OK | The packet is OK |
MYSQLD_PACKET_ERR | The packet contains error information |
MYSQLD_PACKET_RAW | The packet contains raw data |
[[Backend State/Type Constants]]
下面的常量被用於定義 backend MySQL server 的狀態和型別。這些值也存在於 proxy 表中。
Constant | Description |
---|---|
BACKEND_STATE_UNKNOWN | The current status is unknown |
BACKEND_STATE_UP | The backend is known to be up (available) |
BACKEND_STATE_DOWN | The backend is known to be down (unavailable) |
BACKEND_TYPE_UNKNOWN | Backend type is unknown |
BACKEND_TYPE_RW | Backend is available for read/write |
BACKEND_TYPE_RO | Backend is available only for read-only use |
[[Server Command Constants]]
下表中描述的值被用於客戶端和伺服器進行包交換過中標識包中其餘內容的資訊型別。這些值也存在於 proxy 表中。包型別由傳送包的第一個位元組指定。例如,當為了修改或者監聽的目的攔截來自於客戶端的包時,你需要檢查包的第一個位元組是否為 proxy.COM_QUERY 型別。
Constant | Description |
---|---|
COM_SLEEP | Sleep |
COM_QUIT | Quit |
COM_INIT_DB | Initialize database |
COM_QUERY | Query |
COM_FIELD_LIST | Field List |
COM_CREATE_DB | Create database |
COM_DROP_DB | Drop database |
COM_REFRESH | Refresh |
COM_SHUTDOWN | Shutdown |
COM_STATISTICS | Statistics |
COM_PROCESS_INFO | Process List |
COM_CONNECT | Connect |
COM_PROCESS_KILL | Kill |
COM_DEBUG | Debug |
COM_PING | Ping |
COM_TIME | Time |
COM_DELAYED_INSERT | Delayed insert |
COM_CHANGE_USER | Change user |
COM_BINLOG_DUMP | Binlog dump |
COM_TABLE_DUMP | Table dump |
COM_CONNECT_OUT | Connect out |
COM_REGISTER_SLAVE | Register slave |
COM_STMT_PREPARE | Prepare server-side statement |
COM_STMT_EXECUTE | Execute server-side statement |
COM_STMT_SEND_LONG_DATA | Long data |
COM_STMT_CLOSE | Close server-side statement |
COM_STMT_RESET | Reset statement |
COM_SET_OPTION | Set option |
COM_STMT_FETCH | Fetch statement |
COM_DAEMON | Daemon (MySQL 5.1 only) |
COM_ERROR | Error |
[[MySQL Type Constants]]
下面的常量被用於對 query 的結果中的資料進行域型別標識。這些值也存在於 proxy 表中。
Constant | Field Type |
---|---|
MYSQL_TYPE_DECIMAL | Decimal |
MYSQL_TYPE_NEWDECIMAL | Decimal (MySQL 5.0 or later) |
MYSQL_TYPE_TINY | Tiny |
MYSQL_TYPE_SHORT | Short |
MYSQL_TYPE_LONG | Long |
MYSQL_TYPE_FLOAT | Float |
MYSQL_TYPE_DOUBLE | Double |
MYSQL_TYPE_NULL | Null |
MYSQL_TYPE_TIMESTAMP | Timestamp |
MYSQL_TYPE_LONGLONG | Long long |
MYSQL_TYPE_INT24 | Integer |
MYSQL_TYPE_DATE | Date |
MYSQL_TYPE_TIME | Time |
MYSQL_TYPE_DATETIME | Datetime |
MYSQL_TYPE_YEAR | Year |
MYSQL_TYPE_NEWDATE | Date (MySQL 5.0 or later) |
MYSQL_TYPE_ENUM | Enumeration |
MYSQL_TYPE_SET | Set |
MYSQL_TYPE_TINY_BLOB | Tiny Blob |
MYSQL_TYPE_MEDIUM_BLOB | Medium Blob |
MYSQL_TYPE_LONG_BLOB | Long Blob |
MYSQL_TYPE_BLOB | Blob |
MYSQL_TYPE_VAR_STRING | Varstring |
MYSQL_TYPE_STRING | String |
MYSQL_TYPE_TINY | Tiny (compatible with MYSQL_TYPE_CHAR) |
MYSQL_TYPE_ENUM | Enumeration (compatible with MYSQL_TYPE_INTERVAL) |
MYSQL_TYPE_GEOMETRY | Geometry |
MYSQL_TYPE_BIT | Bit |
相關文章
- Redis 內部資料結構Redis資料結構
- 【REDO】Oracle redo內部結構Oracle Redo
- Kafak探究之路- 內部結構小結
- Redis 字串 內部資料結構Redis字串資料結構
- Redis 物件內部組織結構 —— 字典Redis物件
- FPGA內部硬體結構簡介FPGA
- gdb golang 檢視iface 內部結構Golang
- redis 資料結構和內部編碼Redis資料結構
- Java HashMap原理及內部儲存結構JavaHashMap
- PostgreSQL DBA(16) - WAL segment file內部結構SQL
- PostgreSQL DBA(17) - XLOG Record data內部結構SQL
- 放大器內部結構原理圖解圖解
- 資料庫內部儲存結構探索資料庫
- 探索Kafka消費者的內部結構Kafka
- Redis資料結構的內部編碼Redis資料結構
- Redis內部資料結構詳解(4)——ziplistRedis資料結構
- 【Redis】內部資料結構自頂向下梳理Redis資料結構
- 利用泛型模擬棧結構實現內部鏈式儲存結構泛型
- 位元組碼檔案的內部結構之謎
- 見微知著 —— Redis 字串精緻的內部結構Redis字串
- (三分鐘系列)詳解Redis字串內部結構Redis字串
- 見微知著——Redis字串內部結構原始碼分析Redis字串原始碼
- 32. DDR2記憶體內部結構-1記憶體
- 見縫插針 —— 深入 Redis HyperLogLog 內部資料結構分析Redis資料結構
- 這高階玩意的的內部結構你瞭解多少
- CNN、RNN、DNN的內部網路結構有什麼區別?CNNRNNDNN
- 自學C day03-CPU內部結構和暫存器
- ANA:內部機構持續崛起
- 架構團隊如何重構內部系統架構
- 每天一個 PHP 語法六陣列使用及內部結構PHP陣列
- 原創:oracle 事務總結Oracle
- 原來 ArrayList 內部原理這麼簡單
- 使用Kimi+Markmap總結檔案內容生成思維導圖原創
- 每天一個 PHP 語法二字串使用及內部結構PHP字串
- java內部類,區域性內部類,靜態內部類,匿名內部類Java
- 淺析Block的內部結構 , 及分析其是如何利用 NSInvocation 進行呼叫BloC
- 探索Redis設計與實現2:Redis內部資料結構詳解——dictRedis資料結構
- 探索Redis設計與實現3:Redis內部資料結構詳解——sdsRedis資料結構
- 探索Redis設計與實現4:Redis內部資料結構詳解——ziplistRedis資料結構