使用Sqoop从Vertica导入时,“错误:光标”C_2“已存在”

时间:2014-09-01 14:58:11

标签: sqoop vertica

我使用以下命令使用Sqoop从Vertica导入:

sqoop import --driver com.vertica.Driver --connect jdbc:vertica://[host]:[port]/[db] --username [username] --password [pass] -m 1 --table [table]

此操作失败,并显示以下错误:

14/09/01 15:12:21 INFO manager.SqlManager: Using default fetchSize of 1000
14/09/01 15:12:21 INFO tool.CodeGenTool: Beginning code generation
14/09/01 15:12:21 INFO manager.SqlManager: Executing SQL statement: SELECT t.* FROM [table] AS t WHERE 1=0
14/09/01 15:12:21 ERROR manager.SqlManager: Error executing statement: com.vertica.util.PSQLException: ERROR: cursor "C_2" already exists
com.vertica.util.PSQLException: ERROR: cursor "C_2" already exists

我尝试过各种各样的Sqoop选项,并进行了大量的Google搜索,但无法解决为什么我会收到此错误或如何解决此错误。

似乎Vertica对游标有一些限制,如stated here:

  

游标仅向前移动且不可滚动。结果集不能   更新。连接支持在any执行的单个语句   时间。如果要同时执行多个语句,请打开   多个连接。因为HP Vertica没有存储   过程,不支持CallableStatement。该   DatabaseMetaData.getProcedures()和.getProcedureColumns()方法   返回有关SQL函数(包括UDF)的信息而不是   存储过程。

所以我现在最好的猜测是Sqoop用光标打开了多个连接?但话说回来,我只使用一个映射器,所以我不确定是不是这样。

任何人都可以向我提供有关我为何会收到此错误或如何解决此错误的更多信息吗?

是否有其他连接管理器不使用游标?

我将Vertica 5与Vertica JDBC一起使用4. Sqoop 1.4.5。 list-tables工作正常。使用自定义查询导入--query时出现一些错误,所以我认为SQL是正确的。我在export

上收到同样的错误

1 个答案:

答案 0 :(得分:0)

看起来Vertica不支持在JDBC中设置提取大小。因此,在导入时,这将起作用,因为它会禁用提取大小。

sqoop import --driver com.vertica.Driver --connect jdbc:vertica://[host]:[port]/[db] --username [username] --password [pass] -m 1 --table [table] --fetch-size=0

但是,导出仍然不起作用,给出相同的错误。导出没有--fetch-size选项,因此解决此问题的唯一方法是为Sqoop编写Vertica连接管理器。

连接管理器非常简单:

public class VerticaManager extends GenericJdbcManager {

    // driver class to ensure is loaded when making db connection.
    private static final String DRIVER_CLASS = "com.vertica.Driver";

    protected static final int DEFAULT_FETCH_SIZE = 0;

    public VerticaManager(SqoopOptions opts) {
        super(DRIVER_CLASS, opts);
    }

    protected void initOptionDefaults() {
        if (options.getFetchSize() == null) {
            // Vertica JDBC does not support fetch size, so we default to 0
            LOG.info("Using default fetchSize of " + DEFAULT_FETCH_SIZE);
            options.setFetchSize(DEFAULT_FETCH_SIZE);
        }
    }
}

它强制获取大小为0,并为我们设置驱动程序。

因此,在运行sqoop时,我们现在使用:

sqoop [command] --connection-manger com.example.sqoop.manager.VerticaManager ...

有了这个,所有命令似乎都运行良好。