SQL2008R2 導出表 成dbf文件,網上很多文檔,但是真正能執行生成dbf文件的不多,我整理了一下:

SQL2008R2 導出表 成dbf文件,網上很多文檔,但是真正能執行生成dbf文件的不多,我整理了一下:

前提 

1、--如何啓用OLE Automation Procedures。

sp_configure 'show advanced options', 1;
GO
RECONFIGURE;
GO
sp_configure 'Ole Automation Procedures', 1;
GO
RECONFIGURE;
GO

2、--開啓導入功能
    exec sp_configure 'show advanced options',1
    reconfigure
    exec sp_configure 'Ad Hoc Distributed Queries',1
    reconfigure
    --允許在進程中使用ACE.OLEDB.12
    EXEC master.dbo.sp_MSset_oledb_prop N'Microsoft.ACE.OLEDB.12.0', N'AllowInProcess', 1
    --允許動態參數
    EXEC master.dbo.sp_MSset_oledb_prop N'Microsoft.ACE.OLEDB.12.0', N'DynamicParameters', 1
3、64位安裝 AccessDatabaseEngine_X64

4、啓用xp_cmdshell

sp_configure 'show advanced options',1
reconfigure
go
sp_configure 'xp_cmdshell',1
reconfigure
go

其實還有很多困難需要解決,但是多費費心,多試試;網上的辦法還是有效的。

接下來是用存儲過程實現的,

CREATE PROC p_exporttb22 -- 2016-7-10 17:28:52  
    @tbname sysname ,    --要導出的表名  
    @path NVARCHAR(1000) ,   --文件存放目錄--絕對地址要是服務器上的位置,並且要避開根目錄,數據保存在服務器上。    
    @fname NVARCHAR(250) = '' , --文件名,默認爲表名  
    @over BIT = 0      --是否覆蓋已經存在的文件,如果不覆蓋,則直接追加  
AS  
    DECLARE @err INT ,  
        @src NVARCHAR(255) ,  
        @desc NVARCHAR(255) ,  
        @out INT   
    DECLARE @obj INT ,  
        @constr NVARCHAR(1000) ,  
        @sql VARCHAR(8000) ,  
        @fdlist VARCHAR(8000),
        @fdlistUpper VARCHAR(8000)  --insert dbf文件時 字段要大寫,故提前準備
--參數檢測  
    IF ISNULL(@fname, '') = ''  
        SET @fname = @tbname + '.dbf'   
--檢查文件是否已經存在  
    IF RIGHT(@path, 1) <> '/'  
        SET @path = @path + '/'   
    CREATE TABLE #tb ( a BIT, b BIT, c BIT )   
    SET @sql = @path + @fname   
    INSERT  INTO #tb  
            EXEC master..xp_fileexist @sql   
    IF EXISTS ( SELECT  1  
                FROM    #tb  
                WHERE   a = 1 )  
        IF @over = 1  
            BEGIN   
                SET @sql = 'del ' + @sql   
                EXEC master..xp_cmdshell @sql, no_output   
            END   
        ELSE  
            SET @over = 0   
    ELSE  
        SET @over = 1   
--數據庫創建語句  
    SET @sql = @path + @fname   
    SET @constr = 'Provider=Microsoft.ACE.OLEDB.12.0;Extended Properties="dBASE 5.0;'  
    --如果不是64位系統,就不能用“Microsoft.ACE.OLEDB.12.0”,改爲"Microsoft.Jet.OLEDB.4.0",未測試32的情況,
    --下同。具體細節可以參考:http://www.connectionstrings.com/dbf-foxpro/ 
        + ';HDR=NO;DATABASE=' + @path + '"'   
--連接數據庫  
    EXEC @err= sp_OACreate 'adodb.connection', @obj OUT --sp_OACreate  
    IF @err <> 0  
        GOTO lberr   
    EXEC @err= sp_OAMethod  @obj, 'open', NULL, @constr   
    IF @err <> 0  
        GOTO lberr   
--創建表的SQL   
    SELECT  @sql = '' ,  
            @fdlist = ''   
    SELECT  @fdlist = @fdlist + ',' + a.name ,  
            @sql = @sql + ',[' + a.name + '] '  
            + CASE WHEN b.name IN ( 'char', 'nchar', 'varchar', 'nvarchar' )  
                   THEN 'text(' + CAST(CASE WHEN a.length > 250 THEN 250  
                                            ELSE a.length  
                                       END AS VARCHAR) + ')'  
                   WHEN b.name IN ( 'tynyint', 'int', 'bigint', 'tinyint' )  
                   THEN 'int'  
                   WHEN b.name IN ( 'smalldatetime', 'datetime' )  
                   THEN 'datetime'  
                   WHEN b.name IN ( 'money', 'smallmoney' ) THEN 'money'  
                   ELSE b.name  
              END  
    FROM    syscolumns a  
            LEFT JOIN systypes b ON a.xtype = b.xusertype  
    WHERE   b.name NOT IN ( 'image', 'text', 'uniqueidentifier', 'sql_variant',  
                            'ntext', 'varbinary', 'binary', 'timestamp' )  
            AND OBJECT_ID(@tbname) = id   
    SELECT  @sql = 'create table [' + @fname + '](' + SUBSTRING(@sql, 2, 8000)  
            + ')' ,  
            @fdlist = SUBSTRING(@fdlist, 2, 8000)   
    IF @over = 1  
        BEGIN   
            EXEC @err= sp_OAMethod  @obj, 'execute', @out OUT, @sql   
            IF @err <> 0  
                GOTO lberr   
        END   
    EXEC @err= sp_OADestroy @obj   
    SET @sql = 'openrowset(''Microsoft.ACE.OLEDB.12.0'',''dBase 5.0;DATABASE='  
        + @path + ''',''select * from [' + @fname + ']'')'   
        
     SET @fdlistUpper=UPPER(@fdlist)  --insert dbf文件時 字段要大寫,故提前準備
        
--導入數據  
    --EXEC('insert into '+@sql+'('+@fdlist+' ) select '+@fdlist+' from '+@tbname )   
    EXEC('insert into '+@sql+'('+@fdlistUpper+' ) select '+@fdlist+' from '+@tbname )   
    RETURN   
    lberr:   
    EXEC sp_OAGetErrorInfo  0, @src OUT, @desc OUT   
    lbexit:   
    SELECT  CAST(@err AS VARBINARY(4)) AS 錯誤號 ,  
            @src AS 錯誤源 ,  
            @desc AS 錯誤描述   
    SELECT  @sql ,  
            @constr ,  
            @fdlist   
GO  
  
--使用方法:  
p_exporttb11 @tbname='xtm14',@path='E:\db_BAK',@over=0 

p_exporttb @tbname='xtm14',@path='E:\db_BAK',@over=0   --絕對地址要是服務器上的位置,並且要避開根目錄,數據保存在服務器上。  






補充一點,有的時候執行時 報錯,請大家調試一下存儲過程:

我發現insert dbf文件時 描述字段(不是select 字段)必須都是大寫的,這也許是dbf文件的要求,我不太清楚,但是我改成大寫的後,就不報錯了。否則報錯。




發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章