分布式云盘部署服务端的漫漫bug路

云盘服务端代码经历两天bug之后终于部署到了自己的服务器上。因此总结一下这两天所出现的所有问题,日后再出现同样的问题便可解决。

过程

  1. 服务端代码部署到虚拟机并启动

  2. 发现问题,Qt客户端注册与登录无响应

  3. 检查客户端登录注册代码,发现没有问题

  4. 检查客户端收到的错误码,发现客户端并未收到服务端反馈的错误码

  5. 查询服务端Nginx服务器log日志,发现80端口请求注册登录端口未成功

  6. 检查登录注册端口,发现未启动端口,排除客户端的问题

  7. 关闭防火墙,仍无法启动端口

  8. 重新启动服务端代码,查看服务端cgi程序的log日志,发现并没有log日志

  9. spawn-fcgi启动报错提示spawn-fcgi: child exited with: 127

  10. 尝试执行 spawn-fcgi 命令 ,发现没有问题

    1
    2
    3
    4
    5
    qianyouyou:~ $ spawn-fcgi
    Usage: spawn-fcgi [options] [-- <fcgiapp> [fcgi app arguments]]
    spawn-fcgi v1.6.5 - spawns FastCGI processes
    Options:
    省略一万字
  11. 执行cgi程序,发现问题No such file or directory

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    # 找一下 libfcgi.so 位置在哪里。
    qianyouyou:~ $ whereis libfcgi.so
    libfcgi: /usr/local/lib/libfcgi.so /usr/local/lib/libfcgi.a /usr/local/lib/libfcgi.la

    # 然后查看一下 /usr/local/lib/ 下面有什么。
    qianyouyou:~ $ ll /usr/local/lib/libfcgi.so*
    lrwxrwxrwx 1 root root 16 Jan 8 16:07 /usr/local/lib/libfcgi.so -> libfcgi.so.0.0.0*
    -rwxr-xr-x 1 root root 124K Jan 8 16:07 /usr/local/lib/libfcgi.so.0.0.0*

    # 原来没有 libfcgi.so.0 这个文件, 那我们就创造一个吧。
    qianyouyou:~ $ sudo ln -s /usr/local/lib/libfcgi.so.0.0.0 /usr/local/lib/libfcgi.so.0

    # 执行cgi还是不行,于是我把 libfcgi.so.0 在 /usr/lib64/ 和 /usr/lib/ 里都链接了一份。
    qianyouyou:~ $ sudo ln -s /usr/local/lib/libfcgi.so.0.0.0 /usr/lib/libfcgi.so.0
    qianyouyou:~ $ sudo ln -s /usr/local/lib/libfcgi.so.0.0.0 /usr/lib64/libfcgi.so.0


    //fcgi和glog都需要建立软连接, 正常情况下只要在/usr/lib目录下建立链接就可以了,如果不行的话在/usr/lib64目录下也建立链接
    # ln -s /usr/local/lib/libfcgi.so.0 /usr/lib/libfcgi.so.0
    # ln -s /usr/local/lib/libfcgi.so.0 /usr/lib64/libfcgi.so.0
    # ln -s /usr/local/lib/libglog.so.0 /usr/lib/libglog.so.0
    # ln -s /usr/local/lib/libglog.so.0 /usr/lib64/libglog.so.0
  12. 依然提示No such file or directory,重新make编译代码,提示找不到mysql/mysql.h

  13. 发现问题,虚拟机装了mysql-server,没有装mysql-devel,安装mysql-devel

    1
    2
    3
    4
    # Ununtu安装
    sudo apt-get install libmysql++-dev
    # CentOS安装
    sudo yum install -y mysql-devel
  14. make成功,重新启动成功,查看相应端口已启动

    1
    netstat -ant | grep 10000
  15. 客户端登录注册失败,返回错误码,查询服务端log日志,发现没有相应数据库表

  16. 远程链接数据库,创建相应数据表

  17. 虚拟机服务端部署成功

  18. 代码部署到服务器,make同样提示没有mysql/mysql.h

  19. 安装mysql-devel未成功,提示冲突

    1
    2
    Transaction check error: file /usr/include/mysql/client_plugin.h from install of mariadb-1:5.5.41-2.el7_0.x86_64 conflicts with file from package MySQL-client-5.0.96-1.glibc23.x86_64
    ...
  20. 查阅yum安装如何避免冲突,删掉冲突文件,均没有用(后发现由于文件夹为软连接)

    1
    2
    3
    4
    # yum查看依赖库
    yum search mysql

    yum install mysql-devel --exclude a #a为冲突包名
  21. 由于已安装mysql为自定义文件夹,因此锁定问题为找不到自定义文件夹库

  22. 创建预编译链接,创建静态库动态库链接。查阅

    1
    2
    3
    4
    5
    6
    7
    8
    9
    # 一次性命令
    export C_INCLUDE_PATH=/www/server/mysql/include:$C_INCLUDE_PATH
    export CPLUS_INCLUDE_PATH=/www/server/mysql/include:$CPLUS_INCLUDE_PATH
    export LD_LIBRARY_PATH=/www/server/mysql/lib:$LD_LIBRARY_PATH
    export LIBRARY_PATH=/www/server/mysql/lib:$LIBRARY_PATH

    # 所有用户都执行需将以上命令添加至/etc/profile

    # 动态库路径可添加至/etc/ld.so.conf
  23. make成功,但除了login与upload外其余端口均为启动

  24. 执行login可执行文件,提示没有libmysqlcient.so.20

  25. 下载libmysqlclient.so.20,执行可执行文件,仍然报错

  26. 更换mysql版本为5.7

  27. 原本部署的博客无法访问。重新配置博客,博客访问成功。网站1网站2

  28. 服务端重新启动,云盘服务端启动成功

  29. 客户端启动,可注册,不可登录

  30. 检查服务端代码,发现代码没问题

  31. 重新编译,提示没有任何文件改动,删除cgi所有.o文件,重新编译成功。

  32. 服务器云盘部署成功。

防火墙相关

一、CentOS 7快速开放端口:

CentOS升级到7之后,发现无法使用iptables控制Linuxs的端口,baidu之后发现Centos 7使用firewalld代替了原来的iptables。下面记录如何使用firewalld开放Linux端口:

开启端口

[root@centos7 ~]# firewall-cmd –zone=public –add-port=80/tcp –permanent

查询端口号80 是否开启:

[root@centos7 ~]# firewall-cmd –query-port=80/tcp

重启防火墙:

[root@centos7 ~]# firewall-cmd –reload

查询有哪些端口是开启的:

[root@centos7 ~]# firewall-cmd –list-port

命令含义:

–zone #作用域
–add-port=80/tcp #添加端口,格式为:端口/通讯协议
–permanent #永久生效,没有此参数重启后失效

关闭firewall:

systemctl stop firewalld.service #停止firewall

systemctl disable firewalld.service #禁止firewall开机启动

二、CentOS6防火墙开放端口:

在我们使用CentOS系统的时候,CentOS防火墙有时是需要改变设置的。CentOS防火墙默认是打开的,设置CentOS防火墙开放端口方法如下:

打开iptables的配置文件:vi /etc/sysconfig/iptables

修改CentOS防火墙时注意:一定要给自己留好后路,留VNC一个管理端口和SSh的管理端口

下面是一个iptables的示例:

# Firewall configuration written by system-config-securitylevel
# Manual customization of this file is not recommended.
*filter
:INPUT ACCEPT [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
:RH-Firewall-1-INPUT - [0:0]
-A INPUT -j RH-Firewall-1-INPUT
-A FORWARD -j RH-Firewall-1-INPUT
-A RH-Firewall-1-INPUT -i lo -j ACCEPT
-A RH-Firewall-1-INPUT -p icmp –icmp-type any -j ACCEPT
-A RH-Firewall-1-INPUT -p 50 -j ACCEPT
-A RH-Firewall-1-INPUT -p 51 -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state ESTABLISHED,RELATED -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state NEW -m tcp -p tcp –dport 53 -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state NEW -m udp -p udp –dport 53 -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state NEW -m tcp -p tcp –dport 22 -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state NEW -m tcp -p tcp –dport 25 -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state NEW -m tcp -p tcp –dport 80 -j ACCEPT
-A RH-Firewall-1-INPUT -m state –state NEW -m tcp -p tcp –dport 443 -j ACCEPT
-A RH-Firewall-1-INPUT -j REJECT –reject-with icmp-host-prohibited
COMMIT

修改CentOS防火墙需要注意的是,你必须根据自己服务器的情况来修改这个文件。

举例来说,如果你不希望开放80端口提供web服务,那么应该相应的删除这一行:
-A RH-Firewall-1-INPUT -m state –state NEW -m tcp -p tcp –dport 80 -j ACCEPT

全部修改完之后重启iptables:service iptables restart

你可以验证一下是否规则都已经生效:iptables -L

这样,我们就完成了CentOS防火墙的设置修改。

库相关

方法一:在编译自己的项目时添加-L和-I编译选项

1)添加头文件路径: -I #指明头文件的路径

2)添加库文件路径: -L #指定目录。link的时候,去找的目录。gcc会先从-L指定的目录去找,然后才查找默认路径。(告诉gcc,-l库名最可能在这个目录下)。 -l #指定文件(库名),linking options

注:-l紧接着就是库名,这里的库名不是真正的库文件名。比如说数学库,它的库名是m,他的库文件名是libm.so。再比如说matlab eigen库,它的库名是eng,它的库文件名是libeng.so。很容易总结得:把库文件名的头lib和尾.so去掉就是库名了。在使用时,“-leng”就告诉gcc在链接阶段引用共享函数库libeng.so。

方法二:将库路径添加到环境变量

1)添加头文件路径: 在/etc/profile中添加(根据语言不同,任选其一):

1
2
3
4
5
export C_INCLUDE_PATH=C_INCLUDE_PATH:头文件路径            #c 

export CPLUS_INCLUDE_PATH=CPLUS_INCLUDE_PATH:头文件路径 #c++

export OBJC_INCLUDE_PATH=OBJC_INCLUDE_PATH:头文件路径 #java

终端重启后需执行一次source。

另有一种方法:在/etc/ld.so.conf文件中加入自定义的lib库的路径,然后执行sudo /sbin/ldconfig,这个方法对所有终端有效。

2)添加库文件路径:

1
2
LIBRARY_PATH    #used by gcc before compilation to search for directories containing libraries that need to be linked to your program.
LD_LIBRARY_PATH #used by your program to search for directories containing the libraries after it has been successfully compiled and linked.

例如:

1
2
3
MATLAB=/opt/MATLAB/R2012a
export LIBRARY_PATH=$LIBRARY_PATH:$MATLAB/bin/glnxa64
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$MATLAB/bin/glnxa64

题外话,顺便提一下LIBRARY_PATH和LD_LIBRARY_PATH的区别:

我们知道Linux下有2种库:static libraries和shared libraries。如(这里)阐述的,静态库是在编译期间会被链接并拷贝到你的程序中,因此运行时不再需要该静态库。动态库在编译时并不会被拷贝到你的程序中,而是在程序运行时才被载入,因此在程序运行时还需要动态库存在,这时就会用到LD_LIBRARY_PATH指定的路径去查找这个动态库。The libraries can be static or shared. If it is static then the code is copied over into your program and you don’t need to search for the library after your program is compiled and linked. If your library is shared then it needs to be dynamically linked to your program and that’s when LD_LIBRARY_PATH comes into play.

环境变量

库文件在连接(静态库和共享 库)和运行(仅限共享库的程序,静态库会和可执行编译到一起)时被使用,其搜索路径是在系统中进行设置的。一般 Linux 系统把 /lib 和 /usr/lib 两个目录作为默认的库搜索路径,所以使用这两个目录中的库时不需要进行设置搜索路径即可直接使用。对于处于默认库搜索路径之外的库,需要将库的位置添加到 库的搜索路径之中。

设置库文件的搜索路径总的来说有以下几种:

  • LIBRARY_PATH、LD_LIBRARY_PATH等 环境变量:指定连接、运行时库文件路径;
  • /etc/ld.so.conf 文件:添加链接时库文件的搜索路径,运行时还需要使用ldconfig命令将路径刷新到ld.so.cache中;
  • g++/gcc参数-L、-l、-I:指定链接时库文件的路径、名字和头文件,运行时还需要使用环境变量或者在文件/etc/ld.so.conf中指定(或者放到默认/lib路径),然后ldconfig;

在/etc/profile中添加如下环境变量。

编译时用到的环境变量:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#gcc找到头文件的路径
C_INCLUDE_PATH=/usr/include/libxml2:/MyLib
export C_INCLUDE_PATH

#g++找到头文件的路径
CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:/usr/include/libxml2:/MyLib
export CPLUS_INCLUDE_PATH

#gcc和g++在编译的链接(link)阶段查找库文件的目录列表
LIBRARY_PATH=$LIBRARY_PATH:/MyLib
export LIBRARY_PATH


对于头文件的搜索路径:export C_INCLUDE_PATH=<your include path>;
对于库文件的搜索路径:export LIBRARY_PATH=<your lib path>;

运行时环境变量

1
2
3
#程序运行时查找ku文件的路径
LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/MyLib
export LD_LIBRARY_PATH

mysql相关

设置远程连接

方法1

  1. 编辑mysql配置文件,把其中bind-address = 127.0.0.1注释了。vi /etc/mysql/mysql.conf.d/mysqld.cnf

  2. 使用root进入mysql命令行,执行如下2个命令,示例中mysql的root账号和密码:root

1
2
3
4
5
6
7
8
mysql -u root -p

grant all privileges on 库名.表名 to '用户名'@'IP地址'
identified by '密码' with grant option;

#例:
mysql> grant all on . to root@'%' identified by 'root' with grant option;
mysql> flush privileges;
  1. 重启mysql/etc/init.d/mysql restart

方法2

  1. 编辑mysql配置文件,把其中bind-address = 127.0.0.1注释了。vi /etc/mysql/mysql.conf.d/mysqld.cnf
  2. 使用root进入mysql命令行,执行如下2个命令,示例中mysql的root账号密码:root
1
2
3
4
5
6
7
8
9
10
11
12
   mysql –u root -p        

mysql> use mysql;

mysql> update user set host = '%' where user = 'root';

mysql> flush privileges;

#第一句是以权限用户root登录
#第二句:选择mysql库
#第三句:修改host值(以通配符%的内容增加主机/IP地址),当然也可以直接增加IP地址
#第四句:刷新MySQL的系统权限相关表
  1. 重启mysql/etc/init.d/mysql restart

修改MySQL默认编码

1
2
3
4
5
......  
[mysqld]
......
character-set-server=utf8
......

设置表名不区分大小写

1
2
3
4
5
6
......  
[mysqld]
......
character-set-server=utf8
lower_case_table_names=1
......

Jpress相关

通过宝塔进行安装

宝塔是一个优秀的可视化服务器管理工具,提供了web操作面板,方便我们通过宝塔的web面板对服务器进行管理,例如

1、数据库安装、账号密码管理和数据管理 2、FTP账号的管理 3、各种服务器软件的安装,php、tomcat、nginx等 4、文件管理

宝塔的官网网站: http://www.bt.cn

通过宝塔进行安装 JPress,大概分为以下几个步骤:

1、购买服务器并安装宝塔 2、通过宝塔的后台面板安装nginx、Mysql和tomcat。 3、创建网站,并启用tomcat功能 4、上传JPress的war包,并解压缩 5、访问网站,走jpress自动安装过程

1、购买服务器并安装宝塔

购买服务器建议购买阿里云的 centos 7.4 以上 ,里面不要安装其他任何功能(笔者在centos 7.2 下安装宝塔,nginx是无法使用的,centos 7.4 没问题)

安装宝塔非常简单,用 root 账号进入Linux服务,然后执行如下命令即可自动安装宝塔:

1
2
yum install -y wget && wget -O install.sh http://
download.bt.cn/install/install_6.0.sh && bash install.sh

需要注意的是:安装的过程中控制台会打印安装的过程,在安装完成后,控制台会输出宝塔的登陆地址、账号和密码。

重要事情说三遍:

登陆地址、账号和密码,这部分务必要记住。 登陆地址、账号和密码,这部分务必要记住。 登陆地址、账号和密码,这部分务必要记住。

2、通过宝塔的后台,安装nginx、mysql和tomcat

可以在宝塔的后台,通过 软件管理 > 运行环境 可以找到 nginx、mysql 和 tomcat。

点击安装即可。

需要注意的是各个软件的版本号:

  • nginx : 1.14
  • tomcat : 8.5
  • mysql : 5.6

3、创建网站

在宝塔后台,通 网站 > 添加网站 创建一个新的网站。

创建网站的时候需要注意的是,创建mysql数据库的时候,版本要选择 utf8mb4 编码。

在宝塔后台的 网站 里,点击网站域名,在 tomcat 菜单里,启用 tomcat 功能。 img

4、上传war,并解压缩

在宝塔后台的 网站 里,点击根目录对应的目录链接,然后上传 jpress.war 到此目录。

因为宝塔无法对 .war 这种文件格式解压缩,所以需要重命名为 jpress.zip ,当然也可以在本地先把 jpress.war 先重命名为 jpress.zip 然后再上传也可以。

操作完成后,点击 jpress.zip 的解压缩即可。

5、访问网站走jpress自动安装过程

访问你的域名,JPress自动引导进行安装,在JPress安装向导的过程中,只需要填写宝塔创建完毕的数据库账号和密码即可。

问题

问题:宝塔安装初次安装JPress无法正常启动?

答:

1、请查看下 /WEB-INF/classes 目录下是否有 jboot.porpertiesinstall.lock 这两个文件,如果有的话请删除。

2、尝试重启 nginx 和 tomcat。


文章结束了,但我们的故事还在继续
坚持原创技术分享,您的支持将鼓励我继续创作!