使用DBSQL作为PHP PDO数据库引擎
PHP Data Object(PDO)是PHP访问数据库的一个扩展库,也是目前PHP程序访问数据库的标准.PDO定义了一组访问数据库的抽象方法. 不论何种类型的数据库, 我们只用同样的接口访问就可以了.采用PDO接口的PHP程序具有独立性和开放性:与具体的数据库系统无关,与具体的操作系统无关.
本文介绍了如何在Linux环境下应用Berkeley DB SQL(DBSQL)作为PHP PDO数据库引擎.考虑到会有许多SQLite用户迁移到DBSQL以获得更高的并发性和性能,本文创建了一个SQLite3数据库并展示了如何将已有SQLite3数据库迁移到DBSQL上来.
1. 安装PDO SQLite
本文假定您已经有了一个可工作的Apache+PHP 5.x环境.此外,如果你没有一个可工作的PDO SQLite, 那么需要安装一个.以Ubuntu机器为例,我们只需要使用aptitude安装php5-sqlite即可.其它环境请Google/Baidu一下适用的安装步骤.
安装完成后,应该检查一下/usr/lib/php5/20060613+lfs目录下(该目录可能根据环境有所不同,以下一律以本机环境/usr/lib/php5/20060613+lfs为例)是否有pdo.so和pdo_sqlite.so文件:
debian:/usr/lib/php5/20060613+lfs# ls pdo.so pdo_sqlite.so
2. 数据库迁移
(是为了模拟SQLite3用户的迁移场景,本步骤准备了一个SQLite3数据库,并将其迁移到DBSQL数据上来)
创建SQLite3数据库/tmp/test.db,将以下文本保存为/tmp/create.sql:
CREATE TABLE Friends ([id] integer, [LastName] text, [FirstName] text, [Phone] text, CONSTRAINT [Index1] PRIMARY KEY ([id])); INSERT INTO Friends (id, LastName, FirstName, Phone) VALUES (1, 'Zhang', 'San', '1234-0000'); INSERT INTO Friends (id, LastName, FirstName, Phone) VALUES (2, 'Li', 'Si', '1234-0001'); INSERT INTO Friends (id, LastName, FirstName, Phone) VALUES (3, 'Wang', 'Wu', '1234-0002');
使用sqlite3 shell创建一个test.db:
/tmp$ cat create.sql | sqlite3 test.db
到现在为止,我们已经模拟了现实场景:我们有一个可工作的PDO(SQLite)和数据库文件.接下来我们将它迁移到DBSQL上来:
a) 按照http://www.bdbchina.com/2010/04/在unixlinux平台上应用berkeley-db-11gr2-sql/,编译得到库libdb_sql-5.0.so(路径:$HOME/db-5.0.21/build_unix/.libs/libdb_sql-5.0.so)
b) 按照以下步骤dump SQLite3数据库到test.dump文件:
/tmp$ sqlite3 test.db SQLite version 3.6.22 Enter ".help" for instructions Enter SQL statements terminated with a ";" sqlite> .output test.dump sqlite> .dump sqlite> .quit
c) 使用DBSQL shell加载dump文件.加载完成后在/tmp目录下生成新的test.db及test.db-journal:
/tmp$ mv test.db test.db.bak /tmp$ $HOME/db-5.0.21/build_unix/dbsql test.db Berkeley DB 11g Release 2, library version 11.2.5.0.21: (March 30, 2010) Enter ".help" for instructions Enter SQL statements terminated with a ";" dbsql> .read test.dump dbsql> .quit /tmp$ ls create.sql test.db test.db-journal test.dump test.db.bak
3. 安装PDO DBSQL
本步骤需要root权限.具体做法如下:
a)复制libdb_sql-5.0.so到php lib目录下并改名为libdb_sql-50.so:
cp /build_unix/.libs/libdb_sql-5.0.so /usr/lib/php5/20060613+lfs/libdb_sql-50.so
b)使用vi编辑usr/lib/php5/20060613+lfs/pdo_sqlite.so(这是一个二进制文件),并将文件中的libsqlite3.so.0替换为libdb_sql-50.so(只有一处替换).这使得pdo_sqlite.so连接到DBSQL,而不是SQLite3.
c)把usr/lib/php5/20060613+lfs/增加到HTTP Server的LD_LIBRARY_PATH环境变量中.否则Web Server无法找到libdb_sql-50.so. 不同的HTTP Server的具体做法不同.以Apache2为例,编辑/etc/apache2/envvars,增加一行:
export LD_LIBRARY_PATH=/usr/lib/php5/20060613+lfs/
d)重启HTTP Server,仍以Apache2为例:
/etc/init.d/apache2 restart
4. 使用PDO DBSQL
创建好数据库后,我们用PDO接口来访问它:将以下PHP程序保存到HTTP服务器的根目录(如htdoc/)目录下并命名为pdo_dbsql.php:
<?php
try {
$db = new PDO("sqlite:/tmp/test.db");
/*** The SQL SELECT statement ***/
$sql = "SELECT * FROM Friends";
$db->exec($sql);
/*** Print Query Results ***/
echo "<table><tr><th>ID</th><th>Last Name</th>";
echo "<th>First Name</th><th>Phone</th></tr>";
foreach ($db->query($sql) as $row) {
echo "<tr>";
echo "<td>".$row["id"]."</td>";
echo "<td>".$row["LastName"]."</td>";
echo "<td>".$row["FirstName"]."</td>";
echo "<td>".$row["Phone"]."</td>";
echo "</tr>";
}
echo "</table>";
/*** close the database connection ***/
$db = null;
} catch(PDOException $e) {
echo $e->getMessage();
}
?>
使用Web浏览器访问我们编写好的pdo_dbsql.php(如http://192.168.1.131/pdo_dbsql.php),即可看到使用PDO的运行结果:

5. 结束语
本文我们介绍了如何将PDO数据引擎从SQLite迁移到DBSQL上来.对于直接采用DBSQL的用户而言,数据迁移一步可直接跳过,直接创建新的DBSQL数据库就好了.DBSQL与SQLite相比具有更高的并发性和性能,是值得PHP开发者尝试的全新SQL数据库引擎.
不知道您文中实践所用的PHP版本是多少,我测试用的PHP版本是5.3.2,我在pdo_sqlite.so中并未找到libsqlite3.so.0。
后来我尝试在PHP编译配置参数中加上 –with-pdo-sqlite=shared,/opt/dbsql/,此时configure在检测 -lsqlite3时出错,我修改了一下configure文件,把它检测-lsqlite3的C程序修改成直接return 0,然后添加-lpthread -ldl -lrt 然后编译成功,也能够正常使用。不过我觉得我这种方法太不优雅了,也不知道会不会有其他问题,希望能有更标准的方法。
感谢中国研发团队的支持。
@好大的风
你好,我的PHP版本是PHP 5.2.6. 重新编译php的话工作量有点大了,不推荐.建议还是集中精力解决pdo_sqlite.so的问题.首先请您用”ldd pdo_sqlite.so”检查一下您的pdo_sqlite.so依赖于哪些库.必要时将输出结果贴在这里我们一起分析一下.谢谢!
我在arm linux 上用ex_access.c 编译出来的程序生成了一个库文件access.db, 然后用dbsql去查询, 输出如下, 麻烦帮忙分析一下,是编译的问题还是其他问题
#./dbsql access.db
/dev/shm/access.db: library build did not include support for locking
/dev/shm/access.db: library build did not include support for locking
/dev/shm/access.db: library build did not include support for locking
/dev/shm/access.db: library build did not include support for locking
/dev/shm/access.db: library build did not include support for locking
/dev/shm/access.db: PANIC: Operation not supported
/dev/shm/access.db: unable to join the environment
Error: unable to open database “access.db”: database disk image is malformed
你好,ex_access.c程序生成的db文件是Berkeley DB数据库文件,并非合法的Berkeley DB SQL数据库文件。因此不能用DBSQL这个工具打开。