<?php ini_set('display_errors', true); final class DB { private static $db; public static function getInstance(): PDO { if(!self::$db instanceof PDO) { new self(); } return self::$db; } private function __clone() {} private function __construct() { $config = parse_ini_file('./db.ini'); $dsn = sprintf('mysql:localhost=%s;dbname=%s;port=%d;charset=%s', $config['host'], $config['dbname'], $config['port'], $config['charset']); try{ self::$db = new PDO($dsn, $config['user'], $config['password']); }catch(PDOException $e) { exit($e->getMessage()); } } } class Statement { private static $statement; private $state; private function __construct(PDO $db, string $sql) { $this->state = $db->prepare($sql); } public static function getInstance(PDO $db, string $sql) { if(!self::$statement instanceof Statement) { self::$statement = new self($db, $sql); } return self::$statement; } public function bindValue($key, $val) { return $this->state->bindValue($key, $val); } public function bindParam($key, $val) { return $this->state->bindParam($key, $val); } public function execute() { return $this->state->execute(); } public function fetchOne() { return $this->state->fetch(PDO::FETCH_ASSOC); } public function fetchAll() { return $this->state->fetchAll(PDO::FETCH_ASSOC); } public function fetchColumn(int $index = null) { return $this->state->fetchColumn($index); } public function resetQuery() { return $this->state->closeCursor(); } public function effectRow() { return $this->state->rowCount(); } public function errorReason() { return $this->state->errorInfo()[2]; } } /**建立方法的抽象基类 * Class Base */ abstract class Base { protected $db; protected $statement; public function __construct(string $sql) { $this->db = DB::getInstance(); $this->statement = Statement::getInstance($this->db, $sql); } protected function exec() { return $this->statement->execute() ? true: $this->statement->errorReason() ?? 'SQL语句有误'; } public function bindValue($key = null, $val = null) { if(func_num_args() === 0 || (!is_array($key) && !$val)) { return $this; } else if(is_array($key)) { foreach($key as $k => $v) { $this->statement->bindValue($k, $v); } } else { $this->statement->bindValue($key, $val); } return $this; } public function bindParam($key = null, $val = null) { if(func_num_args() === 0 || (!is_array($key) && !$val)) { return $this; } else if(is_array($key)) { foreach($key as $k => $v) { $this->statement->bindParam($k, $v); } } else { $this->statement->bindParam($key, $val); } return $this; } public static function getDB(): PDO { return DB::getInstance(); } } class Query extends Base{ private function queryRes(bool $is_all = false) { $res = $this->exec(); if($res === true) { $data = $is_all? $this->statement->fetchAll(): $this->statement->fetchOne(); return $data === false? []: $data; } return $res; } public function one() { return $this->queryRes(false); } public function all() { return $this->queryRes(true); } public function fetchColumn($index = 0) { $res = $this->exec(); if($res) { $data = $this->statement->fetchColumn($index); return $data === false? '': $data; } return $res; } public function __destruct() { $this->statement->resetQuery(); } } class Operate extends Base{ public function execute() { $res = $this->exec(); if($res === true) { return $this->statement->effectRow(); } throw new PDOException($res); } public static function beginTransaction($fn) { if(!$fn) { return false; } self::getDB()->beginTransaction(); try{ call_user_func($fn); return self::getDB()->commit()? true: false; }catch(PDOException $e) { self::getDB()->rollBack(); throw $e; } } //注意:如果在事务中进行调用,那么就有可能获取不到 public static function lastInsertId() { return self::getDB()->lastInsertId(); } } //$res = (new Query('SELECT `u`.`user`, `temp`.`pwd` FROM `user` AS `u` LEFT JOIN (SELECT `id`, `pwd` FROM `user`) AS `temp` ON `temp`.`id` = `u`.`id` WHERE `u`.`id` > :id'))->bindValue(':id', 3)->all(); //var_dump($res); //$res = (new Query('SELECT * FROM `user`'))->all(); //var_dump($res); //$res = (new Operate('UPDATE `user` SET `user` = :user WHERE `id` = :id'))->bindValue([ // ':user' => 'are you ok???', // ':id' => 1 //])->execute(); //var_dump($res); //Operate::getDB()->beginTransaction(); //try{ // $res1 = (new Operate('UPDATE `user` SET `user` = :user WHERE `id` = :id'))->bindValue([ // ':user' => 'tt', // ':id' => 1 // ])->execute(); // $res2 = (new Operate('UPDATE `user` SET `user` = :user WHERE `id` = :id'))->bindValue([ // ':user' => 'tt', // ':id' => 2 // ])->execute(); // if($res1 === true && $res2 === true) { // Operate::getDB()->commit(); // } //}catch(PDOException $e) { // Operate::getDB()->rollBack(); // throw $e; //} //$res1 = (new Operate('UPDATE `user` SET `user` = :user WHERE `id` = :id'))->bindValue([ // ':user' => 'tt', // ':id' => 1 //])->execute(); //$res2 = (new Operate('UPDATE `user` SET `user` = :user WHERE `id` = :id'))->bindValue([ // ':user' => 'tt', // ':id' => 2 //])->execute(); //var_dump($res1); //var_dump($res2); //$res = Operate::beginTransaction(function() { // (new Operate('INSERT INTO `user` (`user`, `pwd`) VALUES (:user, :pwd)'))->bindValue([ // ':user' => 'wakaka', // ':pwd' => 'nono' // ])->execute(); //}); //var_dump($res); (new Operate('INSERT INTO `user` (`user`, `pwd`) VALUES (:user, :pwd)'))->bindValue([ ':user' => 'wakaka', ':pwd' => 'nono' ])->execute(); var_dump(Operate::lastInsertId()); ?>