[英]Perl script using DBI module with Oracle 8 stops processing
我在使用連接到Oracle 8的DBI模塊(版本1.601)的Perl腳本時遇到問題。操作系統是FreeBSD 7.0。
該腳本只是打開一個連接,循環通過CSV文件一次一行/一行插入數據,然后關閉連接並退出。 cron作業每30分鍾執行一次處理任何傳入CSV文件的腳本。 有時,腳本會在中途停止處理(沒有插入新數據,不會消耗更多的CPU時間),有必要將其終止。
CSV文件似乎有一個大小閾值。 任何低於35000行的腳本,腳本都會執行並退出。 否則它會停止並且過程處於(看似)休眠/等待狀態。
我只能通過SQL * Plus遠程訪問Oracle8。 檢查了Oracle v $會話表並查看這些停滯進程的連接是否未關閉,因此可能達到某些資源限制? 在FreeBSD上運行'limits'會產生以下結果:
cputime infinity secs
filesize infinity kB
datasize 524288 kB
stacksize 65536 kB
coredumpsize infinity kB
memoryuse infinity kB
memorylocked infinity kB
maxprocesses 5547
openfiles 11095
sbsize infinity bytes
vmemoryuse infinity kB
我不確定如何繼續。 我如何或在哪里可以縮小問題的范圍?
任何幫助表示贊賞。
這是腳本,對某些var名稱進行了更改,省略了輸入檢查代碼:
#!/usr/bin/perl -w
use DBI;
use strict;
my $exitstatus = 0;
my $infile = shift;
open (INFILE, "$infile");
my $dbh = DBI->connect(
'dbi:Oracle:sid=mysid;host=myhostname',
'myusername',
'mypassword',
{
RaiseError => 1,
AutoCommit => 1
}
) or die $DBI::errstr;
while (<INFILE>) {
chomp;
next if (/^#.*$/ || /^$/);
my @columns = split /\t/;
my ($var1, $var2, $var3) = @columns;
eval {
my $oProce = qq{
BEGIN
InsertStoredProc(
field1 => $var1,
field2 => $var2,
field3 => $var3
);
END;
};
$dbh->do( $oProce );
};
if ( $@ ) {
$exitstatus=1;
warn "LINE: @columns\n";
warn "Execution of stored procedure failed: $DBI::errstr\n";
warn "################################################################################\n";
}
}
$dbh->disconnect;
close INFILE;
exit $exitstatus;
不是我認為它相關,但代碼效率很低。 您正在為插入的每一行解析SQL。 為什么不這樣做:
my $sth = $dbh->prepare('BEGIN InsertStoredProc(?,?,?); END;');
while (<INFILE>) {
chomp;
next if (/^#.*$/ || /^$/);
my @columns = split /\t/;
#my ($var1, $var2, $var3) = @columns;
eval {
$sth->execute(@columns);
#my $oProce = qq{
# BEGIN
# InsertStoredProc(
# field1 => $var1,
# field2 => $var2,
# field3 => $var3
# );
# END;
#};
#$dbh->do( $oProce );
};
if ( $@ ) {
$exitstatus=1;
warn "LINE: @columns\n";
warn "Execution of stored procedure failed: $DBI::errstr\n";
warn "################################################################################\n";
}
}
關閉AutoCommit的另一個建議也將加速你的代碼,因為你只會提交每N行而不是每一行。 為什么使用AutoCommit會導致掛起對我沒有意義。
至於如果你可以隨意重現它似乎掛起的點,嘗試使用DBI_TRACE = 15 = x.log運行它並在連接中設置ora_verbose => 6。 掛起時日志文件末尾的內容是什么。
你沒有使用AutoCommit試過嗎? 也許您創建了許多事務,Oracle停止處理更多請求。
嘗試每100行提交一次,當沒有更多數據時。
您可以使用strace -p your_program_pid來查看正在進行的操作,腳本停止的位置。
我希望這會對你有所幫助。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.