--- loncom/interface/lonmysql.pm	2004/07/21 21:01:04	1.21
+++ loncom/interface/lonmysql.pm	2005/04/07 06:56:23	1.29
@@ -1,7 +1,7 @@
 # The LearningOnline Network with CAPA
 # MySQL utility functions
 #
-# $Id: lonmysql.pm,v 1.21 2004/07/21 21:01:04 matthew Exp $
+# $Id: lonmysql.pm,v 1.29 2005/04/07 06:56:23 albertel Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -32,23 +32,37 @@ package Apache::lonmysql;
 use strict;
 use DBI;
 use POSIX qw(strftime mktime);
+use Apache::lonnet;
 
 my $mysqluser;
 my $mysqlpassword;
+my $mysqldatabase;
 
 sub set_mysql_user_and_password {
     # If we are running under Apache and LONCAPA, use the LON-CAPA 
     # user and password.  Otherwise...? ? ? ?
-    ($mysqluser,$mysqlpassword) = @_;
+    my ($input_mysqluser,$input_mysqlpassword,$input_mysqldatabase) = @_;
+    if (! defined($mysqldatabase)) {
+        $mysqldatabase = 'loncapa';
+    }
+    if (defined($input_mysqldatabase)) {
+        $mysqldatabase = $input_mysqldatabase;
+    }
     if (! defined($mysqluser) || ! defined($mysqlpassword)) {
         if (! eval 'require Apache::lonnet();') {
             $mysqluser = 'www';
             $mysqlpassword = $Apache::lonnet::perlvar{'lonSqlAccess'};
         } else {
-            $mysqluser = 'fuck';
+            $mysqluser = '';
             $mysqlpassword = '';
         }
     }
+    if (defined($input_mysqluser)) {
+        $mysqluser = $input_mysqluser;
+    } 
+    if (defined($input_mysqlpassword)) {
+        $mysqlpassword = $input_mysqlpassword;
+    }
 }
 
 ######################################################################
@@ -76,7 +90,7 @@ Each table has a numeric ID that is a pa
 The table id is returned by &create_table.  
 If you lose the table id, it is lost forever.
 The table names in MySQL correspond to 
-$ENV{'user.name'}.'_'.$ENV{'user.domain'}.'_'.$table_id.  If the table id 
+$env{'user.name'}.'_'.$env{'user.domain'}.'_'.$table_id.  If the table id 
 is non-numeric, it is assumed to be the full name of a table.  If you pass
 the table id in a form, you MUST ensure that what you send to lonmysql is
 numeric, otherwise you are opening up all the tables in the MySQL database.
@@ -349,7 +363,7 @@ sub connect_to_db {
     if (! defined($mysqluser) || ! defined($mysqlpassword)) {
         &set_mysql_user_and_password();
     }
-    if (! ($dbh = DBI->connect("DBI:mysql:loncapa",$mysqluser,$mysqlpassword,
+    if (! ($dbh = DBI->connect("DBI:mysql:$mysqldatabase",$mysqluser,$mysqlpassword,
                                { RaiseError=>0,PrintError=>0}))) {
         $debugstring = "Unable to connect to loncapa database.";    
         if (! defined($dbh)) {
@@ -556,7 +570,12 @@ sub update_table_info {
     #
     my @info=$sth->fetchrow_array;
     for (my $i=0;$i<= $#info ; $i++) {
-        $Tables{$tablename}->{$tabledesc[$i]}= $info[$i];
+        if ($tabledesc[$i] !~ /^(Create_|Update_|Check_)time$/) {
+            $Tables{$tablename}->{$tabledesc[$i]}= 
+                &unsqltime($info[$i]);
+        } else {
+            $Tables{$tablename}->{$tabledesc[$i]}= $info[$i];
+        }
     }
     #
     # Determine the column order
@@ -580,6 +599,29 @@ sub update_table_info {
     $debugstring = "Retrieved table info for $tablename";
     return 1;
 }
+
+###############################
+
+=pod
+
+=item &table_information()
+
+Inputs: table id
+
+Returns: hash with the table status
+
+=cut
+
+###############################
+sub table_information {
+    my $table_id=shift;
+    if (&update_table_info($table_id)) {
+	return %{$Tables{$table_id}};
+    } else {
+	return ();
+    }
+}
+
 ###############################
 
 =pod
@@ -592,7 +634,7 @@ Returns: array with column order
 
 =cut
 
-
+###############################
 sub col_order {
     my $table_id=shift;
     if (&update_table_info($table_id)) {
@@ -619,7 +661,7 @@ Returns:
 sub create_table {
     return undef if (!defined(&connect_to_db($dbh)));
     my ($table_des)=@_;
-    my $request = &build_table_creation_request($table_des);
+    my ($request,$table_id) = &build_table_creation_request($table_des);
     #
     # Execute the request to create the table
     #############################################
@@ -629,15 +671,6 @@ sub create_table {
             $dbh->errstr();
         return undef;
     }
-    #
-    # Set up the internal bookkeeping
-    #############################################
-    my $table_id;
-    if (exists($table_des->{'id'})) {
-        $table_id = $table_des->{'id'};
-    } else {
-        $table_id = &get_new_table_id();
-    }
     my $tablename = &translate_id($table_id);
     delete($Tables{$tablename}) if (exists($Tables{$tablename}));
     return undef if (! defined(&update_table_info($table_id)));
@@ -770,7 +803,7 @@ sub build_table_creation_request {
         $request.="COMMENT = 'temporary' ";
     } 
     $request .= "TYPE=MYISAM";
-    return $request;
+    return $request,$table_id;
 }
 
 ###############################
@@ -788,7 +821,7 @@ sub get_new_table_id {
     my $newid = 0;
     my @tables = &tables_in_db();
     foreach (@tables) {
-        if (/^$ENV{'user.name'}_$ENV{'user.domain'}_(\d+)$/) {
+        if (/^$env{'user.name'}_$env{'user.domain'}_(\d+)$/) {
             $newid = $1 if ($1 > $newid);
         }
     }
@@ -901,6 +934,58 @@ sub store_row {
     return 1;
 }
 
+
+###############################
+
+=pod
+
+=item &bulk_store_rows()
+
+Inputs: table id, [columns],[[row data1].[row data2],...]
+
+returns undef on error, 1 on success.
+
+=cut
+
+###############################
+sub bulk_store_rows {
+    my ($table_id,$columns,$rows) = @_;
+    # 
+    return undef if (! defined(&connect_to_db()));
+    my $dbh = &get_dbh();
+    return undef if (! defined($dbh));
+    my $table_status = &check_table($table_id);
+    return undef if (! defined($table_status));
+    if (! $table_status) {
+        $errorstring = "table $table_id does not exist.";
+        return undef;
+    }
+    #
+    my $tablename = &translate_id($table_id);
+    #
+    my $request = 'INSERT IGNORE INTO '.$tablename.' ';
+    if (defined($columns) && ref($columns) eq 'ARRAY') {
+        $request .= join(',',@$columns).' ';
+    }
+    if (! defined($rows) || ref($rows) ne 'ARRAY') {
+        $errorstring = "no input rows given.";
+        return undef;
+    }
+    $request .= 'VALUES ';
+    foreach my $row (@$rows) {
+        # avoid doing row stuff here...
+        $request .= '('.join(',',@$row).'),';
+    }
+    $request =~ s/,$//;
+    $dbh->do($request);
+    if ($dbh->err) {
+        $errorstring = 'Attempted '.$/.$request.$/.'Got error '.$dbh->errstr();
+        return undef;
+    }
+    return 1;
+}
+
+
 ###############################
 
 =pod
@@ -1014,7 +1099,7 @@ sub translate_id {
     # id should be a digit.  If it is not a digit we assume the given id
     # is complete and does not need to be translated.
     return $id if ($id =~ /\D/);  
-    return $ENV{'user.name'}.'_'.$ENV{'user.domain'}.'_'.$id;
+    return $env{'user.name'}.'_'.$env{'user.domain'}.'_'.$id;
 }
 
 ###########################################
@@ -1111,7 +1196,22 @@ sub drop_table {
     return 1; # if we got here there was no error, so return a 'true' value
 }
 
+##########################################
+
+=pod
+
+=item fix_table_name 
 
+Fixes a table name so that it will work with MySQL.
+
+=cut
+
+##########################################
+sub fix_table_name {
+    my ($name) = @_;
+    $name =~ s/^(\d+[eE]\d+)/_$1/;
+    return $name;
+}
 
 
 # ---------------------------- convert 'time' format into a datetime sql format