Удобная штука получилась...
<?php
class Config
{
const AUTO = 'auto';
const XML = 'xml';
const JSON = 'json';
const INI = 'ini';
const CSV = 'csv';
const DB = 'pdo';
static private $instances;
static public function & getInstance($file, $type = self::AUTO)
{
if(! isset(self::$instances[$file]))
{
self::$instances[$file] = static::Load($file, $type);
}
return self::$instances[$file];
}
/**
* загружает 2D ассоциативный массив из файла (xml,json,ini,csv)
* или БД (*.pdo - ini-файл с ключами dsn, user, password, table, [driver_options] )
* @param string $filename
* @param const $type
* @return array
*/
public static function Load($filename, $type=self::AUTO)
{
if(!file_exists($filename))
throw new Exception(__CLASS__.": The file $filename does not exist"); //todo: spec. exeption
if($type==self::AUTO)
$type = pathinfo($filename, PATHINFO_EXTENSION);
switch ($type) {
case self::INI:
return parse_ini_file($filename,true);
case self::CSV:
return static::readCSV($filename);
case self::JSON:
return json_decode(file_get_contents($filename),true);
case self::XML:
return static::objectToArray(simplexml_load_file($filename));
case self::DB:
$pdoini = parse_ini_file($filename);
$pdo = new PDO($pdoini['dsn'], $pdoini['user'], $pdoini['password'], is_array($pdoini['driver_options']) ? $pdoini['driver_options'] : null);
return static::LoadFromDB($pdo, $pdoini['table']);
default:
throw new Exception(__CLASS__.": Unknown file format ($type)"); //todo: spec. exeption
}
}
public static function Save($filename, $data, $type=self::AUTO)
{
$h = fopen($filename, "w");
if(!$h)
throw new Exception(__CLASS__.": Can't write file $filename"); //todo: spec. exeption
if($type==self::AUTO)
$type = pathinfo($filename, PATHINFO_EXTENSION);
switch ($type) {
case self::INI:
return static::writeIni($filename,$data);
case self::CSV:
return static::writeCSV($filename, $data);
case self::JSON:
return file_put_contents($filename,json_encode($data));
case self::XML:
return static::writeXML($filename,$data);
case self::DB:
$pdoini = parse_ini_file($filename);
$pdo = new PDO($pdoini['dsn'], $pdoini['user'], $pdoini['password'], is_array($pdoini['driver_options']) ? $pdoini['driver_options'] : null);
return static::SaveToDB($data, $pdo, $pdoini['table']);
default:
throw new Exception(__CLASS__.": Unknown file format ($type)"); //todo: spec. exeption
}
}
//---------- CSV ----------
static private function readCSV($filename)
{
$h = fopen($filename, "r");
if(!$h)
throw new Exception(__CLASS__.": Can't read file $filename"); //todo: spec. exeption
while(($data = fgetcsv($h)) !== FALSE)
{
$val = (count($data)>3) ? array_slice($data,2) : $data[2];
$ret[$data[0]][$data[1]] = $val;
}
fclose($h);
return $ret ?: array();
}
static private function writeCSV($filename, $data)
{
try
{
$h = fopen($filename, "w");
if(!$h)
throw new Exception(__CLASS__.": Can't write file $filename"); //todo: spec. exeption
foreach ($data as $sectname => $section)
{
foreach ($section as $key => $value)
{
if(is_array($value))
$out = array_merge(array($sectname, $key), $value);
else
$out = array($sectname, $key, $value);
if(fputcsv($h, $out)===false)
throw new Exception(__CLASS__.": Can't write file $filename"); //todo: spec. exeption
}
}
return true;
}
catch(Exception $e)
{
if($h) fclose($h);
throw $e;
}
}
//---------- XML ----------
private static function writeXML($filename, $data)
{
$xml = "<?xml version='1.0'?>";
$xml .= '<Root>'.static::array2XML($data).'</Root>';
return file_put_contents($filename,$xml);
}
private static function array2XML($data)
{
foreach ($data as $key => $value) {
if (is_array($value))
$value = static::array2XML($value);
if(is_numeric($key))
$ret.="<element index='$key'>$value</element>";
else
$ret.="<$key>$value</$key>";
}
return $ret;
}
//---------- DB ----------
public static function LoadFromDB(PDO $pdo, $table='Config')
{
$res = $pdo->query("select * from $table");
$rows = $res->fetchAll();
foreach ($rows as $value) {
$ret[$value['section']][$value['key']] = $value['value'];
}
return $ret;
}
public static function createTable(PDO $pdo, $table='Config')
{
$pdo->exec("create table if not exists $table (section varchar(32), key varchar(32), value varchar(256), primary key (section,key))");
}
public static function WriteToDB($data, PDO $pdo, $table='Config')
{
foreach ($data as $sectname => $section)
foreach ($section as $key => $value)
{
$values[] = "($sectname,$key,$value)";
}
$values = implode(',',$values);
return $pdo->exec("INSERT INTO $table (section,key,value) VALUES $values ON DUPLICATE KEY UPDATE value=VALUES(value)");
}
//---------- INI ----------
public static function writeIni($filename, $array2D)
{
$out = '';
foreach($array2D as $key => $value)
{
$out .= '['.$key."]\n";
$out .= static::write_section($value)."\n";
}
file_put_contents($filename, $out);
}
static function write_section(& $ini)
{
$ret = '';
//ksort($ini);
foreach($ini as $key => $val)
{
if (is_array($val))
foreach ($val as $k => $v)
$ret .= $key.'["'.$k.'"] = '.static::value2str($v)."\n";
else
$ret .= $key.' = '.static::value2str($val)."\n";
}
return $ret;
}
static function value2str($val)
{
if ($val === true) return 'true';
if ($val === false) return 'false';
if ($val === null) return 'null';
if (is_string($val)) return '"'.addslashes($val).'"';
return $val;
}
//---------- Util ----------
public static function objectToArray($obj)
{
$arr = (is_object($obj))?
get_object_vars($obj) :
$obj;
if(count($arr)==1 && isset($arr['element']))
$arr = $arr['element'];
foreach ($arr as $key => $val)
{
$arr[$key] = ((is_array($val)) || (is_object($val)))?
self::objectToArray($val) :
$val;
}
return $arr;
}
public static function array_flatten($array)
{
if (!is_array($array)) return FALSE;
$result = array();
foreach ($array as $key => $value)
{
if (is_array($value))
$result = array_merge($result, array_flatten($value));
else
$result[$key] = $value;
}
return $result;
}
}
?>
Комментариев нет:
Отправить комментарий