在SSIS中检查Excel文件目标临时表?

时间:2013-05-24 12:10:15

标签: sql ssis

我已经创建了ssis包来从sql表动态生成excel文件。

但是当我尝试在sql任务中使用下面的查询检查是否存在excel连接临时表时,语法错误会失败

IF object_id(MyExcel) is not null

CREATE TABLE `MyExcel` (
    `CUSIP` varchar(50),
    `FaceAmount` decimal(18,4),
    `Portfolio` varchar(50),
    `PositionDate` DateTime,
    `PositionCost` decimal(18,6),
    `CurrentPrice` decimal(18,6)
)

else drop table MyExcel

错误:

[Execute SQL Task] Error: Executing the query "IF object_id(MyExcel) is not null

CREATE TABLE `..." failed with the following error: "Invalid SQL statement; expected 'DELETE', 'INSERT', 'PROCEDURE', 'SELECT', or 'UPDATE'.". Possible failure reasons: Problems with the query, "ResultSet" property not set correctly, parameters not set correctly, or connection not established correctly.

请指教?

我试过回答

IF OBJECT_ID(N'MyExcel') IS NOT NULL
    BEGIN
        DROP TABLE MyExcel;
    END;

CREATE TABLE [MyExcel] 
(
    [CUSIP]         VARCHAR(50),
    [FaceAmount]    DECIMAL(18,4),
    [Portfolio]     VARCHAR(50),
    [PositionDate]  DATETIME,
    [PositionCost]  DECIMAL(18,6),
    [CurrentPrice]  DECIMAL(18,6)
);

但是语句仍然会出现相同的错误

 IF OBJECT_ID(N'MyExcel') IS NOT NULL
        BEGIN
            DROP TABLE MyExcel;
        END;

我在SQL TASK内使用此查询 连接类型为EXCEL enter image description here

3 个答案:

答案 0 :(得分:4)

这似乎是SQL-Server语法(OBJECT_ID('ObjectName'))和MySQL语法(对象名称的反向标记)的组合。我假设您正在连接到SQL-Server数据库,因此您应该使用[]限定对象名称。 e.g。

IF OBJECT_ID(N'MyExcel') IS NOT NULL
    BEGIN
        CREATE TABLE [MyExcel] 
        (
            [CUSIP]         VARCHAR(50),
            [FaceAmount]    DECIMAL(18,4),
            [Portfolio]     VARCHAR(50),
            [PositionDate]  DATETIME,
            [PositionCost]  DECIMAL(18,6),
            [CurrentPrice]  DECIMAL(18,6)
        );
    END;
ELSE
    BEGIN
        DROP TABLE MyExcel;
    END;

但是,我相信你的逻辑是有缺陷的,你的陈述是“如果表存在,创建它,如果不删除它”,所以如果它已经存在你会得到一个错误说该表已经存在,如果它不会那么你会得到一个错误,说你不能放弃它,因为它不存在。你真正想要的是:

IF OBJECT_ID(N'MyExcel') IS NULL
    BEGIN
        CREATE TABLE [MyExcel] 
        ....

但是,这仍然会给你带来一个问题,因为如果表在任务运行之前就存在了,那么它就不会在之后,如果它之前不存在则会创建,这意味着表是否存在任务完成后存在依赖于表之前是否存在。我想你想做点什么:

IF OBJECT_ID(N'MyExcel') IS NULL
    BEGIN
        CREATE TABLE [MyExcel] 
        (
            [CUSIP]         VARCHAR(50),
            [FaceAmount]    DECIMAL(18,4),
            [Portfolio]     VARCHAR(50),
            [PositionDate]  DATETIME,
            [PositionCost]  DECIMAL(18,6),
            [CurrentPrice]  DECIMAL(18,6)
        );
    END;
ELSE
    BEGIN
        TRUNCATE TABLE [MyExcel];
        -- If you don't want to truncate the table and want it with
        -- it's previous data in just remove the entire `else` clause
    END;

或者

IF OBJECT_ID(N'MyExcel') IS NOT NULL
    BEGIN
        DROP TABLE MyExcel;
    END;

CREATE TABLE [MyExcel] 
(
    [CUSIP]         VARCHAR(50),
    [FaceAmount]    DECIMAL(18,4),
    [Portfolio]     VARCHAR(50),
    [PositionDate]  DATETIME,
    [PositionCost]  DECIMAL(18,6),
    [CurrentPrice]  DECIMAL(18,6)
);

即。在任务运行后,您将始终在数据库中有一个名为MyExcel的表,因此您知道当您进入SSIS包中的下一步时它将存在。

<强>附录

据我所知,您不能将IF与excel连接一起使用。有一篇文章here,用于查询excel工作簿中的元数据,以便您可以检查表是否存在。这可能是技术上正确的做法。

通过使用以下SQL Execute SQL Task,我能够创建一个解决方法:

DELETE  
FROM    MyExcel;

然后将另一个Execute SQL Task添加到On Error事件处理程序中以运行:

CREATE TABLE MyExcel 
(
    CUSIP         VARCHAR(50),
    FaceAmount    DECIMAL(18,4),
    Portfolio     VARCHAR(50),
    PositionDate  DATETIME,
    PositionCost  DECIMAL(18,6),
    CurrentPrice  DECIMAL(18,6)
);

因此,如果表不存在,delete语句将抛出一个错误,这将触发create table语句。因此,确保在任务运行后,表MyExcel肯定存在。

这些任务可以颠倒过来,结果将是相同的

答案 1 :(得分:0)

您不使用CREATE TABLE创建excel文件。如果您将excel文件视为数据库,则表格将为..工作表:)。

要创建Excel文件,请使用Excel Connection Manager。您需要将其指向一次模板文件,并在使用正确的表达式设置excel目标后,将创建该文件。如果它已经存在,您只需要重定向错误。

然后使用Execute Sql创建所需结构的表(即工作表)。

答案 2 :(得分:0)

您可以在控制流的末尾添加一个执行SQL任务,以删除包中的Excel表。这将使环境准备好再次处理包。