University of Southern California

WSCORE2.php

00001 <?php
00020 error_reporting(E_ALL | E_STRICT);
00021 @date_default_timezone_set(date_default_timezone_get());
00022 
00023 /* Autoload models, when WSCORE doesn't define them explicitly */
00024 function __autoload($class_name) {
00025   if (class_exists($class_name)) {
00026     // Don't do anything, we're OK.
00027   } else if (file_exists('models/'.$class_name.'.min.php')) {
00028     require_once('models/'.$class_name.'.min.php');
00029   } else if (file_exists('models/'.$class_name.'.php')) {
00030     require_once('models/'.$class_name.'.php');
00031   }
00032 }
00033 
00035 class WSCORE2 {
00040   public function __construct($conf = NULL) {
00041     $this->attributes = array();
00042     $this->message_queue = array();
00043     $this->db = NULL;
00044     $this->qry = NULL;
00045 
00046     if (is_object($conf) && method_exists($conf, "getKeys")) {
00047       foreach($conf->getKeys() as $key) {
00048         $this->set($key, $conf->get($key));
00049       }
00050     } else if (is_array($conf)) {
00051       foreach ($conf as $key => $value) {
00052         $this->set($key,$value);
00053       }
00054     } else if (is_string($conf)) {
00055       if (strpos(ltrim($conf),"[") !== false || strpos(ltrim($conf),"{") !== false) {
00056         /* First try parsing as a JSON file. */
00057         $obj = json_decode($conf);
00058         if ($obj !== false) {
00059           foreach ($obj as $key => $value) {
00060             $this->set($key,$value);
00061           }
00062         } else {
00063           $this->message("ERROR: Problem decoding JSON configuration");
00064         }
00065       } else {
00066         $this->simpleConf($conf);
00067       }
00068     }
00069   }
00070   
00079   public function simpleConf($configuration) {
00080     $lines = explode("\n",$configuration);
00081     $i = 1;
00082     foreach ($lines as $line) {
00083       if (strpos($line,"#") !== false) {
00084         list($line, $comment) = explode("#", $line);
00085       }
00086       if (trim($line) != "") {
00087         if (strpos($line,":") !== false) {
00088           list($key, $value) = explode(":",$line,2);
00089           $this->set($key, $value);
00090         } else {
00091           $this->message("ERROR: ".$i." doesn't make sense [$line]");
00092         }
00093       }
00094       $i++;
00095     }
00096     if ($this->errorCount() === 0) {
00097       return true;
00098     }
00099     return false;
00100   }
00101 
00102   
00107   public function getKeys() {
00108     if (isset($this->attributes) && is_array($this->attributes)) {
00109       return array_keys($this->attributes);
00110     }
00111     return false;
00112   }
00113   
00120   public function set ($key, $value = NULL) {
00121     if ($value === NULL) {
00122       unset($this->attributes[$key]);
00123       return true;
00124     }
00125     $this->attributes[$key] = $value;
00126     return isset($this->attributes[$key]);
00127   }
00128   
00134   public function get ($key) {
00135     if (isset($this->attributes[$key])) {
00136       return $this->attributes[$key];
00137     }
00138     return false;
00139   }
00140   
00148   public function map($src, $obj, $verbose = false) {
00149     $escape_chars = '';
00150     if (strpos($src, '"') !== false) {
00151       $escape_chars .= '"';
00152     }
00153     if (strpos($src, "'") !== false) {
00154       $escape_chars .= "'";
00155     }
00156     foreach ($obj as $key => $value) {
00157       if ($escape_chars !== '') {
00158         /* Check to see if we need to double escape for JSON content being
00159            mapped. */
00160         if (strpos($value,'\"') === false && strpos($value,"\'") === false) {
00161           $src = str_replace('{' . $key . '}', addcslashes($value, $escape_chars), $src);
00162         } else {
00163           $src = str_replace('{' . $key . '}', addcslashes(str_replace(array('\"', "\'"), array('\\'.'\\'.'"', '\\'.'\\'."'"), $value), $escape_chars), $src);
00164         }
00165       } else {
00166         $src = str_replace('{' . $key . '}', $value, $src);
00167       }
00168     }
00169     if ($verbose === true) {
00170       $this->message("Map(): $src");
00171     }
00172     return $src;
00173   }
00174   
00182   public function message ($msg = NULL) {
00183     if ($msg === NULL) {
00184       $result = implode("\n", $this->message_queue);
00185       unset($this->message_queue);
00186       $this->message_queue = array();
00187       return $result;
00188     }
00189     $this->message_queue[] = $msg;
00190     return true;
00191   }
00192   
00197   public function errorCount () {
00198     $error_count = 0;
00199     foreach($this->message_queue as $msg) {
00200       if (stripos($msg, "ERROR:") !== false) {
00201         $error_count++;
00202       }
00203     }
00204     return $error_count;
00205   }
00206   
00210   public function open () {
00211     switch($this->get("db_type")) {
00212     case 'mysql':
00213       $mysql_host = $this->get("db_host");
00214       if ($mysql_host === false) {
00215         $this->message("ERROR: You must specify a database host to open.");
00216         return false;
00217       }
00218       $mysql_user = $this->get("db_user");
00219       if ($mysql_user === false) {
00220         $this->message("ERROR: You must specify a database user to open.");
00221         return false;
00222       }
00223       $mysql_password = $this->get("db_password");
00224       if ($mysql_password === false) {
00225         $this->message("ERROR: You must specify a database password to open.");
00226         return false;
00227       }
00228       $mysql_database = $this->get("db_name");
00229       if ($mysql_database === false) {
00230         $this->message("ERROR: You must specify a database name to open.");
00231         return false;
00232       }
00233       
00234       $this->db = @mysql_connect($mysql_host, $mysql_user, $mysql_password);
00235       if (! $this->db) {
00236         $this->db = NULL;
00237         $this->message('ERROR: ' . mysql_error());
00238         return false;
00239       } else {
00240         if (! mysql_select_db($mysql_database, $this->db)) {
00241           $this->message("ERROR: Could not select database: $mysql_database " . mysql_error());
00242           return false;
00243         }
00244       }
00245       return true;
00246     case 'sqlite':
00247       $sqlite_database = $this->get("db_name");
00248       if ($sqlite_database === false) {
00249         $this->message("ERROR: You must specify a database name to open.");
00250         return false;
00251       }
00252       $this->db = sqlite_open($sqlite_database,'0666',$error);
00253       if ($this->db === false) {
00254         $this->message("error opening database ".$db_name.": ".$error);
00255         return false;
00256       }
00257       return true;
00258     default:
00259       $this->message("ERROR: Database type not set.");
00260       return false;
00261     }
00262     return false;
00263   }
00264   
00270   public function release () {
00271     if ($this->db === NULL) {
00272       $this->message("ERROR: Database not configured.");
00273       return false;
00274     }
00275     if ($this->qry === NULL) {
00276       $this->message("ERROR: no result set to free");
00277       return false;
00278     }
00279     switch($this->get("db_type")) {
00280     case 'mysql':
00281       if ($this->qry && mysql_free_result($this->qry) === true) {
00282         $this->qry = NULL;
00283         return true;
00284       }
00285       $this->message("ERROR: " . mysql_error($this->db));
00286       return false;
00287     case 'sqlite':
00288       // FIXME: there should be some similar method to mysql_free_result ...
00289       unset($this->qry);
00290       $this->qry = NULL;
00291       return true;
00292     default:
00293       $this->message("ERROR: ".$this->get("db_type")." not supported for release.");
00294       return false;
00295     }
00296     return true;    
00297   }
00298   
00305   public function execute ($sql, $verbose = false) {
00306     if ($this->db === NULL) {
00307       $this->message("ERROR: Database not configured.");
00308       return false;
00309     }
00310     if ($verbose === true) {
00311       $this->message("SQL: $sql");
00312     }
00313     switch($this->get("db_type")) {
00314     case 'mysql':
00315       $this->set('SQLRowCount', 0);
00316       $this->qry = mysql_query($sql);
00317       if ($this->qry === false) {
00318         $this->message("ERROR: SQL [$sql] " . mysql_error());
00319         return false;
00320       }
00321       if ($this->qry) {
00322         $num_rows = @mysql_num_rows($this->qry);
00323         if ($num_rows === false) {
00324           $this->set("SQLRowCount", mysql_affected_rows());
00325         } else {
00326           $this->set("SQLRowCount", $num_rows);
00327         }
00328       }
00329       return true;
00330     case 'sqlite':
00331       $this->set('SQLRowCount', 0);
00332       if (stripos($sql,"SELECT ") !== false) {
00333         $this->qry = sqlite_query($this->db, $sql, SQLITE_ASSOC, $error);
00334         if ($this->qry) {
00335           $this->set('SQLRowCount', sqlite_num_rows($this->qry));
00336         }
00337       } else {
00338         $this->qry = @sqlite_exec($this->db, $sql, $error);
00339         if (! $this->qry) {
00340           $this->message("ERROR: SQL [$sql] " . $error);
00341           return false;
00342         } else {
00343           $this->set('SQLRowCount', sqlite_changes($this->db));
00344         }
00345       }
00346       return true;
00347     default:
00348       $this->message("ERROR: Database type not set.");
00349       return false;
00350     }
00351     return false;
00352   }
00353 
00354 
00362    public function mapExecute ($sql, $obj, $verbose = false) {
00363     if ($this->get("db_type") === "sqlite") {
00364       $sql = str_replace(array("\\'","\\\""), array("''",'""'), $this->map($sql, $obj, $verbose));
00365       return $this->execute($sql, $verbose);
00366     }
00367     return $this->execute($this->map($sql, $obj, $verbose), $verbose);
00368    }
00369   
00375   public function getRow ($verbose = false) {
00376     if ($this->db === NULL) {
00377       $this->message("ERROR: Database not configured.");
00378       return false;
00379     }
00380     switch($this->get("db_type")) {
00381     case 'mysql':
00382       if ($this->qry) {
00383         return mysql_fetch_array($this->qry, MYSQL_ASSOC);
00384       } else {
00385         $this->message("WARNING: no query available");
00386       }
00387       break;
00388     case 'sqlite':
00389       if ($this->qry) {
00390         return sqlite_fetch_array($this->qry, SQLITE_ASSOC);
00391       } else if ($verbose === true) {
00392         $this->message("WARNING: no query available");
00393       }
00394       return false;
00395     default:
00396       $this->message("ERROR: Database type not set.");
00397       break;
00398     }
00399     return false;
00400   } 
00401    
00406   public function lastInsertRowId () {
00407     if ($this->db === NULL) {
00408       $this->message("ERROR: Database not configured.");
00409       return false;
00410     }
00411     switch($this->get("db_type")) {
00412       case 'mysql':
00413         return mysql_insert_id();
00414       case 'sqlite':
00415         return sqlite_last_insert_rowid($this->db);
00416     default:
00417       $this->message("ERROR: Database type not set.");
00418       break;
00419     }
00420     return false;
00421   }
00422   
00427   public function close () {
00428     if ($this->db === NULL) {
00429       $this->message("ERROR: Database not configured.");
00430       return false;
00431     }
00432     switch($this->get("db_type")) {
00433     case 'mysql':
00434       mysql_close($this->db);
00435       return true;
00436     case 'sqlite':
00437       sqlite_close($this->db);
00438       return true;
00439     default:
00440       $this->message("ERROR: Database type not set.");
00441       break;
00442     }
00443     return false;
00444   }
00445 }
00446 
00447 ?>