#!/usr/local/bin/perl ####################################################################### # This CGI is will provide a "user friendly" interface to a table # inside a database. # # The database name has to be provided. # This script has to be renamed or linked to the same name as the table # is called. # # Yves Dorfsman, Jan 10th 2001 # ####################################################################### use DBI; use CGI; use File::Basename; # Name of the Database this script is going to go against $database = "hardware"; # We use the name of the script for the table name $progname = basename($0); $table = $progname; # Connect to the DB $dbc ||= DBI->connect("dbi:Pg:dbname=$database"); #----------------------------------------------------------- $pg = new CGI; $qname = $pg->param('qname'); print "Content-type: text/html\n\n"; print "\n\n"; # Two options: # 1) qname is not defined, therefore this is a first call, we print an HTML # FORM with ranks, column names, and text field for an SQL WHERE clause. # # 2) qname is a list of the columns name, therefore we have been called # the the FORM (see 1), and we need to execute an SQL statement, and # print its result. if ($qname) # We got called by the html FORM { for (split " ", $qname) { # For each column, we get the rank and text field associated with it. $x = join "", $_, ".", "rank"; $y = join "", $_, ".", "where"; $rank{$_} = $pg->param("$x"); $where{$_} = $pg->param("$y"); } # When was that table updated $sqlprep = "SELECT \"when\" from updated where \"table\" = \'$table\'"; $sql1 = $dbc->prepare($sqlprep); $sql1->execute(); $updated = $sql1->fetchrow_array; # Now deal with what's inside the table # Create the SQL ORDER BY statement, fields are ordered by rank. # At the same time, we start to create a SQL SELECT field for (sort { $rank{$a} <=> $rank{$b} } keys %rank) { # we don't need rank 0 next if ($rank{$_} == 0); ##print "$_   $rank{$_}
\n"; $orderfield = join (" ", "$orderfield", ", ") if ($orderfield); $orderfield = join " ", $orderfield, "\"$_\""; $selectfield = join ("", "$selectfield", ", ") if ($selectfield); $selectfield = join " ", $selectfield, "\"$_\""; $header = join "", $header, "", "$_"; } $orderfield = join (" ", "ORDER BY", $orderfield) if ($orderfield); ##print "$orderfield
\n"; # Now we create the SQL WHERE close (WHERE colname = "textfield") while (($key, $value) = each %where) { # if a textfield is empty, we don't care next if ($value eq ""); $wherefield = join (" ", $wherefield, "AND") if ($wherefield); $wherefield = join " ", $wherefield, "WHERE upper(\"$key\") LIKE upper(\'%$value%\')"; if ($rank{$key} == 0) { # we will print any field that has a rank != 0, or a non empty # textfield. But we have to be carrefull to print it twice (hence the if) $selectfield = join ("", "$selectfield", ", ") if ($selectfield); $selectfield = join " ", $selectfield, "\"$key\""; $header = join "", $header, "", "$key"; } } ##print "$wherefield
\n"; ## print "$selectfield
\n"; # If "allfields" is selected, then we use want to do a "select * form" $allfields = $pg->param('allfields'); if ($allfields eq "on") { for (split " ", $qname) { if ($rank{$_} == 0 && $where{$_} eq "") { $selectfield = join ("", "$selectfield", ", ") if ($selectfield); $selectfield = join (" ", $selectfield, "\"$_\""); $header = join ("", $header, "", $_); } } } # Now we prepare and execute the SQL query $sqlprep = join (" ", "SELECT", $selectfield, "FROM $table", $wherefield, $orderfield, ";"); ## print "$sqlprep


\n"; $sql1 = $dbc->prepare($sqlprep); $sql1->execute(); # We create an HTML table, with the result of the sql statement in it print "

Last updated: $updated

\n"; print "\n"; print "\n"; print "$header"; while (@row = $sql1->fetchrow_array) { print "\n"; foreach $i (0 ... $#row) { $row[$i] = " " if ($row[$i] eq ""); print "
$row[$i]"; } print "\n"; } print "
"; print "\n"; } else { # First time, we create the HTML "FORM" # #---------------------------------------------------------- # Find our the name of the columns in the table # Unfortunately this part is very Postgres specific.... # but then, the same trick can be used with most DBM, so it should be easy # to change this part to accomodate another DBM. # (and yes it is very ugly, but I couldn't come up with anything better) $run = "echo 'select * from $table where 1=2;'"; $run = join "|", $run, "LD_LIBRARY_PATH=/usr/local/pgsql/lib"; $run = join " ", $run, "/usr/local/pgsql/bin/psql $database 2>&1"; $run = join "|", $run, "head -1 2>&1"; $result = `$run`; @raw_col = split /\|/, $result; $nbr_field = 0; for (@raw_col) { s/^\s+//; s/\s+$//; push @columns, $_; $nbr_field++; } # Now print a form with a choice of rank and search pattern for each field. print "Select \"Show all fields\" if you want to see the whole table.
"; print "When you select a rank, the columns will appear in that order, and be ordered using the ranks.
"; print "Any column for which you have selected a rank or some text will appear.
"; print "In the text field, use the SQL \'%\' and \'_\' as opposed to the regex \'*\' and \'?\' for your wildcards.
"; print "
"; print "\n"; print ''; print "\n"; print "\n"; print "\n"; $x = join "", $col, ".", "rank"; $y = join "", $col, ".", "where"; print "
"; print "Show all fields
"; print "
RankColumn nameselect with\n"; foreach $col (@columns) { $qname = join " ", $qname, $col; print "
\n"; print "$col\n"; print "\n"; } # send a variable with the names of all the fields print ""; print "\n"; print "
\n"; print "\n"; }