简化PDO方式操作数据库,封装成read和write两个常用方法,以及batchWrite批量数据操作(预处理+事物)、exec批量数据(事物),减少工作量
一、数据库相关信息
数据库名为:dian
数据表名:dian_users 有user和pass字段
二、实现代码
1.封装类文件名 db.class.php
<?php
class PDOTool
{
protected static $_instance = null;
protected static $dbConfig;
protected $dsn;
protected $dbh;
private static $dbHost;
private static $dbName;
private static $dbUser;
private static $dbPasswd;
/**
* 配置数据库信息
*/
private static function setDBConfig()
{
$DB = array(
"host" => self::$dbHost, //数据库地址
"user" => self::$dbUser, //数据库名
"password" => self::$dbPasswd, //数据库帐号
"dbname" => self::$dbName //数据库密码
);
self::$dbConfig = $DB;
}
/**
* 构造方法
*/
public function __construct($dbHost, $dbUser, $dbPasswd, $dbName)
{
try {
self::$dbHost = $dbHost;
self::$dbName = $dbName;
self::$dbUser = $dbUser;
self::$dbPasswd = $dbPasswd;
$this->dsn = 'mysql:host=' . $dbHost . ';dbname=' . $dbName;
$this->dbh = new PDO($this->dsn, $dbUser, $dbPasswd, array(PDO::MYSQL_ATTR_INIT_COMMAND => "set names utf8"));
$this->dbh->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
$this->dbConfig = self::setDBConfig();
} catch (PDOException $e) {
die(json_encode(self::result(false, $e->getMessage(), $e)));
}
}
/**
* 单例模式创建PDOTool类
* @return PDOTool
*/
private static function getInstance()
{
if (self::$_instance === null) {
//加载数据库配置信息
self::setDBConfig();
self::$_instance = new self(self::$dbConfig['host'], self::$dbConfig['user'], self::$dbConfig['password'], self::$dbConfig['dbname']);
}
return self::$_instance;
}
/**
* 开放数据库名信息,写sql语句有时候需要数据库名,具体看个人需求
* @return string 返回数据库名
*/
public static function getDBName()
{
return self::getInstance()->dbConfig['dbname'];
}
/**
* 数据读取方法
* @param $sqlStr string\sql查询语句
* @param $dataArray array\查询的参数列表
* @param $method boolean\查询方式是数组还是单条
* @return array
*/
public static function read($sqlStr, $dataArray, $method = true)
{
try {
$pdo = self::getInstance()->dbh;
//执行预处理语句
$stmt = $pdo->prepare($sqlStr);
if ($dataArray != null && count($dataArray) > 0) {
$stmt->execute($dataArray);
} else {
$stmt->execute();
}
//以数组|单条形式返回
$arr = $method
? $stmt->fetchAll(PDO::FETCH_ASSOC) //默认数组
: $stmt->fetch(PDO::FETCH_ASSOC); //false为单条
//判读数组是否为空
$isEmpty = !empty($arr);
return self::result($isEmpty, $isEmpty ? "查询成功!" : "查询结果为空", $arr);
} catch (PDOException $e) {
die(json_encode(self::result(false, $e->getMessage(), $e)));
}
}
/**
* 数据插入、更新、删除方法
* @param $sqlStr string\sql操作语句
* @param $dataArray array\数据参数列表
* @return array
*/
public static function write($sqlStr, $dataArray)
{
try {
$pdo = self::getInstance()->dbh;
//执行预处理语句
$stmt = $pdo->prepare($sqlStr);
if ($dataArray != null && count($dataArray) > 0) {
$stmt->execute($dataArray);
} else {
$stmt->execute();
}
//获取影响行数
$affectRow = $stmt->rowCount();
$isSuccess = $affectRow > 0;
return self::result($isSuccess, $isSuccess ? "操作成功!" : "操作失败", array("affectedRows" => $affectRow));
} catch (PDOException $e) {
die(json_encode(self::result(false, $e->getMessage(), $e)));
}
}
/**
* 批量数据操作-事物操作
* @param $sql string\需要执行的sql语句
* @param $bathDataArray array\与sql语句相对应的参数列
* @return array
*/
public static function batchWrite($sql, $bathDataArray)
{
try {
$pdo = self::getInstance()->dbh;
//开启事物
$pdo->beginTransaction();
//预处理语句
$stmt = $pdo->prepare($sql);
$dataArrayLenth = count($bathDataArray);
//影响行数
$affectRow = 0;
for ($i = 0; $i < $dataArrayLenth; $i++) {
//执行预处理语句
if ($stmt->execute($bathDataArray[$i])) {
$affectRow++;
};
}
//执行事物的提交操作
$pdo->commit();
$isSuccess = $affectRow > 0;
return self::result($isSuccess, $isSuccess ? "操作成功!" : "操作失败", array("affectedRows" => $affectRow));
} catch (PDOException $e) {
$pdo->rollBack();
die(json_encode(self::result(false, $e->getMessage(), $e)));
}
}
/**
* 可用于执行一个完整导出的sql文件,通常用于安装导入数据库信息。
* @param $sqlArray array\Sql语句
* @return array
*/
public static function exec($sqlArray)
{
try {
$pdo = self::getInstance()->dbh;
//开启事物
$pdo->beginTransaction();
//计算数组长度
$sqlLength = count($sqlArray);
//执行状态
$statusData = array();
//失败条数
$errorCount = 0;
//失败信息数组
$errorData = array();
//sql语句是否全部执行通过
$isPass = true;
for ($i = 0; $i < $sqlLength; $i++) {
if ($sql = trim($sqlArray[$i])) {
$pdo->exec($sql);
$code = $pdo->errorCode();
if ($code != 00000) {
$errorData[$errorCount]["errorCode"] = $code;
$errorData[$errorCount]['errorSql'] = $sql;
$errorCount++;
$isPass = false;
}
}
}
if (!$isPass) {
$pdo->rollBack();
$resultArray = array("errorRows" => $errorCount, "errorData" => $errorData);
return self::result(false, "执行失败,事物回滚!", $resultArray);
}
//提交事务
$pdo->commit();
return self::result(true, "操作成功!", array("affectedRows" => $i));
} catch (PDOException $e) {
//执行事物的回滚操作
$pdo->rollBack();
die(json_encode(self::result(false, $e->getMessage(), $e)));
}
}
/**
* 返回执行结果
* @param $isSuccess boolean\true成功、false失败
* @param $msg string\信息描述
* @param $object object\数据对象
* @return array array\操作结果
*/
private static function result($isSuccess, $msg, $object)
{
return array('success' => $isSuccess, 'msg' => $msg, 'data' => $object);
}
}
?>
2.测试文件名 sql.php
<?php
header("Content-type: text/html; charset=utf-8");
include("db.class.php"); //引入封装的数据库操作类
//初始化连接
$DB = new PDOTool("localhost", "username", "password", "dbname");
//查询数据库信息-----------------------------
//查询方法1 :不带数据的数组
//$sql = "SELECT * FROM `".$dbName."`.`dian_users` "; //1.不带参数的查询
//$mData = array(); //1.不带参数查询的数组,数组传空值
$arrResult = $DB->read($sql, $mData, true); //php全版本可用
$arrResult = $DB::read($sql, $mData, true); //php5.2及以下不支持
//第三个参数默认true,表示查询全部;可使用false,表示只查询一条数据
$data = $arrResult['data']; //取出data
foreach ($data as $key => $value) {
var_dump($value); //显示出来
}
//查询方法2 :带数据的数组
$sql = "SELECT * FROM `" . $dbName . "`.`dian_users` where `user` = ? and pass = ? "; //2.带参数的查询
$mData = array("111", "aaa"); //2.带参数查询的数组,数组值与需要查询的字段名字对应,111代表user的值 ,aaa表示pass的值
//用多维数组存储查询结果-注意如果没有查询到数据,返回的数组为空,但长度是1,不是0
$arrResult = $DB::read($sql, $mData);//调用查询方法,传入sql语句、数组参数
//输出结果
var_dump($arrResult);
//插入一个用户信息-----------------------
$sql = "INSERT INTO `" . $dbName . "`.`dian_users`(`user`, `pass`) VALUES (?, ?)";
//创建数组,存放需要传入的值,注意:数据的位置必须和数据字段的位置对应,不能错乱,有几个问号就有几个数据
$mData = array("555", "fff"); //插入一个用户名为555,密码为fff的帐号
//调用方法写入数据
$ret = $DB::write($sql, $mData); //传入sql语句和数据参数,返回值是bool类型
if ($ret['success'] == true) {
echo "写入成功";
} else {
echo "写入失败";
}
?>
3.返回结果类型-数组
read返回值:success:成功true、失败false
{
"success": true,
"msg": "查询成功!",
"data": [查询出来的数据]
}
write返回值:success:成功true、失败false
{
"success": true,
"msg": "操作成功!",
"data": {
"affectedRows": 17
}
}
exec执行成功结果和write一致
exec执行失败返回值:
{
"success": false,
"msg": "执行失败,事物回滚!",
"data": {
"errorRows": 执行出错语句条数,
"errorData": [
{
"errorCode": "出错响应码",
"errorSql": "出错sql语句1"
},
{
"errorCode": "出错响应码",
"errorSql": "出错sql语句2"
}
]
}
}