unsigned long
mysql_real_escape_string(MYSQL *mysql,
char *to,
const char *from,
unsigned long length)
此函數會建立一個合法的 SQL 字串,以用於 SQL 陳述式中。請參閱字串文字。
如果啟用 NO_BACKSLASH_ESCAPES
SQL 模式,mysql_real_escape_string()
會失敗並產生 CR_INSECURE_API_ERR
錯誤。在此情況下,該函數無法逸出引號字元,除非將其加倍,而且為了正確執行此動作,它必須知道比可用資訊更多的關於引號內容的資訊。請改用 mysql_real_escape_string_quote()
,此函數會採用額外的引數來指定引號內容。
mysql
引數必須是有效的開啟連線,因為字元逸出取決於伺服器正在使用的字元集。
會編碼 from
引數中的字串,以產生逸出的 SQL 字串,並考量連線的目前字元集。結果會放置在 to
引數中,後面接著一個終止的空位元組。
編碼的字元為 \
、'
、"
、NUL
(ASCII 0)、\n
、\r
和 Control+Z。嚴格來說,MySQL 只需要逸出反斜線和用於在查詢中引號字串的引號字元即可。mysql_real_escape_string()
會引號其他字元,以使其在日誌檔案中更容易閱讀。為進行比較,請參閱字串文字的引號規則和 QUOTE()
SQL 函數,位於字串文字和字串函數和運算子。
from
所指向的字串必須是 length
個位元組長。您必須配置 to
緩衝區,使其至少為 length*2+1
個位元組長。(在最壞的情況下,每個字元可能都需要編碼為使用兩個位元組,而且必須有空間容納終止的空位元組。)當 mysql_real_escape_string()
傳回時,to
的內容為以 null 結尾的字串。傳回值是編碼字串的長度,不包括終止的空位元組。
如果您必須變更連線的字元集,請使用 mysql_set_character_set()
函數,而不是執行 SET NAMES
(或 SET CHARACTER SET
) 陳述式。mysql_set_character_set()
的作用類似於 SET NAMES
,但也會影響 mysql_real_escape_string()
使用的字元集,而 SET NAMES
則不會。
下列範例會在 INSERT
陳述式中插入兩個逸出的字串,每個字串都在單引號字元內
char query[1000],*end;
end = my_stpcpy(query,"INSERT INTO test_table VALUES('");
end += mysql_real_escape_string(&mysql,end,"What is this",12);
end = my_stpcpy(end,"','");
end += mysql_real_escape_string(&mysql,end,"binary data: \0\r\n",16);
end = my_stpcpy(end,"')");
if (mysql_real_query(&mysql,query,(unsigned int) (end - query)))
{
fprintf(stderr, "Failed to insert row, Error: %s\n",
mysql_error(&mysql));
}
範例中使用的 my_stpcpy()
函數包含在 libmysqlclient
程式庫中,其作用類似於 strcpy()
,但會傳回第一個參數的終止空值的指標。
放置在 to
引數中的編碼字串的長度,不包括終止的空位元組,如果發生錯誤,則為 -1。
由於 mysql_real_escape_string()
傳回不帶正負號的值,因此您可以將傳回值與 (unsigned long)-1
(或與 (unsigned long)~0
,這兩者相等) 進行比較來檢查 -1。
-
如果啟用
NO_BACKSLASH_ESCAPES
SQL 模式,就會發生此錯誤,因為在這種情況下,無法保證mysql_real_escape_string()
會產生正確編碼的結果。為了避免此錯誤,請改用mysql_real_escape_string_quote()
。