Perl:多个从CSV插入Oracle DB表

时间:2013-07-25 18:13:40

标签: oracle perl csv sqlplus multiple-insert

我试图在Linux环境中将CSV文件中的大量记录插入到Oracle DB中的表中。插入很简单 - CSV具有需要插入单个列表的ID,以便进一步处理。

以下是我的思路: 1.将文件读入数组 2.遍历数组中的每个项目并将其插入表格

我无法使用SQL * Loader或DBI,对数据库服务器的访问受到限制,我不允许在用于连接数据库的主机上安装任何额外的软件包。所以我需要使用最简单的东西。

以下是有效的作品:

#!/usr/bin/perl
use warnings;
use strict;

my $returnVar;
my $inputfile = $ARGV[0];

# Read file into an array
open(FILE, "<", $inputfile) or die("Unable to open file: $inputfile");
my @idlist = <FILE>;
close(FILE);

#insert array into table
foreach my $id(@idlist)
{
   chomp($id);
   $returnVar = `sqlplus -s cvo/cvo123\@CVOSTAGE\ <<END
        set heading off
                    set echo off
                    set feedback off
                    set pagesize 0
        insert into tmp_tx_id values('$id');
        exit`;
}

这是错误的,因为每次插入记录时都需要打开/关闭连接。我需要插入大量的记录(> 100万),我同意这是一种可怕的方式。我尝试以下列方式修改它,但没有成功:

.
.
<File has been read into the array>

$returnVar1 = `sqlplus -s cvo/cvo123\@CVOSTAGE\ <<END
                      set heading off
                      set echo off
                      set feedback off
                      set pagesize 0`;

foreach my $id(@idlist)
{
    chomp($id);
    $returnVar2 = `insert into tmp_tx_id values(\'$id\');`;
}
system("exit");

显然,在SQL Plus提示符下不执行insert语句 - 它将转到命令shell。这是我得到的错误:

sh: -c: line 0: syntax error near unexpected token `('
sh: -c: line 0: `insert into tmp_tx_id values('664436565');'

有没有办法可以执行多个Insert语句,而不必每次都打开/关闭连接? 任何其他建议(甚至在Perl之外)都非常受欢迎 - 我是一名学习的程序员。

由于

2 个答案:

答案 0 :(得分:1)

你可以将shell的heredoc表示法变为Perl反引号表达式,但考虑将sql命令写入文件的替代方法:

open my $fh, '>', '/tmp/my-inserts.sql';
print $fh "set heading off\n", "set echo off\n", ... ;
foreach my $id(@idlist)
{
    chomp($id);
    print $fh "insert into tmp_tx_id values('$id');";
}
close $fh;

... and then ...

$returnVar1 = `sqlplus -s cvo/cvo123\@CVOSTAGE  < /tmp/my-inserts.sql`;

这有助于简化调试 - 当sqlplus告诉你第4683行出错时,你有一条记录你要在第4683行插入的内容。

您还应该考虑installing modules on your system is not as impossible as it seems,然后将DBI与占位符一起使用,就像其他每个使用数据库的Perl程序员一样。

答案 1 :(得分:0)

您可以使用sql插件准备一个脚本(可能不是整个文件,您可以将其拆分为100K插入块)并直接从命令行使用sqlplus执行它们,如下所示:

sqlplus <user@connect> @inserts.sql

在脚本文件的开头,您可以指定日志文件

spool '<logfile>'

加上你想要的任何选项(set trimspool on对于调整行尾的空格非常有用) 最后:

commit ;
spool off

在perl中准备脚本很容易。