近几年IT界软硬件“国产化”搞得很密集,给很多公司带来了商机。但是有些公司拿国外的代码改改换个皮肤,就是“自主知识产权”的国产软件,光明正大卖钱,这个有点…,还经常有丑闻露出,譬如某星浏览器、C某-IDE…
话不多说,最近有个项目需要国产化改造,业主方推荐了国产数据库—瀚高数据库,我们原来用的是MySQL社区版,业主方不认可。我去看了下,这个瀚高数据库就是拿开源的postgresql数据库改的,加了点三权分立、国密SM3/SM4啥的。
- 安装
到官网登记试用,然后几天内转了几个人,最后终于拿到安装包介质 hgdb-see_4.5.8-db43858_amd64.deb ,按照官方安装文档,有很多安装参数需要设置,那是为了服务器环境准备的,我们开发测试环境,就无所谓了。
在国产操作系统银河麒麟linux上 sudo dpkg -ihgdb-see_4.5.8-db43858_amd64.deb 即可安装。默认安装目录是/opt/highgo/。
安装完成后,记得安装jdk(有了就忽略),一会启动配置助手,需要jdk。
下一步,配置新实例,选择server安装的目录、data存放的目录,然后一直下一步到结束,中间的参数,可以拷贝出来另外,以备不时之需。
主要记住端口5866,三个用户sysdba/syssao/syssso设置同一个口令,否则容易忘记(生产环境切勿)。
结束后,要给linux的root用户和经常用的操作用户设置环境变量,否则很多操作不方便。
命令是 vi ~/.bashrc ,加入以下几行,保存退出,然后 source~/.bashrc 或重登录,让其生效。
export HGDB_HOME=/opt/highgo/hgdb-see-4.5.8export PGDATA=/root/dataexport PATH=$PATH:$HGDB_HOME/bin
- 启停数据库
启停需要sudo操作,或者直接用root用户操作。
通过服务启动。
[root@hgdb ~]$ systemctl start hgdb-see-4.5.8.service
通过服务停止。
[root@hgdb ~]$ systemctl stop hgdb-see-4.5.8.service
通过数据库命令启动。
[root@hgdb ~]$ pg_ctl start -D /root/data
通过数据库命令停止。
[root@hgdb ~]$ pg_ctl stop -D /root/data
- 本机基本管理操作
瀚高数据库自带了一个sql developer,进入目录/opt/highgo/hgdbdeveloper/bin,sudo ./hgdbdeveloper即可启动GUI界面,可以进行创建数据库、建立用户、建表、查询等操作。
在这之前,我用了跨平台的dbeaver来连接hgdb,用的postgre默认的jdbc jar都连不上,可能是hgdb改了jdbc的认证方式(比如加了sm3 、sm4)。他自带驱动在这里。
root@longware-ubuntu:/opt/highgo/hgdb-see-4.5.8/etc/drivers# lsDotNET JDBC ODBC
- 本机SQL操作
因为有了环境变量,可以直接psql口令登录,不知道命令可以help求助,可以直接各种SQL操作,select、create、alter、delete等,忘记了SQL语法可以看这里。
longware@longware-ubuntu:~$ psql -U sysdba longware用户 sysdba 的口令:注意: -------------------------------------------Login User: sysdba Login time: 2023-11-10 17:12:11.142098+08 Login Address: [local] Last Login Status: SUCCESS Login Failures: 0 Valied Until: 2023-11-16 20:40:51+08 -------------------------------------------psql (4.5.8)输入 "help" 来获取帮助信息.longware=# \d 关联列表 架构模式 | 名称 | 类型 | 拥有者 ----------+--------------------+--------+-------- public | company | 数据表 | sysdba public | hg_t_audit_log | 数据表 | syssao public | pg_buffercache | 视图 | sysdba public | pg_stat_statements | 视图 | sysdba public | t1 | 数据表 | sysdba(5 行记录)longware=# \d t1 数据表 "public.t1" 栏位 | 类型 | 校对规则 | 可空的 | 预设 ---------+-------------------+----------+--------+------ column1 | character varying | | | column2 | "char"[] | | | longware=# select * from t1; column1 | column2 ------------+--------- aaaaaa | {b} aaaafdasaa | {c} aaa中国aa | {d}(3 行记录)longware=#
- windows上PHP远程连接hgdb数据库
编辑php.ini,找到ext dll区域,将pgsql、pdo_pgsql前面的分号去掉,保存,重启web服务,
查看phpinfo里是否有pgsql
要想远程连接数据库,需要开通远程连接权限,如果你连接db时程序报错无权限,
[10-Nov-2023 19:15:25 Asia/Shanghai] PHP Warning: pg_connect(): Unable to connect to PostgreSQL server: 致命错误: 没有用于主机 "192.168.2.180", 用户 "sysdba", 数据库 "longware", SSL 关闭 的 pg_hba.conf 记录 in D:\UPUPW_ANK_W32\WebRoot\Vhosts\local-php74\hgdb_pgsql.php on line 11
则编辑/root/data/pg_hba.conf,在末尾增加以下内容(192.x.x.x为我windows内网ip),保存退出,重载配置。如果不报错,可忽略。
root@longware-ubuntu:~# vi ./data/pg_hba.confhost all all 192.168.2.180/32 sm3root@longware-ubuntu:~# pg_ctl reload2023-11-10 19:10:55.840 CST [40163] 日志: 接收到 SIGHUP, 重载配置文件服务器进程发出信号
改成“host all all 0.0.0.0/0 sm3”支持任意ip连接,但有风险。
如果php连接hgdb报以下错误信息:
Warning: pg_connect(): Unable to connect to PostgreSQL server: authentication method 13 not supported in D:\Workspace\wwwroot\hgdb\hgdb_pgsql.php on line 11
则表示已经连接到hgdb了,但是用户名和密码验证发生问题。pg_hba.conf里可以设置sm3、md5、scram-sha-256、cert等验证方式,更改这里当然可以,但是其他的系统可能就会发生问题,最好是从连接发起端解决问题。
我的思路是:瀚高改了postgre的代码,验证方式可能也有变更;但是他们官网说是可以直接用php自带的postgre dll,但是php自带的postgre dll可能没有瀚高改的东西,所以问题应该就在这。
我咨询了瀚高的技术人员,聊了大半天,没有得到有效解决。网络搜了半天,大概也说是这个原因,但是没看到有效的方法。在和瀚高的技术人员沟通过程中,聊到了libpq,我让他们发一个windows libpq dll给我,经过测试无效。
于是我去deb安装包里找,果然有收获。deb安装包里自带的sql developer的目录里,除了linux的可执行文件,还有windows的exe,有exe那就有dll,果然有。点此下载可用的libpq.dll
将libpq.dll拷贝到php目录(我的有D:\UPUPW_ANK_W32\Modules\PHPX\PHP56 和 D:\UPUPW_ANK_W32\Modules\PHPX\PHP74),测试php程序,都能成功连接hgdb。
show me your code !
1 <?php 2 $host = "host=192.168.2.114"; 3 $port = "port=5866"; 4 $dbname = "dbname=longware"; 5 $credentials = "user=sysdba password=Aa123!"; 6 7 $db = pg_connect("$host $port $dbname $credentials"); 8 if(!$db){ 9 echo "Error : Unable to open database
";10 } else {11 echo "Opened database successfully
";12 }13 14 //创建数据表15 $sql ="CREATE TABLE IF NOT EXISTS COMPANY (".16 "ID INT PRIMARY KEY NOT NULL,".17 "NAME TEXT NOT NULL,".18 "AGE INT NOT NULL,".19 "ADDRESS CHAR(50)," .20 "SALARY REAL".21 ");";22 23 $ret = pg_query($db, $sql);24 if(!$ret){25 echo pg_last_error($db);26 exit;27 } else {28 echo "Table created successfully
";29 }30 31 //插入数据32 $sql ="INSERT INTO COMPANY (ID,NAME,AGE,ADDRESS,SALARY)".33 "VALUES (1, 'Paul', 32, 'California', 20000.00 );".34 "INSERT INTO COMPANY (ID,NAME,AGE,ADDRESS,SALARY)".35 "VALUES (2, 'Allen', 25, 'Texas', 15000.00 );".36 "INSERT INTO COMPANY (ID,NAME,AGE,ADDRESS,SALARY)".37 "VALUES (3, 'Teddy', 23, 'Norway', 20000.00 );".38 "INSERT INTO COMPANY (ID,NAME,AGE,ADDRESS,SALARY)".39 "VALUES (4, 'Mark', 25, 'Rich-Mond ', 65000.00 );";40 41 $ret = pg_query($db, $sql);42 if(!$ret){43 echo pg_last_error($db);44 exit;45 } else {46 echo "Records created successfully
";47 }48 49 //查询数据50 $sql ="SELECT * from COMPANY;";51 52 $ret = pg_query($db, $sql);53 if(!$ret){54 echo pg_last_error($db);55 exit;56 }57 while($row = pg_fetch_row($ret)){58 echo "ID = ". $row[0] . "\n";59 echo "NAME = ". $row[1] ."\n";60 echo "ADDRESS = ". $row[2] ."\n";61 echo "SALARY = ".$row[4] ."
";62 }63 echo "Operation done successfully
";64 pg_close($db);65 ?>
View Code
PHP使用PDO操作hgdb
<?phpheader("content-type:text/html;charset=utf-8");//连接属性$dbms='pgsql'; //数据库类型$host='192.168.2.114'; //数据库主机名$dbName='longware'; //使用的数据库$user='sysdba'; //数据库连接用户名$pass='Aa123!'; //对应的密码$port='5866';$dsn="$dbms:host=$host;port=$port;dbname=$dbName";try { //初始化一个PDO对象 $pdo = new PDO($dsn, $user, $pass); //初始化一个PDO对象 echo "成功连接到数据库服务器!
";} catch (PDOException $e) { die ("Error!: " . $e->getMessage() . "
");}/*CREATE SEQUENC Estudent_id_seqINCREMENT 1MINVALUE 1NO MAXVALUESTART 1CACHE 10;CREATE TABLE student (id INT PRIMARY KEY DEFAULT nextval('student_id_seq'),name VARCHAR(255),age int,birthday date);*/// 预编译插入语句$sql = 'INSERT INTO student(id, name, age, birthday) VALUES(DEFAULT, :name, :age, :birthday)';$stmt = $pdo->prepare($sql);// 绑定参数值$name = 'tony';$age=19;$birthday = '2020-06-01 20:11:11';$stmt->bindValue(':name', $name);$stmt->bindValue(':age', $age);$stmt->bindValue(':birthday', $birthday);$stmt->execute();// 执行插入操作// 返回id$id = $pdo->lastInsertId('student_id_seq');echo '插入数据成功,用户id:' . $id . '
';// 绑定参数值$name = 'david';$age=23;$stmt->bindValue(':name', $name);$stmt->bindValue(':age', $age);$stmt->bindValue(':birthday', date("Y-m-d H:i:s"));$stmt->execute();// 执行插入操作// 返回id$id = $pdo->lastInsertId('student_id_seq');echo '插入数据成功,用户id:' . $id . '
';// 执行查询语句$stmt = $pdo->query('SELECT * FROM student');$students = [];while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) { $students[] = [ 'id' => $row['id'], 'name' => $row['name'], 'age' => $row['age'], 'birthday' => $row['birthday'] ];}?> table { font-family: arial, sans-serif; border-collapse: collapse; width: 100%; } td, th { border: 1px solid #dddddd; text-align: left; padding: 8px; } tr:nth-child(even) { background-color: #00bb00; }php_conn 学生列表
ID | Name | Age | Birthday |
---|---|---|---|
<?php echo htmlspecialchars($student['id']) ?> | <?php echo htmlspecialchars($student['name']); ?> | <?php echo htmlspecialchars($student['age']); ?> | <?php echo htmlspecialchars($student['birthday']); ?> |
View Code
自带的sql developer的bin目录里,双击exe,也能顺利打开,连接hgdb。
- windows上Java远程连接hgdb数据库
Java其实很简单,从/opt/highgo/hgdb-see-4.5.8/etc/drivers/JDBC目录拿到jdbc driver文件hgjdbc-6.1.0.jar,在eclipse建立一个java project,将jar加入build path,写几行测试代码,即可连通。
1 package hgdb; 2 3 import java.sql.Connection; 4 import java.sql.DriverManager; 5 import java.sql.ResultSet; 6 import java.sql.Statement; 7 8 public class testhighgo { 9 10 public static void main(String[] args) {11 Connection ct = null;12 Statement sm = null;13 ResultSet rs = null;14 try {15 // 加载HighGo DB的驱动16 Class.forName("com.highgo.jdbc.Driver");17 ct = DriverManager.getConnection("jdbc:highgo://192.168.2.114:5866/longware", "sysdba", "Aa123!");18 sm = ct.createStatement();19 // 执行查询语句20 String sql = "select * from t1 order by 1";21 System.out.println("sql=====" + sql);22 rs = sm.executeQuery(sql);23 // 循环结果,并打印24 while (rs.next()) {25 System.out.println("====" + rs.getString(2) + "====" + rs.getString(1));26 }27 // 抛出异常28 } catch (Exception e) {29 e.printStackTrace();30 } finally {31 // 关闭数据库连接32 try {33 if (rs != null) {34 rs.close();35 }36 if (sm != null) {37 sm.close();38 }39 if (ct != null) {40 ct.close();41 }42 } catch (Exception ex) {43 ex.printStackTrace();44 }45 }46 }47 48 }
View Code
其实,我是先用java测试连接的,java没有报错,因为瀚高官方jdbc driver里面有相关的认证处理,里面还有SM3的代码。
- 在Linux本机用PHP连接hgdb数据库
用apt命令安装好apache、php7.4,将info.php和前面的2个php脚本拷贝到/var/www/html之下,用浏览器访问或命令行执行,仍然报错authentication method 13 not supported
因为知道是libpq的问题,那么看看有哪些libpq库文件就知道问题了。
1 root@longware-ubuntu:/# locate libpq.so -----查找文件,发现文件主要在hgdb lib和操作系统的usr lib 2 /opt/highgo/hgdb-see-4.5.8/etc/drivers/ODBC/psqlODBC/lib/libpq.so.5 3 /opt/highgo/hgdb-see-4.5.8/lib/libpq.so 4 /opt/highgo/hgdb-see-4.5.8/lib/libpq.so.5 5 /opt/highgo/hgdb-see-4.5.8/lib/libpq.so.5.12 6 /opt/highgo/hgproxy/lib/libpq.so 7 /opt/highgo/hgproxy/lib/libpq.so.5 8 /opt/highgo/hgproxy/lib/libpq.so.5.12 9 /usr/lib/x86_64-linux-gnu/libpq.so.510 /usr/lib/x86_64-linux-gnu/libpq.so.5.1411 12 root@longware-ubuntu:/# ll /usr/lib/x86_64-linux-gnu/libpq.* -l ------看看具体文件,是真实文件,还是链接,发现1真1链13 lrwxrwxrwx 1 root root 13 8月 9 20:01 /usr/lib/x86_64-linux-gnu/libpq.so.5 -> libpq.so.5.1414 -rw-r--r-- 1 root root 329912 8月 9 20:01 /usr/lib/x86_64-linux-gnu/libpq.so.5.1415 16 root@longware-ubuntu:/# ll /opt/highgo/hgdb-see-4.5.8/lib/libpq* -l ------看看具体文件,是真实文件,还是链接,发现2真2链17 -rw-r--r-- 1 root root 360738 7月 8 2022 /opt/highgo/hgdb-see-4.5.8/lib/libpq.a18 lrwxrwxrwx 1 root root 13 7月 8 2022 /opt/highgo/hgdb-see-4.5.8/lib/libpq.so -> libpq.so.5.12*19 lrwxrwxrwx 1 root root 13 7月 8 2022 /opt/highgo/hgdb-see-4.5.8/lib/libpq.so.5 -> libpq.so.5.12*20 -rwxr-xr-x 1 root root 362560 7月 8 2022 /opt/highgo/hgdb-see-4.5.8/lib/libpq.so.5.12*21 22 root@longware-ubuntu:/# cd /usr/lib/x86_64-linux-gnu/ --------于是思路来了,狸猫换太子,将os的lib换成hgdb的lib,先备份,再软链接23 root@longware-ubuntu:/usr/lib/x86_64-linux-gnu# mv libpq.so.5 bak-libpq.so.524 root@longware-ubuntu:/usr/lib/x86_64-linux-gnu# mv libpq.so.5.14 bak-libpq.so.5.14 25 26 root@longware-ubuntu:/usr/lib/x86_64-linux-gnu# ln -s /opt/highgo/hgproxy/lib/libpq.so.5.12 libpq.so.527 root@longware-ubuntu:/usr/lib/x86_64-linux-gnu# ln -s /opt/highgo/hgproxy/lib/libpq.so.5.12 libpq.so.5.14 28 29 root@longware-ubuntu:/usr/lib/x86_64-linux-gnu# ll /usr/lib/x86_64-linux-gnu/libpq.* -l ---------查看,再确认一下30 lrwxrwxrwx 1 root root 37 11月 10 23:00 /usr/lib/x86_64-linux-gnu/libpq.so.5 -> /opt/highgo/hgproxy/lib/libpq.so.5.12*31 lrwxrwxrwx 1 root root 37 11月 10 23:01 /usr/lib/x86_64-linux-gnu/libpq.so.5.14 -> /opt/highgo/hgproxy/lib/libpq.so.5.12*32 33 root@longware-ubuntu:/usr/lib/x86_64-linux-gnu# systemctl restart apache2 ----------重启apache
重启apache之后,php在本机就可以连接hgdb了。
如果服务器是共享的,有多个应用在跑,那么不建议直接换lib,因为可能会导致其他应用挂掉。 对于独占或开发测试机,那就随便折腾了。