BCP簡介
bcp是SQL Server中負責導入導出數據的一個命令行工具,它是基於DB-Library的,並且能以並行的方式高效地導入導出大批量的數據。bcp可以將數據庫的表或視圖直接導出,也能通過SELECT FROM語句對表或視圖進行過濾后導出。在導入導出數據時,可以使用默認值或是使用一個格式文件將文件中的數據導入到數據庫或將數據庫中的數據導出到文件中
BCP執行方式
- bcp通過控制台命令行執行
- 通過調用SQL Server的一個系統存儲過程xp_cmdshell以SQL語句的方式運行
*注:通過xp_cmdshell方式,需要啟用xp_cmdshell
EXEC sp_configure 'show advanced options', 1
GO
RECONFIGURE
GO
EXEC sp_configure 'xp_cmdshell', 1
GO
RECONFIGURE
GO
BCP的參數說明
bcp共有四個動作可以選擇。
(1) 導入。
這個動作使用in命令完成,后面跟需要導入的文件名。
(2) 導出。
這個動作使用out命令完成,后面跟需要導出的文件名。
(3) 使用SQL語句導出。
這個動作使用queryout命令完成,它跟out類似,只是數據源不是表或視圖名,而是SQL語句。
(4) 導出格式文件。
這個動作使用format命令完成,后而跟格式文件名。
下面介紹一些常用的選項:
-f format_file
format_file表示格式文件名。這個選項依賴於上述的動作,如果使用的是in或out,format_file表示已經存在的格式文件,如果使用的是format則表示是要生成的格式文件。
-x
這個選項要和-f format_file配合使用,以便生成xml格式的格式文件。
-F first_row
指定從被導出表的哪一行導出,或從被導入文件的哪一行導入。
-L last_row
指定被導出表要導到哪一行結束,或從被導入文件導數據時,導到哪一行結束。
-c
使用char類型做為存儲類型,沒有前綴且以"\t"做為字段分割符,以"\n"做為行分割符。
-w
和-c類似,只是當使用Unicode字符集拷貝數據時使用,且以nchar做為存儲類型。
-t field_term
指定字符分割符,默認是"\t"。
-r row_term
指定行分割符,默認是"\n"。
-S server_name[ \instance_name]
指定要連接的SQL Server服務器的實例,如果未指定此選項,bcp連接本機的SQL Server默認實例。如果要連接某台機器上的默認實例,只需要指定機器名即可。
-U login_id
指定連接SQL Sever的用戶名。
-P password
指定連接SQL Server的用戶名密碼。
-T
指定bcp使用信任連接登錄SQL Server。如果未指定-T,必須指定-U和-P。
-k
指定空列使用null值插入,而不是這列的默認值。
**命令格式: bcp {dbtable | query} {in | out | queryout | format} 數據文件
[-m 最大錯誤數] [-f 格式化文件] [-e 錯誤文件]
[-F 首行] [-L 末行] [-b 批大小]
[-n 本機類型] [-c 字符類型] [-w 寬字符類型]
[-N 將非文本保持為本機類型] [-V 文件格式版本] [-q 帶引號的標識符]
[-C 代碼頁說明符] [-t 字段終止符] [-r 行終止符]
[-i 輸入文件] [-o 輸出文件] [-a 數據包大小]
[-S 服務器名稱] [-U 用戶名] [-P 密碼]
[-T 可信連接] [-v 版本] [-R 允許使用區域設置]
[-k 保留空值] [-E 保留標識值]
[-h"加載提示"] [-x 生成xml 格式化文件]
使用bcp導出數據
1. 使用bcp導出整個表或視圖。
--命令行執行使用密碼連接
bcp OEDB.dbo.kqdata out c:\a.txt -c -S "XXX.XXX.XXX.XXX" -U "sa" -P "password"
bcp OEDB.dbo.kqdata out c:\A.txt -c -S"XXX.XXX.XXX.XXX" -T --使用信任連接
--sql語句方式執行
EXEC master..xp_cmdshell 'bcp oedb.dbo.kqdata out c:\a.txt -c -U"sa" -P"password"'
2. 對導出過濾后的結果數據
EXEC master..xp_cmdshell 'bcp "SELECT TOP 1000 * FROM oedb.dbo.kqdata where kqdata<'2016-01-01'" queryout c:\a.txt -c -U"sa" -P"password"'
--取第10條到13條記錄進行導出
EXEC master..xp_cmdshell 'bcp "SELECT TOP 20 * FROM oedb.dbo.kqdata" queryout c:\a.txt -F 10 -L 13 -c -U"sa" -P"password"'
--導出成csv
Exec master..xp_cmdshell 'bcp "oedb.dbo.kqdata" out "c:\a.csv" -c -t"," -r"\n" -T'
3.使用bcp導出格式文件
bcp不僅可以根據表、視圖導入導出數據,還可以配合格式文件對導入導出數據進行限制。格式文件以純文本文件形式存在,分為一般格式和xml格式。用戶可以手工編寫格式文件,也可以通過bcp命令根據表、視圖自動生成格式文件
EXEC master..xp_cmdshell 'bcp "ltk.dbo.t480" format nul -f "C:\From\format.xml" -x -c -t -S "127.0.0.1" -U "xxx" -P "yyyy"'
--上述命令將t480表的結構生成了一個格式文件format.xml
注意之處:
a.命令與下面都可成功導出數據格式文件;請注意-f 、-S、-U、-P后有無空格都是一樣的
EXEC master..xp_cmdshell 'bcp "ltk.dbo.t480" format nul -f"C:\From\format2.xml" -x -c -t -S"127.0.0.1" -U"sa" -P"yyyy"'
b.命令不可以換行,換行將導致輸出失敗,且沒有提示,例如下面
EXEC master..xp_cmdshell 'bcp "ltk.dbo.t480" format nul -f"C:\From\format2.xml"
-x -c -t -S"127.0.0.1" -U"xx" -P"yy"'
c.若是使用sql語句試圖生成格式文件,則導致失敗,例如:
EXEC master..xp_cmdshell 'bcp "select TraySerial,LotBarcode,Judgement,Cell,MachineID,OperatorID,DataTime from ltk.dbo.t480" format nul -f"C:\From\format2.xml" -x -c -t -S"127.0.0.1" -U"sa" -P"yyyy"'
d.所生成的格式文件,不僅可以用於bcp導入,也可應用於bulk導入
4.使用bcp導入數據
bcp可以通過in命令將上面所導出的a.txt再重新導入到數據庫中
將數據導入到kqdata表中
EXEC master..xp_cmdshell 'bcp ohr.dbo.kqdata in c:\a.txt -c -T'
導入數據也同樣可以使用-F和-L選項來選擇導入數據的記錄行。
EXEC master..xp_cmdshell 'bcp ohr.dbo.kqdata in c:\a.txt -c -F 10 -L 13 -T'
在導入數據時可以根據已經存在的格式文件將滿足條件的記錄導入到數據庫中,不滿足則不導入。
使用普通的格式文件
EXEC master..xp_cmdshell 'bcp ohr.dbo.kqdata in c:\a.txt -F 10 -L 13 -c -f c:\a_format.fmt -T'
使用xml格式的格式文件
EXEC master..xp_cmdshell 'bcp ohr.dbo.kqdata in c:\a.txt -F 10 -L 13 -c -x -f c:\a_format2.fmt -T'
導入csv格式文件
Exec master..xp_cmdshell 'bcp "ohr.dbo.kqdata" in "c:\a.csv" -c -t"," -r"\n" -T'
導入文件示例:
導入文本數據樣本如下
TraySerial,LotBarcode,Judgement,Cell,MachineID,OperatorID,DataTime
0004175,00615027A9N27D32BD0S,1,00,07,5105420648,2005/01/21 02:30:38
0003972,00615027A9N27D32BD0S,1,00,07,5105420648,2005/01/21 02:30:44
0001152,00615027A9N27D32BD0S,1,00,07,5105420648,2005/01/21 02:30:49
0004503,00615027A9N27D32BD0S,1,00,07,5105420648,2005/01/21 02:30:51
分析:數據字段使用“,”分隔符,行位是默認,所以應使用命令 -c -t","
Exec master..xp_cmdshell 'bcp "LTK.dbo.t490" in C:\From\data.txt -f C:\From\format.xml -c -t"," -S "." -U "sa" -P "password"'
常見錯誤:
錯誤1:Error = [Microsoft][SQL Server Native Client 10.0]String data, right truncation
原因:數據類型不一致導致,檢查數據文件是否首行是列頭,數據應該從數據文件的第二行開始,即命令中增加 -F 2
錯誤2:
NULL
Starting copy...
NULL
0 rows copied.
Network packet size (bytes): 4096
Clock Time (ms.) Total : 1
NULL
原因:數據格式存在問題,可嘗試先從數據庫導出數據,然后再導入,測試成功后回頭再比對兩份文件的差異;