来自Oracle的Sqoop:“Snapshot too Old”

时间:2015-08-21 14:41:20

标签: bigdata sqoop

我正在使用此命令设置从oracle表到hdfs目录的sqoop自动进程:

sqoop-import --connect jdbc:oracle:thin:@redacted.company.com:1234/db --username redacted --password secret123 --num-mappers 1 --table table --target-dir /data/destination/directory/ --as-avrodatafile --compress --compression-codec org.apache.hadoop.io.compress.BZip2Codec

不幸的是,我收到以下错误消息:

Error:java.io.IOException: SQLException in nextKeyValue
    ...
Caused by: java.sql.SQLException: ORA-01555: snapshot too old: rollback segment number 336 with name "_SYSSMU336_879580159$" too small
    at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:447)
    at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:396)
    at oracle.jdbc.driver.T4C8Oall.processError(T4C8Oall.java:951)
    at oracle.jdbc.driver.T4CTTIfun.receive(T4CTTIfun.java:513)
    at oracle.jdbc.driver.T4CTTIfun.doRPC(T4CTTIfun.java:227)
    at oracle.jdbc.driver.T4C8Oall.doOALL(T4C8Oall.java:531)
    at oracle.jdbc.driver.T4CPreparedStatement.doOall8(T4CPreparedStatement.java:208)

我试图实现的业务要求是将整个表导入到我们的hdfs中。由于我们不拥有或管理此数据库,因此我无法控制UNDO表空间和相关参数。该工作计划在凌晨1点运行,这不是一个高峰时间,但由于自动化流程触及它,我不能诱使人们在工作期间停止使用它。

我应该如何修改sqoop-import语句以避免此错误?

2 个答案:

答案 0 :(得分:0)

这不是Sqoop问题。您将直接在Oracle上执行相同的语句时遇到相同的错误。这是一个撤消表空间问题。您必须加快查询速度,或者必须增加Oracle撤消表空间大小。

可能的修复列表:

  • 在数据库活动较少时安排您的任务(甚至可能 让人们停止工作一段时间)。
  • 优化使用此错误失败的查询以读取更少的数据 并减少时间增加UNDO表空间的大小。
  • 增加UNDO_RETENTION参数的大小。
  • 将UNDO表空间设置为GUARANTEE模式。
  • 如果要导出表格,请考虑使用 CONSISTENT =没有参数。
  • 不要在游标循环中提交

此致 Giova

答案 1 :(得分:0)

--num-mappers=10的使用(即增加的并行性)足以在这种情况下克服问题而不会过多地影响源。

此外,添加--direct参数将导致Sqoop使用特定于Oracle的连接器,这将进一步加快速度,并且只要我说服该数据库上的DBA打开它,就会将其添加到我的解决方案中必要的特权。 Direct还支持选项-Doraoop.import.consistent.read={true|false},它似乎在函数中反映了Oracle导出实用程序的CONSISTENT参数(注意,默认为false),因为撤消表空间不会用于尝试保持一致性,无需在撤消表空间完全填满之前竞争导入。