[摘要] MySQL是一个可用于各种流行操作系统平台的关系数据库系统,具有客户机/服务器体系结构的分布式数据库管理系统。其客户机程序的API主要是用Perl、PHP、Java、Python、C、Tcl等,本文主要探讨结合公司科技成果管理中的数据,在Linux系统下MySQL数据库接口-PHP API的开发与应用,充分发挥MySQL功能强、使用方便、运行速度快、安全性强等特点。
关键词:MySQL;数据库;Linux;数据库接口;PHP API;编程;科研管理
0. 引言
数据库技术作为现代软件工业的基石之一,当今市场上有多种数据库产品可供选择:Oracle、SQL Server、DB2、Informix、Sybase、 MySQL、PostgreSQL等,然而哪种更适合开发的需要呢?目前众多软件开发应用都是针对一些中小型部门而已,而那些大型数据库(Oracle、DB2)昂贵的价格难以承受,主要用于旗舰型数据库服务器。对一些中小型数据库开发,MySQL、PostgreSQL都是很不错的选择。在公司科技成果管理中的数据完全可以用MySQL作为数据库服务器,本文主要探讨结合公司科技成果管理中的数据,在Linux系统下MySQL数据库接口-PHP API的开发与应用,充分发挥MySQL功能强、使用方便、运行速度快、安全性强等特点。
数据库接口编程环境:RedHat Linux 7.2, MySQL 3.23.51, Apache 1.3.22+PHP 4.06。
1. MySQL数据库简介
MySQL是一个可用于各种流行操作系统平台的关系数据库系统,具有客户机/服务器体系结构的分布式数据库管理系统。MySQL完全适用于网络,是一个真正的多用户、多线程的SQL数据库服务器。SQL(结构化查询语言)是世界上最流行的和标准化的数据库语言。MySQL是以一个客户机/服务器结构的实现,它由一个服务器守护程序mysqld和很多不同的客户程序及库组成。
MySQL有许多吸引人之处:
① 速度:运行速度很快,开发者声称MySQL可能是目前能得到的最快的数据库;
② 容易使用:一个高性能切相对简单的数据库系统;
③ 价格:在诸如UNIX、Linux这样的操作系统上是免费的,而在Windows系统上,其客户机程序和客户机程序库是免费的;
④ 支持查询语言:MySQL可以利用SQL,也可利用支持ODBC的应用程序;
⑤ 性能:许多客户机可同时连接到服务器,多个客户机可同时使用多个数据库,可利用几个输入查询并查看结果的界面来交互式地访问MySQL(命令行客户机程序、Web浏览器或X Window System客户机程序);此外,还有各种语言(如Perl、Java、PHP、C、Python、Tcl等)编写界面;
⑥ 连接性和安全性:MySQL是完全网络化的,其数据库可在Internet/Intranet的任何地方访问,可以和任何地方的任何人共享数据库,而且还能进行访问控制;
⑦ 可移植性:MySQL可运行在各种版本的UNIX以及其他非UNIX的系统(如Windows和OS/2)上;
⑧ 开放式的分发:很容易获得,只要通过网络下载即可。
MySQL支持大量的列类型,它可以被分为3类:数字类型、日期和时间类型以及字符串(字符)类型。多种列类型:1、 2、 3、4、和 8 字节长度的有符号/无符号整数、FLOAT、DOUBLE、CHAR、VARCHAR、TEXT、BLOB、DATE、TIME、DATETIME、TIMESTAMP、YEAR、SET和ENUM类型。
对于MySQL在RedHat Linux 7.2系统下的安装设置和操作管理,由于介绍这些的书籍文章都相当多,在此也就不多说,望读者查看相关资料。
2.数据库的设计
在公司厂级科技成果的管理中,主要牵涉到科研课题的实施、考核、鉴定、评审和奖励。我们考虑的科技成果数据是鉴定评审中的技术资料,科技成果申请鉴定必须提供较详细且反映技术水平的资料,以及主要完成人名单。
2. 1建立数据表关系图
其必备资料--《科技成果鉴定证书》、《技术总结》、《工作总结》、《使用报告》等,这些资料内容多,然而我们只需要些能反映科技成果技术水平的资料存入数据库,同时还需建立一个主要完成人的数据表。根据这些,我们可以确定《科技成果鉴定证书》中的内容基本符合上述的要求,为此,可以建立如下数据表:
① 科技成果表:存储每项成果的具体内容,能充分反映成果的技术水平及等级;
② 主要完成人表:存储每项成果主要完成人的简要内容,可为以后科技人员查询、统计,也可成为一个科技人员数据库;
③ 提供的文件资料表:存储文件资料的简要信息,可审核资料的齐全性。
科技成果表与主要完成人表、文件资料表都是一对多(1:n)的关系,如图2.1是三个数据表的关系图:
图 2.1 数据表关系图
2.2建立数据表结构
MySQL使用一种称为SQL(Structured Query Language)的语言,SQL是当今标准数据库语言,所有主要的数据库系统都使用它。
用CREATE TABLE语句来创建表结构,其一般格式为:
CREATE TABLE tbl_name ( column_specs )
其中tbl_name为表的名称,column_specs给出表中列的说明。
根据三个数据表的关系,为符合公司的型号研究及科技成果管理规定,可依次建立三个数据表结构。
Prod表的CREATE TABLE语句如下所示:
#数据表'科技成果'的结构
CREATE TABLE prod (
prod_id smallint(6) unsigned NOT NULL auto_increment,
prod_title varchar(60) NOT NULL default '',
prod_sn varchar(10) NOT NULL default '',
prod_principal varchar(20) NOT NULL default '',
prod_principal_pos varchar(20) NOT NULL default '',
prod_member_count tinyint(2) unsigned NOT NULL default '0',
prod_file_count tinyint(2) unsigned NOT NULL default '0',
prod_depart varchar(30) NOT NULL default '',
prod_cooperation_depart varchar(30) NOT NULL default '',
prod_finish_time date NOT NULL default '0000-00-00',
prod_content text NOT NULL,
prod_app text NOT NULL,
prod_tech_level text NOT NULL,
prod_benefit text NOT NULL,
prod_type enum('直八型机','直十型机','直十一型机','S-92','汽车','综合') NOT NULL default '综合',
prod_conclusion text NOT NULL,
prod_appraisal_time date NOT NULL default '0000-00-00',
prod_grade enum('一等','二等','三等') NOT NULL default '一等',
prod_remark varchar(200) NOT NULL default '',
PRIMARY KEY (prod_id),
UNIQUE KEY prod_id (prod_id),
KEY prod_title (prod_title)
) TYPE=MyISAM;
prod_member表的CREATE TABLE语句如下所示:
#数据表'主要完成人'的结构
CREATE TABLE prod_member (
member_id smallint(4) unsigned NOT NULL auto_increment,
prod_id smallint(4) unsigned NOT NULL default '0',
member_order tinyint(2) unsigned NOT NULL default '0',
member_name varchar(10) NOT NULL default '',
member_age varchar(10) NOT NULL default '',
member_degree enum('博士','硕士','本科','专科','其他') NOT NULL default '本科',
member_prof varchar(20) NOT NULL default '',
member_depart varchar(30) NOT NULL default '',
member_offer varchar(100) NOT NULL default '',
PRIMARY KEY (member_id),
UNIQUE KEY member_id (member_id),
KEY prod_id (prod_id),
KEY member_name (member_name)
) TYPE=MyISAM;
prod_file表的CREATE TABLE语句如下所示:
#数据表'提供的文件资料'的结构
CREATE TABLE prod_file (
file_id smallint(6) unsigned NOT NULL auto_increment,
prod_id smallint(4) unsigned NOT NULL default '0',
file_name varchar(30) NOT NULL default '',
file_pages tinyint(3) unsigned NOT NULL default '0',
file_writer varchar(10) NOT NULL default '',
file_offer varchar(20) NOT NULL default '',
PRIMARY KEY (file_id),
UNIQUE KEY file_id (file_id),
KEY prod_id (prod_id)
) TYPE=MyISAM;
通过以上语句,建立了prod、prod_member及prod_file三个表,接下来应进行的是编写数据库接口程序,达到数据管理的目的。
3.利用PHP API实现MySQL数据库接口
PHP(PHP Hypertext Preprocesser的首字母缩写)是一种在服务器端执行的脚本语言,可以很好地和HTML融合,产生需要的文档。与大多脚本语言或编程语言(Perl、Python)一样,都是与平台无关,且是开放源代码。PHP是专门为WEB设计,在这领域非常优秀。支持多种数据库库,包括常用的Oracle、 mSQL、 Sybase、 Informix、 MySQL等等。
3.1平台与Web服务器
Linux不管是在服务器操作系统还是在桌面操作系统都有相当重要的地位,所体现出来的性能完全可以适应各种网络应用,在RedHat Linux 7.2系统环境下进行MySQL数据库接口开发,不但可以降低开发费用,而且可以更好发挥MySQL数据库的性能。
如果没有服务器,PHP做不了什么有意义的事,所以必须考虑到要用到的Web服务器。在Linux下,多数都是选择Apache作为Web服务器,当前最流行的组合是Apache + PHP + MySQL。图3.1所示为客户机与服务器的体系结构图。
图 3.1 客户机与服务器体系结构图
很多书籍也介绍过Apache+PHP的安装与设置,在此也不多说。
3.2 PHP访问MySQL数据库
任何访问MySQL数据库的PHP脚本都要做下面的事情:
① 连接到MySQL数据库服务器;
② 向MySQL数据库服务器发送SQL查询,并得到结果;
③ 用函数从由第二步返回的结果中获得数据;
④ 建立HTML表单,显示结果。
根据上述步骤,建立其程序框图,如图3.2所示。
有了程序框图之后,由于PHP自身的特点,可应用面向对象程序设计方法,对于PHP访问MySQL可封装成类:数据库连接类mysql_conn和数据结果类mysql_recordset。对于程序开发,许多开发者花费在代码调试和改写上的时间超过了编写代码的时间,以结构、组织方式和代码重用的形式应用到程序中来分析PHP需要对MySQL所要进行的操作。根据程序框图建立起类和实用程序关系图,如图3.3所示。采用了UML建模语言技术,方便地描述出各种包含关系和所编写的函数文件。
对图3.3说明如下:
· mysql_conn类和mysql_recordset类是抽象类,其中mysql_recordset类是由mysql_conn派生,即mysql_recordset类依赖于mysql_conn类。依赖关系(dependency)表示一个类要创建另一个类的实例或者调用另一个类的方法。
· 其他为非抽象类,是为实现PHP访问MySQL而写的实用程序-数据库的连接/关闭、获得查询结果、显示查询结果。
· 方法名字前面的加号("+")表示该方法是公用方法,可以被其他对象或者函数调用;减号("-")表示方法或者变量是私有的,只能由同一对象内部的成员函数访问。在PHP中方法和变量是公用的,但我们应该总是把变量看成私有,避免从对象外部直接访问变量。
通过如此的图形结构化,很明了地知道PHP API 是如何对MySQL数据库进行访问的。
3.3 PHP API实例
对于用户,需要在一个页面中尽可能浏览到他所需要的信息。一项科技成果除了要显示上述三个表的内容外,我们还可以为用户提供上一年的一些成绩不错的课题和那些多次获得科技进步奖的科技人员的简要信息。所以,一个页面中要显示五方面的内容,则要进行五次SQL查询。
在此主要对查询主要完成人所获成果数前十的SQL查询语句进行分析。一个科技人员可能完成过多项成果,然而要对这进行统计排序:
① GROUP BY column_list子句根据列表中给出的列对结果集进行分组,则通过GROUP BY member_name对相同姓名的科技人员进行分组,以区分每人所完成的课题项数。
② ORDER BY 确定怎样对结果排序,可以是列名、别名或按列选择列表内的位置进行引用,还可定一个表达式作为排序列。由于要统计完成课题数目,利用函数COUNT(*)来进行降序排序,即ORDER BY COUNT(*) DESC。
③ LIMIT子句可用来从SELECT语句的结果汇总选择部分行,因为只需要了解前十位完成课题数目较多的科技人员的简要信息,所以可用LIMIT 10来选前十位。
通过上面三方面叙述,可得出SQL语句:
$sql = "SELECT member_id, member_name, COUNT(*) FROM prod_member GROUP BY member_name ORDER BY 'COUNT(*)' DESC LIMIT 10";
其他几个SQL查询语句也可通过此类方法进行分析,然后得出相关的SQL语句。
根据唯一的成果ID号$prod_id,通过相关的查询获得信息。首先,建立初始化MySQL对象,进行连接,并对其初始化,即用mysql_begin() 可完成。然后,完成数据库查询操作,以数组的形式返回查询结果。最后,关闭数据库。以下为PHP API实现数据库接口的源代码,运行结果如图3.4所示:
<?php
//****************************************************************************//
//Manage the production of science and technology ,the software writen with //
//the langugae PHP and the database MySQL //
//****************************************************************************//
//$ID:prod_fact_detail.php V 0.10 2002-12-8 //
//Note: //
// (simple comment about this file) //
//****************************************************************************//
//Authors:JackyYan (banksir@sina.com) //
// Writen in ChangHe ($date) ($time) //
//****************************************************************************//
// Copyright (c) 2001-2003 JackyYan //
// This program is free software. You can redistribute it and/or modify //
//it under the terms of the GNU General Public License as published by //
//the Free Software Foundation; either version 2 of the License. //
//****************************************************************************//
……
$last_year = 0;
$early_year = 0;
//Search all the prods
//Function mysql_begin() defined in fun_db.inc.php
//连接MySQL数据库
mysql_begin();
//Get the year of last prod
$year_array = get_year($year, $result, $db_name."_prod", "prod_appraisal_time");
if (check_empty($prod_id)) {
$prod_id = check_int($prod_id);
$sql = "SELECT * FROM ".$db_name."_prod WHERE prod_id='$prod_id';";
//发出SQL查询,得到查询结果
$prod_array = get_array_list($result, $sql, 1, 1, "get_prodinfo_array");
$year_array["year"] = substr($prod_array[0]["prod_appraisal_time"], 0, 4);
if (is_array($prod_array)) {
//如果成果的查询结果存在,则继续查询主要完成人及文件资料
$member_sum = $prod_array[0]["prod_member_count"];
$file_sum = $prod_array[0]["prod_file_count"];
//Get the related file information(文件资料)
$sql = "SELECT * FROM ".$db_name."_prod_file WHERE prod_id='$prod_id';";
$prod_file_array = get_array_list($result, $sql, 1, $file_sum, "get_prodfile_array");
if (is_array($prod_file_array)) {
$i = 0;
foreach ($prod_file_array as $value) {
//Determined the number of file writen
if (!check_empty($value["file_offer"])) {
$i++;
}
}
$file_sum = $i;
}
//Get the related member(主要完成人)
$sql = "SELECT * FROM ".$db_name."_prod_member WHERE prod_id='$prod_id' ORDER BY member_order ASC;";
$prod_member_array = get_array_list($result, $sql, 1, $member_sum, "get_prodmember_array");
if (is_array($prod_member_array)) {
$i = 0;
foreach ($prod_member_array as $value) {
if (!check_empty($value["member_name"])) {
$i++;
}
}
$member_sum = $i;;
} else {
for ($i = 1; $i <= $member_sum; $i++) {
$prod_member_order[$i] = $i;
}
}
//Get all the members are not writen
if (is_array($prod_member_order)) {
$i = 1;
foreach ($prod_member_order as $value) {
$member_order[$i] = $value;
$i++;
}
}
}
} else {
if (isset($msg)) {
$Warning_msg = $msg;
} else {
$Warning_msg = ERROR_NEWS_ID_EMPTY;
}
$prod_array = set_style("massage_style", $Warning_msg);
}
//Get the grade is First(前一年厂级成果前十)
$year_02 = get_local_time("year")-1;
$sql = "SELECT prod_id, prod_title, prod_grade FROM " .$db_name."_prod WHERE prod_appraisal_time LIKE '$year_02%' ORDER BY prod_grade, prod_appraisal_time DESC LIMIT ".$lastdata_nums;
$array["prodtop"] = get_array_list($result, $sql, 1, $lastdata_nums, "get_prodlist_array");
//Get the most prod's member(主要完成人所获成果数前十)
$sql = "SELECT member_id, member_name, COUNT(*) FROM ".$db_name."_prod_member GROUP BY member_name ORDER BY 'COUNT(*)' DESC LIMIT ".$lastdata_nums;
$array["membertop"] = get_array_list($result, $sql, 1, $lastdata_nums, "get_prodmember_array");
//Function mysql_end() defined in fun_db.inc.php
//关闭MySQL数据库
mysql_end();
……
?>
4.结束语
MySQL 作为一个免费的数据库,虽然功能不是十分强大,且灵活性较差,完全可以满足一般应用软件的要求,特别是在当前的网络时代,可以构建出高性能、高稳定性的中小型网络数据库。通过多种API开发语言都可对MySQL编写数据接口,在软件的免费潮流中,Linux+MySQL+Apache+PHP是一个完美的结合。笔者用此方案成功地进行了开发,如昌河科研管理。
[参考文献、网站]
1.《MySQL网络数据库指南》 (美)Paul DuBois著,钟鸣 田晓涛等译 机械工业出版社 2000年8月
2.《PHP高级编程》(美)Jesus Castagnetto等著,薛忠胜等译 机械工业出版社2001年3月
3.《Linux高级编程》(美)Neil Matthew等著,叶小虎等译 机械工业出版社2002年1月
4.http://www.mysql.com(MySQL官方网站)
5.http://www.php.net(PHP官方网站)
6.http://www.linux.org(Linux官方网站)