mysql 的load data infile

前些日子在開發一個輿情監測系統,需要在一個操作過程中往數據表里插入大量的數據,為了改變以往生硬地逐條數據插入的笨辦法,也為了提高執行效率,決定用load data infile來執行數據插入。

LOAD DATA INFILE語句從一個文本文件中以很高的速度讀入一個表中。如果指定LOCAL關鍵詞,從客戶主機讀文件。如果LOCAL沒指定,文件必須位于服務器上。(LOCAL在mysql3.22.6或以后版本中可用。)

為了安全原因,當讀取位于服務器上的文本文件時,文件必須處于數據庫目錄或可被所有人讀取。另外,為了對服務器上文件使用LOAD DATA INFILE,在服務器主機上你必須有file的權限。

頭一回用load data infile,以為只是把插入語句寫到一個文件里,然后用load data infile把文件傳入數據庫就OK了,于是生成了一個內容類似同n句 insert into table_name (`id`,`name`,`content`) values (1,”a”,”abc”),(2,”b”,”abc”),(3,”c”,”abc”);組成的.sql文件。然后在PHP中執行 LOAD DATA INFILE ‘file_name.sql’ INTO TABLE table_name;發現總是執行出錯,真暈,不知道怎么回事,只好去再詳細地讀一下mysql的應用手冊:

如果你指定一個FIELDS子句,它的每一個子句(TERMINATED BY, [OPTIONALLY] ENCLOSED BY和ESCAPED BY)也是可選的,除了你必須至少指定他們之一。
如果你不指定一個FIELDS子句,缺省值與如果你這樣寫的相同:
FIELDS TERMINATED BY ‘ ‘ ENCLOSED BY ” ESCAPED BY ”
如果你不指定一個LINES子句,缺省值與如果你這樣寫的相同:
LINES TERMINATED BY ‘ ‘
換句話說,缺省值導致讀取輸入時,LOAD DATA INFILE表現如下:
在換行符處尋找行邊界
在定位符處將行分進字段
不要期望字段由任何引號字符封裝
將由“”開頭的定位符、換行符或“”解釋是字段值的部分字面字符

才知道原來我的sql里的內容并不是按照 load data infile的缺省設置來寫的, 例如缺省設置下,每一句插入語句里的字段是由制表符隔開且內容不以任何引號封裝(也就是括起來)的,但我的是由逗號隔開且有雙引號括起來的,難怪會執行出錯。
于是,將sql執行語句寫成mysql_query(‘load data local infile “file_name.sql” into table `table_name` FIELDS TERMINATED BY “,” ENCLOSED BY ‘”‘ ESCAPED BY “” LINES TERMINATED BY ” ” STARTING BY “”‘);
這會算是執行成功了,成功地往指定的數據表里插入了很多條記錄,可是又發現了一個問題,插入的數據亂七八糟的,字段與要插入的內容不符合我的要求,而且有好多是把字段名給插入到字段里面去了,唉,只好再回頭去又讀了一遍mysql中的load data infile用法,終于搞明白了,原來file_name.sql里面只需要按一定格式把內容寫進去就行了,不是把整個sql執行語句都寫進去的,真笨!^_^
于是,把內容換成了
1,”a”,”abc”
2,”b”,”abc”
3,”c”,”abc”
而且內容要與數據表里的字段從數量上和順序上都要嚴格對應
在本地服務器(我用的是WINDOW主機)上測試了一下,OK,操作成功!
然后把程序傳到網絡服務器上(LINUX主機),一執行,提示:
Can’t get stat of ……” (Errcode: 13)
開始還以為是sql文件權限或者是mysql的root用戶權限的問題,后來想不對呀,mysql的root用戶是超級用戶,肯定有權限的,那問題就出在sql文件的權限上,后來把sql的權限改成777,執行操作后還是不行。
網上搜索了一下,有說把文件放在/var/lib/mysql里就行了,一試,果真可以,可是我又不可能在PHP網頁中把sql文件生成放到/var/lib/mysql下,費盡了心思,最后終于在網上搜索到一個解決辦法:

使用LOCAL將比讓服務器直接存取文件慢些,因為文件的內容必須從客戶主機傳送到服務器主機。在另一方面,你不需要file權限裝載本地文件。
你也可以使用mysqlimport實用程序裝載數據文件;它由發送一個LOAD DATA INFILE命令到服務器來運作。 –local選項使得mysqlimport從客戶主機上讀取數據。如果客戶和服務器支持壓縮協議,你能指定–compress在較慢的網絡上獲得更好的性能。

其實辦法簡單得很,那就是把load data infile寫成load data local infile 就OK啦。

? 版權聲明
THE END
喜歡就支持一下吧
點贊5 分享