From: Galen Charlton Date: Fri, 20 Mar 2015 21:21:16 +0000 (+0000) Subject: teach Clark Kent how to limit the size of a resultset X-Git-Url: https://old-git.evergreen-ils.org/?a=commitdiff_plain;h=f57776d50ca0cc6419b87ed9a476441be91d7835;p=working%2FEvergreen.git teach Clark Kent how to limit the size of a resultset A report that returns too many rows may consume memory to not good effect. This patch adds a new command-line parameter to Clark Kent, --resultset-limit, to allow report results to be truncated at the specified number of rows. Since the user cannot know how many results the report would have had without the limit, the main purpose of this patch is to reduce the chance that clark-kent.pl will trigger OOM-killer. Signed-off-by: Galen Charlton --- diff --git a/Open-ILS/src/perlmods/lib/OpenILS/Reporter/SQLBuilder.pm b/Open-ILS/src/perlmods/lib/OpenILS/Reporter/SQLBuilder.pm index 940972a33e..3291a4fe73 100644 --- a/Open-ILS/src/perlmods/lib/OpenILS/Reporter/SQLBuilder.pm +++ b/Open-ILS/src/perlmods/lib/OpenILS/Reporter/SQLBuilder.pm @@ -38,6 +38,13 @@ sub relative_time { return $self->builder->{_relative_time}; } +sub resultset_limit { + my $self = shift; + my $limit = shift; + $self->builder->{_resultset_limit} = $limit if (defined $limit); + return self->builder->{_resultset_limit}; +} + sub resolve_param { my $self = shift; my $val = shift; @@ -237,6 +244,8 @@ sub toSQL { if ($self->is_subquery) { $sql = '('; + } elsif ($self->resultset_limit) { + $sql = 'SELECT * FROM ('; } $sql .= "SELECT\t" . join(",\n\t", map { $_->toSQL } @{ $self->{_select} }) . "\n" if (@{ $self->{_select} }); @@ -251,6 +260,9 @@ sub toSQL { if ($self->is_subquery) { $sql .= ') '. $self->{_alias} . "\n"; + } elsif ($self->resultset_limit) { + $sql .= ') limited_to_' . $self->resultset_limit . + '_hits LIMIT ' . $self->resultset_limit . "\n"; } return $self->{_sql} = $sql; diff --git a/Open-ILS/src/reporter/clark-kent.pl b/Open-ILS/src/reporter/clark-kent.pl index 3821011fd8..de8d80679e 100755 --- a/Open-ILS/src/reporter/clark-kent.pl +++ b/Open-ILS/src/reporter/clark-kent.pl @@ -35,12 +35,14 @@ my ($count, $config, $sleep_interval, $lockfile, $daemon) = (1, 'SYSCONFDIR/open # before Clark refuses to try to draw a chart my $max_rows_for_charts = 1000; my $statement_timeout = 10 * 60 * 1000; +my $resultset_limit; GetOptions( "daemon" => \$daemon, "sleep=i" => \$sleep_interval, "concurrency=i" => \$count, "max-rows-for-charts=i" => \$max_rows_for_charts, + "resultset-limit=i" => \$resultset_limit, "statement-timeout=i" => \$statement_timeout, "bootstrap|boostrap=s" => \$config, "lockfile=s" => \$lockfile, @@ -174,6 +176,7 @@ while (my $r = $sth->fetchrow_hashref) { $r->{resultset}->set_pivot_label($report_data->{__pivot_label}) if $report_data->{__pivot_label}; $r->{resultset}->set_pivot_default($report_data->{__pivot_default}) if $report_data->{__pivot_default}; $r->{resultset}->relative_time($r->{run_time}); + $r->{resultset}->resultset_limit($resultset_limit) if $resultset_limit; push @reports, $r; }