PHP网页设计PEAR:创立两头的数据库使用层1
掌握静态网页的制作技术是学习开发网站的先决条件,这一点就讲到这里,因为这篇文章不是教程文章,也就不对技术进行深入的刨析了。创立|数据|数据库内容:
1、 甚么是DB类
2、 为何要设计笼统的两头数据层
3、 DB的利用入门
4、 DB_Common 利用参考
5、 更进一步,创立你本人的两头数据库使用层
6、 DB的缺乏
7、参考资本
关于作者
相干内容:
1、用PEAR来写你的下一个php法式
2、经常使用模块
3、利用PHPDoc轻松创立你的PEAR文档
潘凡 (nightsailer@hotmail.com)
北京赛迪网信息手艺无限公司
2001 年 8 月
关于PHP的使用法式来讲,90%以上需求和数据库来打交道。那末,你是若何把持数据库的?当你的后端数据库晋级或变迁后,你的这些法式是不是可以随之光滑地晋级和挂接呢?假如你正在思索这个成绩,那末无妨和我来会商一下,若何利用PEAR中的DB类来创立与数据库有关的数据库使用层。
1、 甚么是DB类
咱们起首复杂地懂得一下DB类。DB类是PEAR中停止数据操作的几个类的纠合,它的次要目标是供应一个一致的,笼统的数据接口,这个接口与后真个数据库是有关的。因而,假如你的使用法式利用这个通用的接口来停止数据库的操作,那末就可以够光滑地切换到分歧的数据库上面,如MYSQL,SQL,SYBASE等等。实践上,DB类但愿可以起到复杂的相似ODBC或是PERL中的DBI的感化。说到这里,不能不提一下PHP中的另外一个优异的库:ADODB。ADODB也和DB一样,供应了一个笼统的两头层,并且ADODB所撑持的后端数据库要比DB多(最少今朝如斯),不外ADODB没有直接利用PEAR的一些特征,只是吸收了PEAR的很多思惟,包含DB,因而两者的利用办法有很多类似的中央。我不想评论两者孰优孰劣,人人可以依据团体的喜欢来利用。
2、 为何要设计笼统的两头数据层
在具体会商DB的利用之前,咱们先会商一下为何要设计两头的数据层,由于这意味着你需求作出一些就义和妥协,好比,你需求多写一些代码,有的局限于特定命据库的特征将没法直接利用。
咱们回想一下咱们曩昔的做法,若何毗连到MYSQL数据库?这切实其实是个小儿科的成绩,上面的代码你必定很熟习:
<?php
/**
* 毗连到MYSQL数据库
*/
$host = "localhost";
$user = "root";
$passwd = "";
$persistent = 1;
if ($persisternt){
$conn = mysql_connect($host,$user,$passwd);
}else {
$conn = mysql_pconnect($host,$user,$passwd);
}
?>
好了,如今创立了数据库毗连,咱们可使用它来停止数据库的操作,咱们能够利用相似的代码:
<?php
function sql_exec($sql) {
global $db_Name;
$result = mysql_db_query($db_dbName,$sql);
if (!$result) {
echo mysql_errno(). ": ".mysql_error(). "<br>$sql<br>";
exit();
}
return $result;
}
$db_Name = "test";
$sql = "select * from users";
$result = sql_exec($sql);
while( $row = mysql_fetch_row($result) ){
echo "姓名:$row 性别:$row 岁数 $row<br>";
}
mysql_free_result($result);
?>
看起来很不错,是吗?你能够在你的代码里利用良多相似的代码片断。然而,不要太乐意,成绩来了。假设,俄然,你的数据库需求从MYSQL迁徙到其余数据库平台,好比ORACLE,SYBASE。迁徙的缘由良多,或许是你的老板突发奇想,以为如许能卖个好代价,或是你的数据猛增,招致MYSQL的功能下落,总之,迁徙是事在必行了。你怎样做,你或许会想,呵呵,这复杂,把相干的函数交换一下不就好了。
听起来复杂,然而……起首,毗连数据库的函数要改,需求把mysql_connect和mysql_pconnect交换成OCILogon和OCIPLogon。mysql_errno和mysql_error()固然不克不及利用,你需求从OCIError()前往的数组中提取呼应的信息。
这还不是太糟,最糟的是相干的mysql_fetch_row,mysql_fetch_array等语句遍及于你的很多代码函数和过程当中,你需求一一查找,剖析,然后从头交换或编写响应的ORACLE的版本。假如,你的数据库操作是集中在一个某一个模块或类中,这项任务还可以承受,不然,等于你从头浏览和修正了绝大局部的代码。即便这个不幸的人不是你,那末他也会背后咒骂你的;=)
以上,咱们回想了咱们之前的做法,和能够带来的不幸。那末,假如利用DB类来做相似的操作,应当是甚么样的呢?上面是响应的DB版本代码:
<?php
include_once "DB.php";
/*
* 毗连到数据库
*/
$db_host = "localhost";
$db_user = "root";
$db_passwd = "";
$db_dbName = "test";
$PersistentConnection = 1 ;
$db_type ="mysql";
$db_proto ="";
$db = DB::connect("$db_type://$db_user@$db_passwd:$db_host/$db_dbName",$db_options);
if( DB::isError($db) ){
die "没法毗连数据库,毛病缘由:".DB::errorMessage($db);
}
function sql_exec($sql) {
global $db;
$result = $db->query($sql);
if (DB::isError($result)){
echo "产生数据库毛病:".DB::errorMessage($result);
exit();
}
return $result;
}
/////////////////////////////////////////////
$sql = "select * from users";
$result = sql_exec($sql);
while( $row = $result->fetchRow() ){
echo "姓名:$row 性别:$row 岁数 $row<br>";
}
?>
除毗连数据库局部,其他的看起来只是有一些巨大的变更,失足处置利用的是PEAR相似的体例(isError),实践上也是从PEAR承继来的。一样的情形,假如你要把数据库从mysql迁徙到其余模式,此次假设说是PostegreSQL,一个LINUX中很优异的数据库,你所做的只是改动一行代码:
$db_type ="mysql";
酿成:
$db_type ="pgsql";
其他的,不必变化。怎样,晋级的感到是否是很清新呢,你可以用剩下的工夫好好研读其他的代码,或和我持续往下会商DB的利用办法。
3、 DB的利用入门
DB类由3局部构成:
DB.php 这是前端接口,在DB类里供应了很多"静态"的公用办法,咱们普通只需求INCLUDE_ONCE这个文件就能够了。
DB/common.php 这是后端数据库的通用笼统类,分歧的数据库的后端类需求承继并完成这个类中界说的公用办法和属性,假如你的数据库不被撑持,你可以本人编写一个撑持类,如许,你的使用法式就能够迁徙过去了。
DB/storage.php 这是一个帮助的东西,它可以把SQL查询做为对象前往,同时可以保护这些对象,在对象改动的时分,响应地更新数据库。
DB/ifx.php
mssql.phpMs SQL Server撑持类
oci8.php Orcale 8i撑持类
pgsql.phpPostegreSQL撑持类
sybase.php Sybase撑持类
ibase.phpibase撑持类
msql.php mSQL 撑持类
mysql.phpmysql撑持类
odbc.php odbc 撑持类
这些是响应后端数据库的撑持类了。响应详细的数据库的操作是由这些撑持类来完成的。
上面,咱们起首具体引见DB.PHP中的一些"静态"办法:
connect()办法
这个办法是最主要的静态办法了,咱们经由过程失掉一个DB_COMMON对象,而且毗连到响应的数据库。这个办法的原型以下:
function &connect($dsn, $options = false)
$dsn是数据源称号(data source name)的缩写,可所以字符串,或是特定的数组模式。
普通来讲,$dsn是一个字符串,它的格局以下:
phptype(dbsyntax)://username:password@protocol+hostspec/database
*phptype:php后端数据库的类型称号(如mysql, odbc 等等.)
*dbsyntax: 数据库所利用的SQL语法尺度,普通不必。
*protocol: 利用的通信协定。(如tcp, unix 等等.)
*hostspec: 数据库地点的主机的描写。(模式是:主机名[:端标语])
*database: 数据库的称号。
*username: 上岸的用户名。
*password: 上岸的暗码。
关于DSN,经常使用的模式以下:
*phptype://username:password@protocol+hostspec:110//usr/db_file.db
*phptype://username:password@hostspec/database_name
*phptype://username:password@hostspec
*phptype://username@hostspec
*phptype://hostspec/database
*phptype://hostspec
*phptype(dbsyntax)
*phptype
关于省略的局部,将利用缺省值。
固然,$dsn也能够是一个数组,数组的模式以下:
$dsn = array(
'phptype'=> 'mysql',
'dbsyntax' => '',
'protocol' => '',
'hostspec' => 'localhost',
'database' => 'test',
'username' => 'root',
'password' => ''
)
$options 是数据库的选项,夹杂型。假如是布尔型,那末普通来讲,这个参数指明是不是利用耐久性毗连(persistent connect),假如后端数据库撑持,当$options是TRUE的时分,将利用耐久性毗连。假如是数组,那末暗示这是特定的后端数据库的选项,这些选项将传递到DB_common类中的set_option办法中,后端数据库经由过程完成或重载这个办法,可以本人决意若何利用这些选项。
isError($value)
这个办法用来判别DB的一些办法前往的了局是不是是一个毛病对象,你可使用这个办法来剖断某个操作的了局是不是是抛出了异常。
固然,假如你的使用法式从是PEAR承继的,也能够直接利用PEAR的isError来判别,特别是当你的法式中抛出的异常的多是数据库之外的异常的时分,这个办法只能判别是不是是DB_Errro对象,其他的PEAR_Error对象是没法辨认出的。
function isWarning($value)
这个办法是判别DB办法的前往了局是不是是一个正告。和毛病分歧的是,正告不是致命的,所以仍可以持续履行下去。
function errorMessage($value)
一旦肯定呈现了毛病,那末可使用这个办法来获得响应的毛病信息,上面是DB中的预界说的毛病信息:
DB_ERROR => "unknown error",
DB_ERROR_ALREADY_EXISTS => "already exists",
DB_ERROR_CANNOT_CREATE => "can not create",
DB_ERROR_CANNOT_DELETE => "can not delete",
DB_ERROR_CANNOT_DROP => "can not drop",
DB_ERROR_CONSTRAINT => "constraint violation",
DB_ERROR_DIVZERO => "division by zero",
DB_ERROR_INVALID => "invalid",
DB_ERROR_INVALID_DATE => "invalid date or time",
DB_ERROR_INVALID_NUMBER => "invalid number",
DB_ERROR_MISMATCH => "mismatch",
DB_ERROR_NODBSELECTED => "no database selected",
DB_ERROR_NOSUCHFIELD => "no such field",
DB_ERROR_NOSUCHTABLE => "no such table",
DB_ERROR_NOT_CAPABLE => "DB backend not capable",
DB_ERROR_NOT_FOUND => "not found",
DB_ERROR_NOT_LOCKED => "not locked",
DB_ERROR_SYNTAX => "syntax error",
DB_ERROR_UNSUPPORTED => "not supported",
DB_ERROR_VALUE_COUNT_ON_ROW => "value count on row",
DB_OK => "no error",
DB_WARNING => "unknown warning",
DB_WARNING_READ_ONLY => "read only"
assertExtension($name)
静态载入PHP的数据库扩大。$name是你的PHP扩大的称号,不包括扩大名(如.dll,.so)。
当你需求让PHP载入某个数据库的扩大,然而你没有权限修正php.ini的时分,可使用这个函数。
固然,DB外部也是主动挪用这个办法来载入所需的PHP数据库的扩大。
好比:你假如需求加载oracle的扩大,那末可以如许利用:
<?php
include_once "DB.php";
if ( DB::assertExtension("php_oci8") ){
echo "oracle 8扩大加载胜利!";
}else {
die "没法加载oracle 8扩大";
}
?>
以上是在DB类中界说的"静态"办法,所谓静态办法,是指你可以不需求构建对象,就能够直接利用,而且只需你指明DB::,你可以在任何中央直接挪用这些办法。
在DB.php中,除DB外,也有几个十分主要的类,在后端数据库中也利用了这些类:
DB_Error
这个类是从PEAR_Error承继来的,在数据库操作中,关于呈现的致命的毛病,普通会抛出这个毛病。
构建函数:
function DB_Error($code = DB_ERROR, $mode = PEAR_ERROR_RETURN, $level = E_USER_NOTICE, $debuginfo = null)
$code是DB毛病代码,$mode决意毛病处置的形式,缺省是前往,$level 毛病级别,
$debuginfo是附加的调式信息,如方才履行的SQL语句等等。
DB_Warning
相似DB_Error。
DB_result
这长短常主要的类。
当履行响应的SQL查询后,后真个数据库类将前往一个DB_result的对象实例,你可使用这个类的办法来取得查询了局的数据。这个类实践上是后端数据库了局集的包装,这里说的办法,在实践运转中是直接挪用了后端数据库的同名的办法,不外,关于咱们来讲,利用这个包装类会感到更天然一些。
function fetchRow($fetchmode = DB_FETCHMODE_DEFAULT)
获得一行数据,$fetchmod是获得数据的形式,假如没有指定,那末利用缺省体例。其他的体例咱们在前面会商DB_Common接口的时分会具体会商。
function fetchInto(&$arr, $fetchmode = DB_FETCHMODE_DEFAULT)
获得一行数据,同时追加到给定的$att数组中。$att是要追加到的数组,它是依照援用体例传递的。
function numCols()
获得了局集的列数。假如失足,前往DB_Error对象。
function numRows()
获得了局集的行数。假如失足,前往DB_Error对象。
function free()
释放了局集所占用的资本。
至此,咱们已进修了DB根基的利用办法,上面咱们复杂温习一下,关于个中没有见到的办法,咱们在前面会具体引见:
毗连数据库:
<?php
$db = DB::connect("$db_type://$db_user@$db_passwd:$db_host/$db_dbName",$db_options);
if (DB::isError($db)){
echo "数据库毗连毛病:".DB::errorMessage($db)."<br>";
exit();
}
/* 查询1 */
$sql = "select * from user_log";
$result = $db->query($sql);
if (DB::isError($result) ){
echo "数据库毛病:".DB::errorMessage($result);
exit();
}
$colCount = $result->numCols();
echo "<tr><td colspan=\"".$colCount."\">共找到".$result->numRows()."位用户</td></tr>";
while($row = $result->fetch()){
echo "<tr><br />";
for($i=0;$i<$colCount;$i++){
echo "<td>".$row[$]."</td><br />";
}
echo "</tr><br />";
}
$result->free();
$db->disconnect();
?>
4、 DB_Common 利用参考
DB_Common类是一个通用的接口,DB跨数据库平台的才能是经由过程完成这个接口来做到的。假如你的数据库不在DB撑持之列,你可以本人编写一个类承继DB_Common类,完成这些接口的函数。
function toString()
前往以后类的字符串描写,格局是类名:(phptype="",dbsyntax=""),通常为相似于:
DB_mysql:(phptype=mysql,dbsyntax=)
function quoteString($string)
圈引一个字符串,使之在查询中可以平安地放在单引号的分界符之间。普通关于字符型的字段,咱们查询的时分利用''作为分隔符,因而假如字符串中有'则会失足,这个函数把字符串中的'交换成\'.
function provides($feature)
指明以后DB的后端法式是不是完成了给定的特征,前往布尔值。$feature是功效的明称,通常为:"prepare","pconnect","transactions".在后端法式的构建函数中应当设置这些值。例子:
if($db->provider("transactions")){
//撑持事务
}else {
//不撑持事务
}
function errorCode($nativecode)
用于将后端数据库发生的毛病代码映照到DB的通用毛病代码中去。外部挪用。后端数据库在构建函数中应当初始化$errorcode_map属性。例子(mysql):
//在DB_mysql的构建函数中
$this->errorcode_map = array(
1004 => DB_ERROR_CANNOT_CREATE,
1005 => DB_ERROR_CANNOT_CREATE,
1006 => DB_ERROR_CANNOT_CREATE,
1007 => DB_ERROR_ALREADY_EXISTS,
1008 => DB_ERROR_CANNOT_DROP,
1046 => DB_ERROR_NODBSELECTED,
1050 => DB_ERROR_ALREADY_EXISTS,
1051 => DB_ERROR_NOSUCHTABLE,
1054 => DB_ERROR_NOSUCHFIELD,
1062 => DB_ERROR_ALREADY_EXISTS,
1064 => DB_ERROR_SYNTAX,
1100 => DB_ERROR_NOT_LOCKED,
1136 => DB_ERROR_VALUE_COUNT_ON_ROW,
1146 => DB_ERROR_NOSUCHTABLE,
);
你的留言本应该加入注册以及分页功能了,而如果你更强的话,UI(用户界面)也可以加强,完成之后,感觉是不是特有成就感?不管怎么样,咱好歹是写了一个动态网站程序了,放在自己的网站上耍耍吧。 学好程序语言,多些才是王道,写两个小时代码的作用绝对超过看一天书,这个我是深有体会(顺便还能练打字速度)。 最后祝愿,php会给你带来快乐的同时 你也会给他带来快乐。 如果你可以写完像留言板这样的程序,那么你可以去一些别人的代码了, 有时候汉字的空格也能导致页面出错,所以在写代码的时候,要输入空格最好用引文模式。 当留言板完成的时候,下步可以把做1个单人的blog程序,做为目标, 个人呢觉得,配wamp 最容易漏的一步就是忘了把$PHP$目录下的libmysql.dll拷贝到windows系统目录的system32目录下,还有重启apache。 首推的搜索引擎当然是Google大神,其次我比较喜欢 百度知道。不过搜出来的结果往往都是 大家copy来copy去的,运气的的概率很大。 做为1门年轻的语言,php一直很努力。 开发工具也会慢慢的更专业,每个公司的可能不一样,但是zend studio是个大伙都会用的。 爱上php,他也会爱上你。 我还是推荐用firefox ,配上firebug 插件调试js能省下不受时间。谷歌的浏览器最好也不少用,因为谷歌的大侠们实在是太天才啦,把一些原来的js代码加了一些特效。 做为1门年轻的语言,php一直很努力。 做为1门年轻的语言,php一直很努力。 对于初学者来说不推荐去拿钱买的。当然如果一个网站你经常去用,而且里面的资料也比较有用,最好还是买个会员比较好,毕竟那些也是别人的工作成果。 建议加几个专业的phper的群,当然啦需要说话的人多,一处一点问题能有人回答你的,当然啦要让人回答你的问题,平时就得躲在里面聊天,大家混熟啦,愿意回答你问题的人自然就多啦。 你很难利用原理去编写自己的代码。对于php来说,系统的学习我认为还是很重要的,当你有一定理解后,你可你针对某种效果研究,我想那时你不会只是复制代码的水平了。 开发工具也会慢慢的更专业,每个公司的可能不一样,但是zend studio是个大伙都会用的。 真正的方向了,如果将来要去开发团队,你一定要学好smarty ,phplib这样的模板引擎, 如果你可以写完像留言板这样的程序,那么你可以去一些别人的代码了,
页:
[1]
2