PHP用PDO如何封装简单易用的DB类详解


Posted in PHP onJuly 30, 2017

前言

PDO扩展为PHP访问数据库定义了一个轻量级的、一致性的接口,它提供了一个数据访问抽象层,这样,无论使用什么数据库,都可以通过一致的函数执行查询和获取数据。PDO随PHP5.1发行,在PHP5.0的PECL扩展中也可以使用。

我个人理解:PDO是一个抽象类,为我们提供访问数据的接口方法,下面这篇将给大家介绍关于PHP如何利用PDO封装简单易用的DB类,下面话不多说,来一起看看详细的介绍:

使用

创建测试库和表

create database db_test;
CREATE TABLE `user` (
 `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
 `name` char(11) NOT NULL,
 `created_at` int(10) unsigned NOT NULL,
 PRIMARY KEY (`uid`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
INSERT INTO `user` VALUES ('1', 'wang', '1501109027');
INSERT INTO `user` VALUES ('2', 'meng', '1501109026');
INSERT INTO `user` VALUES ('3', 'liu', '1501009027');
INSERT INTO `user` VALUES ('4', 'yuan', '1500109027');

代码测试

require __DIR__ . '/DB.php';
$db = new DB();
$db->__setup([
 'dsn'=>'mysql:dbname=db_test;host=localhost',
 'username'=>'root',
 'password'=>'******',
 'charset'=>'utf8'
]);


$user = $db->fetch('SELECT * FROM user where id = :id', ['id' => 1]);
echo $user['name'];
echo "\n";

$insertId = $db->insert('user', ['name' => 'salamander', 'created_at' => time()]);
echo "insert user {$insertId}\n";
$users = $db->fetchAll('SELECT * FROM user');
foreach ($users as $item) {
 echo "user {$item['id']} is {$item['name']} \n";
}

运行结果

PHP用PDO如何封装简单易用的DB类详解

DB工具类

<?php
/**
 * User: Salamander
 * Date: 2016/9/2
 * Time: 9:16
 */

class DB
{
 private $dsn;
 private $sth;
 private $dbh;
 private $user;
 private $charset;
 private $password;

 public $lastSQL = '';

 public function __setup($config = array())
 {
  $this->dsn = $config['dsn'];
  $this->user = $config['username'];
  $this->password = $config['password'];
  $this->charset = $config['charset'];
  $this->connect();
 }

 private function connect()
 {
  if(!$this->dbh){
   $options = array(
    \PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES ' . $this->charset,
   );
   $this->dbh = new \PDO($this->dsn, $this->user,
    $this->password, $options);
  }
 }

 public function beginTransaction()
 {
  return $this->dbh->beginTransaction();
 }

 public function inTransaction()
 {
  return $this->dbh->inTransaction();
 }

 public function rollBack()
 {
  return $this->dbh->rollBack();
 }

 public function commit()
 {
  return $this->dbh->commit();
 }

 function watchException($execute_state)
 {
  if(!$execute_state){
   throw new MySQLException("SQL: {$this->lastSQL}\n".$this->sth->errorInfo()[2], intval($this->sth->errorCode()));
  }
 }

 public function fetchAll($sql, $parameters=[])
 {
  $result = [];
  $this->lastSQL = $sql;
  $this->sth = $this->dbh->prepare($sql);
  $this->watchException($this->sth->execute($parameters));
  while($result[] = $this->sth->fetch(\PDO::FETCH_ASSOC)){ }
  array_pop($result);
  return $result;
 }

 public function fetchColumnAll($sql, $parameters=[], $position=0)
 {
  $result = [];
  $this->lastSQL = $sql;
  $this->sth = $this->dbh->prepare($sql);
  $this->watchException($this->sth->execute($parameters));
  while($result[] = $this->sth->fetch(\PDO::FETCH_COLUMN, $position)){ }
  array_pop($result);
  return $result;
 }

 public function exists($sql, $parameters=[])
 {
  $this->lastSQL = $sql;
  $data = $this->fetch($sql, $parameters);
  return !empty($data);
 }

 public function query($sql, $parameters=[])
 {
  $this->lastSQL = $sql;
  $this->sth = $this->dbh->prepare($sql);
  $this->watchException($this->sth->execute($parameters));
  return $this->sth->rowCount();
 }

 public function fetch($sql, $parameters=[], $type=\PDO::FETCH_ASSOC)
 {
  $this->lastSQL = $sql;
  $this->sth = $this->dbh->prepare($sql);
  $this->watchException($this->sth->execute($parameters));
  return $this->sth->fetch($type);
 }

 public function fetchColumn($sql, $parameters=[], $position=0)
 {
  $this->lastSQL = $sql;
  $this->sth = $this->dbh->prepare($sql);
  $this->watchException($this->sth->execute($parameters));
  return $this->sth->fetch(\PDO::FETCH_COLUMN, $position);
 }

 public function update($table, $parameters=[], $condition=[])
 {
  $table = $this->format_table_name($table);
  $sql = "UPDATE $table SET ";
  $fields = [];
  $pdo_parameters = [];
  foreach ( $parameters as $field=>$value){
   $fields[] = '`'.$field.'`=:field_'.$field;
   $pdo_parameters['field_'.$field] = $value;
  }
  $sql .= implode(',', $fields);
  $fields = [];
  $where = '';
  if(is_string($condition)) {
   $where = $condition;
  } else if(is_array($condition)) {
   foreach($condition as $field=>$value){
    $parameters[$field] = $value;
    $fields[] = '`'.$field.'`=:condition_'.$field;
    $pdo_parameters['condition_'.$field] = $value;
   }
   $where = implode(' AND ', $fields);
  }
  if(!empty($where)) {
   $sql .= ' WHERE '.$where;
  }
  return $this->query($sql, $pdo_parameters);
 }

 public function insert($table, $parameters=[])
 {
  $table = $this->format_table_name($table);
  $sql = "INSERT INTO $table";
  $fields = [];
  $placeholder = [];
  foreach ( $parameters as $field=>$value){
   $placeholder[] = ':'.$field;
   $fields[] = '`'.$field.'`';
  }
  $sql .= '('.implode(",", $fields).') VALUES ('.implode(",", $placeholder).')';

  $this->lastSQL = $sql;
  $this->sth = $this->dbh->prepare($sql);
  $this->watchException($this->sth->execute($parameters));
  $id = $this->dbh->lastInsertId();
  if(empty($id)) {
   return $this->sth->rowCount();
  } else {
   return $id;
  }
 }

 public function errorInfo()
 {
  return $this->sth->errorInfo();
 }

 protected function format_table_name($table)
 {
  $parts = explode(".", $table, 2);

  if(count($parts) > 1) {
   $table = $parts[0].".`{$parts[1]}`";
  } else {
   $table = "`$table`";
  }
  return $table;
 }

 function errorCode()
 {
  return $this->sth->errorCode();
 }
}

class MySQLException extends \Exception { }

框架中使用建议

在框架中使用DB类,用单例模式或者用依赖容器来管理较好。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对三水点靠木的支持

PHP 相关文章推荐
PHP5 安装方法
Jan 15 PHP
dedecms中显示数字验证码的修改方法
Mar 21 PHP
php自动加载的两种实现方法
Jun 21 PHP
php中计算未知长度的字符串哪个字符出现的次数最多的代码
Aug 14 PHP
PHP中如何定义和使用常量
Feb 28 PHP
php下拉选项的批量操作的实现代码
Oct 14 PHP
PHP二维数组去重实例分析
Nov 18 PHP
CI框架数据库查询缓存优化的方法
Nov 21 PHP
PHP单例模式定义与使用实例详解
Feb 06 PHP
Yii2 中实现单点登录的方法
Mar 09 PHP
laravel使用Faker数据填充的实现方法
Apr 12 PHP
PHP解决高并发的优化方案实例
Dec 10 PHP
详解PHP防止直接访问.php 文件的实现方法
Jul 28 #PHP
php简单实现单态设计模式的方法分析
Jul 28 #PHP
[原创]PHP实现SQL语句格式化功能的方法
Jul 28 #PHP
使用php自动备份数据库表的实现方法
Jul 28 #PHP
PHP自定义函数判断是否为Get、Post及Ajax提交的方法
Jul 27 #PHP
PHP 7安装使用体验之性能大提升,兼容性强,扩展支持不够(升级PHP要谨慎)
Jul 27 #PHP
laravel 5.4中实现无限级分类的方法示例
Jul 27 #PHP
You might like
mysql中存储过程、函数的一些问题
2007/02/14 PHP
php中url传递中文字符,特殊危险字符的解决方法
2013/08/17 PHP
cakephp打印sql语句的方法
2015/02/13 PHP
深入理解PHP中的Streams工具
2015/07/03 PHP
ThinkPHP整合datatables实现服务端分页的示例代码
2018/02/10 PHP
FireFox与IE 下js兼容触发click事件的代码
2008/11/20 Javascript
让IE6支持min-width和max-width的方法
2010/06/25 Javascript
JS函数实现动态添加CSS样式表文件
2012/12/15 Javascript
JS 实现Json查询的方法实例
2013/04/12 Javascript
什么是Node.js?Node.js详细介绍
2014/06/01 Javascript
JS日期加减,日期运算代码
2015/11/05 Javascript
jQuery解决input元素的blur事件和其他非表单元素的click事件冲突问题
2016/08/15 Javascript
总结Javascript中数组各种去重的方法
2016/10/04 Javascript
微信小程序开发之视频播放器 Video 弹幕 弹幕颜色自定义实例
2016/12/08 Javascript
w3c编程挑战_初级脚本算法实战篇
2017/06/23 Javascript
node.js 发布订阅模式的实例
2017/09/10 Javascript
Angular中的$watch方法详解
2017/09/18 Javascript
echarts整合多个类似option的方法实例
2018/07/10 Javascript
在vue项目中集成graphql(vue-ApolloClient)
2018/09/08 Javascript
Vue过滤器,生命周期函数和vue-resource简单介绍
2021/01/12 Vue.js
简单介绍Python中用于求最小值的min()方法
2015/05/15 Python
详谈Numpy中数组重塑、合并与拆分方法
2018/04/17 Python
python生成多个只含0,1元素的随机数组或列表的实例
2018/11/12 Python
python实现滑雪游戏
2020/02/22 Python
call在Python中改进数列的实例讲解
2020/12/09 Python
加大码胸罩、内裤和服装:Just My Size
2019/03/21 全球购物
澳大利亚礼品卡商店:Gift Card Store
2019/06/24 全球购物
四风存在的原因分析
2014/02/11 职场文书
考核工作实施方案
2014/03/30 职场文书
松材线虫病防治方案
2014/06/15 职场文书
2014年度培训工作总结
2014/11/27 职场文书
百年孤独读书笔记
2015/06/29 职场文书
Pytorch使用shuffle打乱数据的操作
2021/05/20 Python
oracle索引总结
2021/09/25 Oracle
利用Python多线程实现图片下载器
2022/03/25 Python
Python 第三方库 openpyxl 的安装过程
2022/12/24 Python