CWIS Developer Documentation
Axis--Database.php
Go to the documentation of this file.
1 <?PHP
2 
3 #
4 # Axis--Database.php
5 # A Simple SQL Database Abstraction Object
6 #
7 # Copyright 1999-2002 Axis Data
8 # This code is free software that can be used or redistributed under the
9 # terms of Version 2 of the GNU General Public License, as published by the
10 # Free Software Foundation (http://www.fsf.org).
11 #
12 # Author: Edward Almasy (almasy@axisdata.com)
13 #
14 # Part of the AxisPHP library v1.2.5
15 # For more information see http://www.axisdata.com/AxisPHP/
16 #
17 
22 class Database {
23 
24  # ---- PUBLIC INTERFACE --------------------------------------------------
25  /*@(*/
27 
40  function Database(
41  $UserName = NULL, $Password = NULL, $DatabaseName = NULL, $HostName = NULL)
42  {
43  # save DB access parameter values
44  $this->DBUserName = $UserName ? $UserName : self::$GlobalDBUserName;
45  $this->DBPassword = $Password ? $Password : self::$GlobalDBPassword;
46  $this->DBHostName = $HostName ? $HostName :
47  (isset(self::$GlobalDBHostName) ? self::$GlobalDBHostName
48  : "localhost");
49  $this->DBName = $DatabaseName ? $DatabaseName : self::$GlobalDBName;
50 
51  # if we don't already have a connection or DB access parameters were supplied
52  $HandleIndex = $this->DBHostName.":".$this->DBName;
53  if (!array_key_exists($HandleIndex, self::$ConnectionHandles)
54  || $UserName || $Password || $DatabaseName || $HostName)
55  {
56  # open connection to DB server
57  self::$ConnectionHandles[$HandleIndex] = mysql_connect(
58  $this->DBHostName, $this->DBUserName,
59  $this->DBPassword, TRUE)
60  or die("Could not connect to database: ".mysql_error());
61 
62  # set local connection handle
63  $this->Handle = self::$ConnectionHandles[$HandleIndex];
64 
65  # select DB
66  mysql_select_db($this->DBName, $this->Handle)
67  or die(mysql_error($this->Handle));
68  }
69  else
70  {
71  # set local connection handle
72  $this->Handle = self::$ConnectionHandles[$HandleIndex];
73  }
74  }
75 
80  function __sleep()
81  {
82  return array("DBUserName", "DBPassword", "DBHostName", "DBName");
83  }
87  function __wakeup()
88  {
89  # open connection to DB server
90  $this->Handle = mysql_connect(
91  $this->DBHostName, $this->DBUserName, $this->DBPassword)
92  or die("could not connect to database");
93 
94  # select DB
95  mysql_select_db($this->DBName, $this->Handle)
96  or die(mysql_error($this->Handle));
97  }
107  static function SetGlobalServerInfo($UserName, $Password, $HostName = "localhost")
108  {
109  # save default DB access parameters
110  self::$GlobalDBUserName = $UserName;
111  self::$GlobalDBPassword = $Password;
112  self::$GlobalDBHostName = $HostName;
113 
114  # clear any existing DB connection handles
115  self::$ConnectionHandles = array();
116  }
117 
122  static function SetGlobalDatabaseName($DatabaseName)
123  {
124  # save new default DB name
125  self::$GlobalDBName = $DatabaseName;
126 
127  # clear any existing DB connection handles
128  self::$ConnectionHandles = array();
129  }
130 
135  function SetDefaultStorageEngine($Engine)
136  {
137  # choose config variable to use based on server version number
138  $ConfigVar = version_compare($this->GetServerVersion(), "5.5", "<")
139  ? "storage_engine" : "default_storage_engine";
140 
141  # set storage engine in database
142  $this->Query("SET ".$ConfigVar." = ".$Engine);
143  }
144 
149  function GetServerVersion()
150  {
151  # retrieve version string
152  $Version = $this->Query("SELECT VERSION() AS ServerVer", "ServerVer");
153 
154  # strip off any build/config suffix
155  $Pieces = explode("-", $Version);
156  $Version = array_shift($Pieces);
157 
158  # return version number to caller
159  return $Version;
160  }
161 
167  function DBHostName() { return $this->DBHostName; }
168 
174  function DBName() { return $this->DBName; }
175 
181  function DBUserName() { return $this->DBUserName; }
182 
190  static function Caching($NewSetting = NULL)
191  {
192  # if cache setting has changed
193  if (($NewSetting !== NULL) && ($NewSetting != self::$CachingFlag))
194  {
195  # save new setting
196  self::$CachingFlag = $NewSetting;
197 
198  # clear any existing cached results
199  self::$QueryResultCache = array();
200  }
201 
202  # return current setting to caller
203  return self::$CachingFlag;
204  }
205 
216  static function AdvancedCaching($NewSetting = NULL)
217  {
218  if ($NewSetting !== NULL)
219  {
220  self::$AdvancedCachingFlag = $NewSetting;
221  }
222  return self::$AdvancedCachingFlag;
223  }
224 
239  function SetQueryErrorsToIgnore($ErrorsToIgnore)
240  {
241  $this->ErrorsToIgnore = $ErrorsToIgnore;
242  }
243 
244  /*@)*/ /* Setup/Initialization */ /*@(*/
246 
254  function Query($QueryString, $FieldName = "")
255  {
256  # if caching is enabled
257  if (self::$CachingFlag)
258  {
259  # if SQL statement is read-only
260  if ($this->IsReadOnlyStatement($QueryString))
261  {
262  # if we have statement in cache
263  if (isset(self::$QueryResultCache[$QueryString]["NumRows"]))
264  {
265  if (self::$QueryDebugOutputFlag)
266  { print("DB-C: $QueryString<br>\n"); }
267 
268  # make sure query result looks okay
269  $this->QueryHandle = TRUE;
270 
271  # increment cache hit counter
272  self::$CachedQueryCounter++;
273 
274  # make local copy of results
275  $this->QueryResults = self::$QueryResultCache[$QueryString];
276  $this->NumRows = self::$QueryResultCache[$QueryString]["NumRows"];
277 
278  # set flag to indicate that results should be retrieved from cache
279  $this->GetResultsFromCache = TRUE;
280  }
281  else
282  {
283  # execute SQL statement
284  $this->QueryHandle = $this->RunQuery($QueryString);
285  if (!is_resource($this->QueryHandle)) { return FALSE; }
286 
287  # save number of rows in result
288  $this->NumRows = mysql_num_rows($this->QueryHandle);
289 
290  # if too many rows to cache
291  if ($this->NumRows >= 50)
292  {
293  # set flag to indicate that query results should not
294  # be retrieved from cache
295  $this->GetResultsFromCache = FALSE;
296  }
297  else
298  {
299  # if advanced caching is enabled
300  if (self::$AdvancedCachingFlag)
301  {
302  # save tables accessed by query
303  self::$QueryResultCache[$QueryString]["TablesAccessed"] =
304  $this->TablesAccessed($QueryString);
305  }
306 
307  # if rows found
308  if ($this->NumRows > 0)
309  {
310  # load query results
311  for ($Row = 0; $Row < $this->NumRows; $Row++)
312  {
313  $this->QueryResults[$Row] =
314  mysql_fetch_assoc($this->QueryHandle);
315  }
316 
317  # cache query results
318  self::$QueryResultCache[$QueryString] = $this->QueryResults;
319  }
320  else
321  {
322  # clear local query results
323  unset($this->QueryResults);
324  }
325 
326  # cache number of rows
327  self::$QueryResultCache[$QueryString]["NumRows"] = $this->NumRows;
328 
329  # set flag to indicate that query results should be retrieved from cache
330  $this->GetResultsFromCache = TRUE;
331  }
332  }
333  }
334  else
335  {
336  # if advanced caching is enabled
337  if (self::$AdvancedCachingFlag)
338  {
339  # if table modified by statement is known
340  $TableModified = $this->TableModified($QueryString);
341  if ($TableModified)
342  {
343  # for each cached query
344  foreach (self::$QueryResultCache
345  as $CachedQueryString => $CachedQueryResult)
346  {
347  # if we know what tables were accessed
348  if ($CachedQueryResult["TablesAccessed"])
349  {
350  # if tables accessed include the one we may modify
351  if (in_array($TableModified, $CachedQueryResult["TablesAccessed"]))
352  {
353  # clear cached query results
354  unset($GLOBALS["APDBQueryResultCache"][$CachedQueryString]);
355  }
356  }
357  else
358  {
359  # clear cached query results
360  unset($GLOBALS["APDBQueryResultCache"][$CachedQueryString]);
361  }
362  }
363  }
364  else
365  {
366  # clear entire query result cache
367  self::$QueryResultCache = array();
368  }
369  }
370  else
371  {
372  # clear entire query result cache
373  self::$QueryResultCache = array();
374  }
375 
376  # execute SQL statement
377  $this->QueryHandle = $this->RunQuery($QueryString);
378  if ($this->QueryHandle === FALSE) { return FALSE; }
379 
380  # set flag to indicate that query results should not be retrieved from cache
381  $this->GetResultsFromCache = FALSE;
382  }
383 
384  # reset row counter
385  $this->RowCounter = 0;
386 
387  # increment query counter
388  self::$QueryCounter++;
389  }
390  else
391  {
392  # execute SQL statement
393  $this->QueryHandle = $this->RunQuery($QueryString);
394  if ($this->QueryHandle === FALSE) { return FALSE; }
395  }
396 
397  if (($FieldName != "") && ($this->QueryHandle != FALSE))
398  {
399  return $this->FetchField($FieldName);
400  }
401  else
402  {
403  return $this->QueryHandle;
404  }
405  }
406 
419  function ExecuteQueriesFromFile($FileName)
420  {
421  # open file
422  $FHandle = fopen($FileName, "r");
423 
424  # if file open succeeded
425  if ($FHandle !== FALSE)
426  {
427  # while lines left in file
428  $Query = "";
429  $QueryCount = 0;
430  while (!feof($FHandle))
431  {
432  # read in line from file
433  $Line = fgets($FHandle, 32767);
434 
435  # trim whitespace from line
436  $Line = trim($Line);
437 
438  # if line is not empty and not a comment
439  if (!preg_match("/^#/", $Line)
440  && !preg_match("/^--/", $Line)
441  && strlen($Line))
442  {
443  # add line to current query
444  $Query .= " ".$Line;
445 
446  # if line completes a query
447  if (preg_match("/;$/", $Line))
448  {
449  # run query
450  $QueryCount++;
451  $Result = $this->Query($Query);
452  $Query = "";
453 
454  # if query resulted in an error that is not ignorable
455  if ($Result === FALSE)
456  {
457  # stop processing queries and set error code
458  $QueryCount = NULL;
459  break;
460  }
461  }
462  }
463  }
464 
465  # close file
466  fclose($FHandle);
467  }
468 
469  # return number of executed queries to caller
470  return $QueryCount;
471  }
472 
478  function QueryErrMsg()
479  {
480  return $this->ErrMsg;
481  }
482 
488  function QueryErrNo()
489  {
490  return $this->ErrNo;
491  }
492 
499  static function DisplayQueryErrors($NewValue = NULL)
500  {
501  if ($NewValue !== NULL) { self::$DisplayErrors = $NewValue; }
502  return self::$DisplayErrors;
503  }
504 
509  function NumRowsSelected()
510  {
511  # if caching is enabled and query was cached
512  if (self::$CachingFlag && $this->GetResultsFromCache)
513  {
514  # return cached number of rows to caller
515  return $this->NumRows;
516  }
517  else
518  {
519  # call to this method after an unsuccessful query
520  if (!is_resource($this->QueryHandle))
521  {
522  return 0;
523  }
524 
525  # retrieve number of rows and return to caller
526  return mysql_num_rows($this->QueryHandle);
527  }
528  }
529 
535  function FetchRow()
536  {
537  # if caching is enabled and query was cached
538  if (self::$CachingFlag && $this->GetResultsFromCache)
539  {
540  # if rows left to return
541  if ($this->RowCounter < $this->NumRows)
542  {
543  # retrieve row from cache
544  $Result = $this->QueryResults[$this->RowCounter];
545 
546  # increment row counter
547  $this->RowCounter++;
548  }
549  else
550  {
551  # return nothing
552  $Result = FALSE;
553  }
554  }
555  else
556  {
557  # call to this method after successful query
558  if (is_resource($this->QueryHandle))
559  {
560  $Result = mysql_fetch_assoc($this->QueryHandle);
561  }
562 
563  # call to this method after unsuccessful query
564  else
565  {
566  $Result = FALSE;
567  }
568  }
569 
570  # return row to caller
571  return $Result;
572  }
573 
580  function FetchRows($NumberOfRows = NULL)
581  {
582  # assume no rows will be returned
583  $Result = array();
584 
585  # for each available row
586  $RowsFetched = 0;
587  while ((($RowsFetched < $NumberOfRows) || ($NumberOfRows == NULL))
588  && ($Row = $this->FetchRow()))
589  {
590  # add row to results
591  $Result[] = $Row;
592  $RowsFetched++;
593  }
594 
595  # return array of rows to caller
596  return $Result;
597  }
598 
615  function FetchColumn($FieldName, $IndexFieldName = NULL)
616  {
617  $Array = array();
618  while ($Record = $this->FetchRow())
619  {
620  if ($IndexFieldName != NULL)
621  {
622  $Array[$Record[$IndexFieldName]] = $Record[$FieldName];
623  }
624  else
625  {
626  $Array[] = $Record[$FieldName];
627  }
628  }
629  return $Array;
630  }
631 
640  function FetchField($FieldName)
641  {
642  $Record = $this->FetchRow();
643  return isset($Record[$FieldName]) ? $Record[$FieldName] : NULL;
644  }
645 
652  function LastInsertId()
653  {
654  return (int)$this->Query(
655  "SELECT LAST_INSERT_ID() AS InsertId",
656  "InsertId");
657  }
658 
673  function UpdateValue(
674  $TableName, $FieldName, $NewValue, $Condition, &$CachedRecord)
675  {
676  # expand condition if supplied
677  if ($Condition != NULL) { $Condition = " WHERE ".$Condition; }
678 
679  # read cached record from database if not already loaded
680  if (!isset($CachedRecord))
681  {
682  $this->Query("SELECT * FROM `".$TableName."` ".$Condition);
683  $CachedRecord = $this->FetchRow();
684  }
685 
686  # if new value supplied
687  if ($NewValue !== DB_NOVALUE)
688  {
689  # update value in database
690  $this->Query("UPDATE `".$TableName."` SET `".$FieldName."` = "
691  .(($NewValue === NULL) ? "NULL" : "'"
692  .mysql_real_escape_string($NewValue)."'")
693  .$Condition);
694 
695  # update value in cached record
696  $CachedRecord[$FieldName] = $NewValue;
697  }
698 
699  # return value from cached record to caller
700  return isset($CachedRecord[$FieldName])
701  ? $CachedRecord[$FieldName] : NULL;
702  }
703 
720  function UpdateIntValue(
721  $TableName, $FieldName, $NewValue, $Condition, &$CachedRecord)
722  {
723  return $this->UpdateValue($TableName, $FieldName,
724  (($NewValue === DB_NOVALUE) ? DB_NOVALUE : (int)$NewValue),
725  $Condition, $CachedRecord);
726  }
727 
745  $TableName, $FieldName, $NewValue, $Condition, &$CachedRecord)
746  {
747  return $this->UpdateValue($TableName, $FieldName,
748  (($NewValue === DB_NOVALUE) ? DB_NOVALUE : (float)$NewValue),
749  $Condition, $CachedRecord);
750  }
751 
752  /*@)*/ /* Data Manipulation */ /*@(*/
754 
761  function LogComment($String)
762  {
763  $this->Query("-- ".$String);
764  }
765 
772  function FieldExists($TableName, $FieldName)
773  {
774  $this->Query("DESC ".$TableName);
775  while ($CurrentFieldName = $this->FetchField("Field"))
776  {
777  if ($CurrentFieldName == $FieldName) { return TRUE; }
778  }
779  return FALSE;
780  }
781 
788  function GetFieldType($TableName, $FieldName)
789  {
790  $this->Query("DESC ".$TableName);
791  return $this->FetchField("Type");
792  }
793 
799  static function QueryDebugOutput($NewSetting)
800  {
801  self::$QueryDebugOutputFlag = $NewSetting;
802  }
803 
809  static function NumQueries()
810  {
811  return self::$QueryCounter;
812  }
813 
820  static function NumCacheHits()
821  {
822  return self::$CachedQueryCounter;
823  }
824 
830  static function CacheHitRate()
831  {
832  if (self::$QueryCounter)
833  {
834  return (self::$CachedQueryCounter / self::$QueryCounter) * 100;
835  }
836  else
837  {
838  return 0;
839  }
840  }
841 
842  /*@)*/ /* Miscellaneous */
843 
844  # ---- PRIVATE INTERFACE -------------------------------------------------
845 
846  protected $DBUserName;
847  protected $DBPassword;
848  protected $DBHostName;
849  protected $DBName;
850 
851  private $Handle;
852  private $QueryHandle;
853  private $QueryResults;
854  private $RowCounter;
855  private $NumRows;
856  private $GetResultsFromCache;
857  private $ErrorsToIgnore = NULL;
858  private $ErrMsg = NULL;
859  private $ErrNo = NULL;
860 
861  private static $DisplayErrors = FALSE;
862 
863  private static $GlobalDBUserName;
864  private static $GlobalDBPassword;
865  private static $GlobalDBHostName;
866  private static $GlobalDBName;
867 
868  # debug output flag
869  private static $QueryDebugOutputFlag = FALSE;
870  # flag for whether caching is turned on
871  private static $CachingFlag = TRUE;
872  # query result advanced caching flag
873  private static $AdvancedCachingFlag = FALSE;
874  # global cache for query results
875  private static $QueryResultCache = array();
876  # stats counters
877  private static $QueryCounter = 0;
878  private static $CachedQueryCounter = 0;
879  # database connection link handles
880  private static $ConnectionHandles = array();
881 
887  private function IsReadOnlyStatement($QueryString)
888  {
889  return preg_match("/^[ ]*SELECT /i", $QueryString) ? TRUE : FALSE;
890  }
891 
898  private function TableModified($QueryString)
899  {
900  # assume we're not going to be able to determine table
901  $TableName = FALSE;
902 
903  # split query into pieces
904  $QueryString = trim($QueryString);
905  $Words = preg_split("/\s+/", $QueryString);
906 
907  # if INSERT statement
908  $WordIndex = 1;
909  if (strtoupper($Words[0]) == "INSERT")
910  {
911  # skip over modifying keywords
912  while ((strtoupper($Words[$WordIndex]) == "LOW_PRIORITY")
913  || (strtoupper($Words[$WordIndex]) == "DELAYED")
914  || (strtoupper($Words[$WordIndex]) == "IGNORE")
915  || (strtoupper($Words[$WordIndex]) == "INTO"))
916  {
917  $WordIndex++;
918  }
919 
920  # next word is table name
921  $TableName = $Words[$WordIndex];
922  }
923  # else if UPDATE statement
924  elseif (strtoupper($Words[0]) == "UPDATE")
925  {
926  # skip over modifying keywords
927  while ((strtoupper($Words[$WordIndex]) == "LOW_PRIORITY")
928  || (strtoupper($Words[$WordIndex]) == "IGNORE"))
929  {
930  $WordIndex++;
931  }
932 
933  # if word following next word is SET
934  if (strtoupper($Words[$WordIndex + 1]) == "SET")
935  {
936  # next word is table name
937  $TableName = $Words[$WordIndex];
938  }
939  }
940  # else if DELETE statement
941  elseif (strtoupper($Words[0]) == "DELETE")
942  {
943  # skip over modifying keywords
944  while ((strtoupper($Words[$WordIndex]) == "LOW_PRIORITY")
945  || (strtoupper($Words[$WordIndex]) == "IGNORE")
946  || (strtoupper($Words[$WordIndex]) == "QUICK"))
947  {
948  $WordIndex++;
949  }
950 
951  # if next term is FROM
952  if (strtoupper($Words[$WordIndex]) == "FROM")
953  {
954  # next word is table name
955  $WordIndex++;
956  $TableName = $Words[$WordIndex];
957  }
958  }
959 
960  # discard table name if it looks at all suspicious
961  if ($TableName)
962  {
963  if (!preg_match("/[a-zA-Z0-9]+/", $TableName))
964  {
965  $TableName = FALSE;
966  }
967  }
968 
969  # return table name (or lack thereof) to caller
970  return $TableName;
971  }
972 
979  private function TablesAccessed($QueryString)
980  {
981  # assume we're not going to be able to determine tables
982  $TableNames = FALSE;
983 
984  # split query into pieces
985  $QueryString = trim($QueryString);
986  $Words = preg_split("/\s+/", $QueryString);
987  $UQueryString = strtoupper($QueryString);
988  $UWords = preg_split("/\s+/", $UQueryString);
989 
990  # if SELECT statement
991  if ($UWords[0] == "SELECT")
992  {
993  # keep going until we hit FROM or last word
994  $WordIndex = 1;
995  while (($UWords[$WordIndex] != "FROM")
996  && strlen($UWords[$WordIndex]))
997  {
998  $WordIndex++;
999  }
1000 
1001  # if we hit FROM
1002  if ($UWords[$WordIndex] == "FROM")
1003  {
1004  # for each word after FROM
1005  $WordIndex++;
1006  while (strlen($UWords[$WordIndex]))
1007  {
1008  # if current word ends with comma
1009  if (preg_match("/,$/", $Words[$WordIndex]))
1010  {
1011  # strip off comma and add word to table name list
1012  $TableNames[] = substr($Words[$WordIndex], 0, -1);
1013  }
1014  else
1015  {
1016  # add word to table name list
1017  $TableNames[] = $Words[$WordIndex];
1018 
1019  # if next word is not comma
1020  $WordIndex++;
1021  if ($Words[$WordIndex] != ",")
1022  {
1023  # if word begins with comma
1024  if (preg_match("/^,/", $Words[$WordIndex]))
1025  {
1026  # strip off comma (NOTE: modifies $Words array!)
1027  $Words[$WordIndex] = substr($Words[$WordIndex], 1);
1028 
1029  # decrement index so we start with this word next pass
1030  $WordIndex--;
1031  }
1032  else
1033  {
1034  # stop scanning words (non-basic JOINs not yet handled)
1035  break;
1036  }
1037  }
1038  }
1039 
1040  # move to next word
1041  $WordIndex++;
1042  }
1043  }
1044  }
1045 
1046  # discard table names if they look at all suspicious
1047  if ($TableNames)
1048  {
1049  foreach ($TableNames as $Name)
1050  {
1051  if (!preg_match("/^[a-zA-Z0-9]+$/", $Name))
1052  {
1053  $TableNames = FALSE;
1054  break;
1055  }
1056  }
1057  }
1058 
1059  # return table name (or lack thereof) to caller
1060  return $TableNames;
1061  }
1062 
1069  private function RunQuery($QueryString)
1070  {
1071  if (self::$QueryDebugOutputFlag) { $QueryStartTime = microtime(TRUE); }
1072  $this->QueryHandle = mysql_query($QueryString, $this->Handle);
1073  if (self::$QueryDebugOutputFlag)
1074  {
1075  print "DB: ".$QueryString." ["
1076  .sprintf("%.2f", microtime(TRUE) - $QueryStartTime)
1077  ."s]"."<br>\n";
1078  }
1079  if (($this->QueryHandle === FALSE) && $this->ErrorsToIgnore)
1080  {
1081  foreach ($this->ErrorsToIgnore as $SqlPattern => $ErrMsgPattern)
1082  {
1083  if (preg_match($SqlPattern, $QueryString)
1084  && preg_match($ErrMsgPattern, mysql_error($this->Handle)))
1085  {
1086  $this->QueryHandle = TRUE;
1087  break;
1088  }
1089  }
1090  }
1091 
1092  if ($this->QueryHandle === FALSE)
1093  {
1094  $this->ErrMsg = mysql_error($this->Handle);
1095  $this->ErrNo = mysql_errno($this->Handle);
1096  $this->NumRows = 0;
1097  if (self::$DisplayErrors)
1098  {
1099  print("<b>SQL Error:</b> <i>".$this->ErrMsg
1100  ."</i> (".$this->ErrNo.")<br/>\n");
1101  print("<b>SQL Statement:</b> <i>"
1102  .htmlspecialchars($QueryString)."</i><br/>\n");
1103  $Trace = debug_backtrace();
1104  array_shift($Trace);
1105  $LocString = "";
1106  $OurFile = __FILE__;
1107  $PrefixLen = 9999;
1108  foreach ($Trace as $Loc)
1109  {
1110  $Index = 0;
1111  while ($Loc["file"][$Index] == $OurFile[$Index]) { $Index++; }
1112  $PrefixLen = min($PrefixLen, $Index);
1113  }
1114  foreach ($Trace as $Loc)
1115  {
1116  $Sep = "";
1117  $ArgString = "";
1118  foreach ($Loc["args"] as $Arg)
1119  {
1120  $ArgString .= $Sep;
1121  switch (gettype($Arg))
1122  {
1123  case "boolean":
1124  $ArgString .= $Arg ? "TRUE" : "FALSE";
1125  break;
1126 
1127  case "integer":
1128  case "double":
1129  $ArgString .= $Arg;
1130  break;
1131 
1132  case "string":
1133  $ArgString .= '"<i>'.htmlspecialchars(substr($Arg, 0, 40))
1134  .((strlen($Arg) > 40) ? "..." : "").'</i>"';
1135  break;
1136 
1137  case "array":
1138  case "resource":
1139  case "NULL":
1140  $ArgString .= strtoupper(gettype($Arg));
1141  break;
1142 
1143  case "object":
1144  $ArgString .= get_class($Arg);
1145  break;
1146 
1147  case "unknown type":
1148  $ArgString .= "UNKNOWN";
1149  break;
1150  }
1151  $Sep = ",";
1152  }
1153  $Loc["file"] = substr($Loc["file"], $PrefixLen);
1154  $LocString .= "&nbsp;&nbsp;";
1155  if (array_key_exists("class", $Loc))
1156  { $LocString .= $Loc["class"]."::"; }
1157  $LocString .= $Loc["function"]."(".$ArgString.")"
1158  ." - ".$Loc["file"].":".$Loc["line"]
1159  ."<br>\n";
1160  }
1161  print("<b>Trace:</b><br>\n".$LocString);
1162  }
1163  }
1164  return $this->QueryHandle;
1165  }
1166 }
1167 
1168 # define return values (numerical values correspond to MySQL error codes)
1169 define("DB_OKAY", 0);
1170 define("DB_ERROR", 1);
1171 define("DB_ACCESSDENIED", 2);
1172 define("DB_UNKNOWNDB", 3);
1173 define("DB_UNKNOWNTABLE", 4);
1174 define("DB_SYNTAXERROR", 5);
1175 define("DB_DBALREADYEXISTS", 6);
1176 define("DB_DBDOESNOTEXIST", 7);
1177 define("DB_DISKFULL", 8);
1178 
1179 # define value to designate omitted arguments (so DB values can be set to NULL)
1180 define("DB_NOVALUE", "!-_-_-DB_NOVALUE-_-_-!");
1181 
1182 # MySQL error code mapping
1184  1045 => DB_ACCESSDENIED,
1185  1049 => DB_UNKNOWNDB,
1186  1046 => DB_UNKNOWNTABLE,
1187  1064 => DB_SYNTAXERROR,
1188  1007 => DB_DBALREADYEXISTS, # ? (not sure)
1189  1008 => DB_DBDOESNOTEXIST, # ? (not sure)
1190  1021 => DB_DISKFULL, # ? (not sure)
1191  );
1192 
1193 ?>
QueryErrMsg()
Get most recent error message text set by Query().
static Caching($NewSetting=NULL)
Get or set whether query result caching is currently enabled.
const DB_UNKNOWNDB
static SetGlobalDatabaseName($DatabaseName)
Set default database name.
SetQueryErrorsToIgnore($ErrorsToIgnore)
Set query errors to ignore.
SetDefaultStorageEngine($Engine)
Set default database storage engine.
ExecuteQueriesFromFile($FileName)
Execute queries from specified file.
UpdateIntValue($TableName, $FieldName, $NewValue, $Condition, &$CachedRecord)
A convenience function to get or set an integer value in the database.
const DB_SYNTAXERROR
SQL database abstraction object with smart query caching.
GetServerVersion()
Get database server version number.
const DB_NOVALUE
DBUserName()
Get name used to connect with database server.
Database($UserName=NULL, $Password=NULL, $DatabaseName=NULL, $HostName=NULL)
Object constructor.
FetchRow()
Get next database row retrieved by most recent query.
LastInsertId()
Get ID of row added by the last SQL &quot;INSERT&quot; statement.
static SetGlobalServerInfo($UserName, $Password, $HostName="localhost")
const DB_DBALREADYEXISTS
PHP
Definition: OAIClient.php:39
GetFieldType($TableName, $FieldName)
Get field (column) type.
NumRowsSelected()
Get number of rows returned by last query.
FetchRows($NumberOfRows=NULL)
Get specified number of database rows retrieved by most recent query.
static QueryDebugOutput($NewSetting)
Enable or disable debugging output for queries.
Query($QueryString, $FieldName="")
Query database (with caching if enabled).
FetchField($FieldName)
Pull next row from last DB query and get a specific value from that row.
FieldExists($TableName, $FieldName)
Get whether specified field exists in specified table.
static NumCacheHits()
Get the number of queries that have resulted in cache hits since program execution began...
FetchColumn($FieldName, $IndexFieldName=NULL)
Get all available values for specified database field retrieved by most recent query.
DBHostName()
Get host name of system on which database server resides.
const DB_ACCESSDENIED
UpdateFloatValue($TableName, $FieldName, $NewValue, $Condition, &$CachedRecord)
A convenience function to get or set a float value in the database.
QueryErrNo()
Get most recent error code set by Query().
$APDBErrorCodeMappings
UpdateValue($TableName, $FieldName, $NewValue, $Condition, &$CachedRecord)
A convenience function to get or set a value in the database.
static AdvancedCaching($NewSetting=NULL)
Get or set whether advanced query result cachine is currently enabled.
static DisplayQueryErrors($NewValue=NULL)
Get/set whether Query() errors will be displayed.
static CacheHitRate()
Get the ratio of query cache hits to queries as a percentage.
DBName()
Get current database name.
LogComment($String)
Peform query that consists of SQL comment statement.
__wakeup()
Restore database connection when unserialized.
static NumQueries()
Get the number of queries that have been run since program execution began.
const DB_DBDOESNOTEXIST
const DB_UNKNOWNTABLE
const DB_DISKFULL