Anaconda

  1. 下载相关环境

    1
    wget https://mirrors.tuna.tsinghua.edu.cn/anaconda/archive/Anaconda3-2019.10-Linux-x86_64.sh --no-check-certificate
  2. 增加执行权限

    1
    chmod +x Anaconda3-2019.10-Linux-x86_64.sh
  3. 安装(按照提示操作即可)

    1
    bash Anaconda3-2019.10-Linux-x86_64.sh
  4. 加载环境变量

    1
    source /root/.bashrc

    或者

    1
    source ~./bashrc
  5. 检查是否安装成功

    1
    which python

image-20220911204343707

torchvision

下载torchvison地址:https://download.pytorch.org/whl/cu110/torch_stable.html

torchvision-0.8.2%2Bcu110-cp38-cp38-win_amd64.whl中的命名解释:

  • torchvision-0.8.2:表示 torchvision版本为:0.8.2

  • cu110:支持的cuda(GPU)版本为:11.0【cu102:表示cuda版本为10.2】

  • cp38:指的是anaconda中的python版本为python38

  • win_amd64:用于64位window系统。

  • torch-1.7.1:表示torch版本为1.7.1

我的anacond中python版本为python38,在windows64位系统上运行,故需要的版本为:torchvision-0.8.2%2Bcu110-cp38-cp38-win_amd64.whl

编程环境和软件工具安装手册

:heartpulse: 具体版本应根据实际需求确定

Java

jdk 下载

JDK 历史版本页面

JDK 国内官网下载地址:

JDK8 国内官网下载地址:

卸载已有的 openJDK

查询本机中已经安装过的 java rpm 包,命令如下;

1
rpm -qa |grep java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
[root@localhost ~]$ rpm -qa |grep java

java-1.8.0-openjdk-1.8.0.65-3.b17.el7.x86_64
java-1.7.0-openjdk-headless-1.7.0.91-2.6.2.3.el7.x86_64
javapackages-tools-3.4.1-11.el7.noarch
java-1.8.0-openjdk-headless-1.8.0.65-3.b17.el7.x86_64
nuxwdog-client-java-1.0.3-2.el7.x86_64
java-1.7.0-openjdk-1.7.0.91-2.6.2.3.el7.x86_64
mysql-connector-java-5.1.25-3.el7.noarch
python-javapackages-3.4.1-11.el7.noarch
tzdata-java-2015g-1.el7.noarch
javassist-3.16.1-10.el7.noarch
java-1.7.0-openjdk-devel-1.7.0.91-2.6.2.3.el7.x86_64
javamail-1.4.6-8.el7.noarch

如上,将下面几个删除即可

1
2
3
4
5
6
java-1.8.0-openjdk-1.8.0.65-3.b17.el7.x86_64
java-1.7.0-openjdk-headless-1.7.0.91-2.6.2.3.el7.x86_64
java-1.8.0-openjdk-headless-1.8.0.65-3.b17.el7.x86_64
nuxwdog-client-java-1.0.3-2.el7.x86_64
java-1.7.0-openjdk-1.7.0.91-2.6.2.3.el7.x86_64
java-1.7.0-openjdk-devel-1.7.0.91-2.6.2.3.el7.x86_64

.noarch 文件属于通用文件,不影响,不用删除,删了也没事~

1
2
3
4
5
6
javapackages-tools-3.4.1-11.el7.noarch
mysql-connector-java-5.1.25-3.el7.noarch
python-javapackages-3.4.1-11.el7.noarch
tzdata-java-2015g-1.el7.noarch
javassist-3.16.1-10.el7.noarch
javamail-1.4.6-8.el7.noarch

删除命令,(注:删除命令需要用 root 权限)

1
rpm -e --nodeps xxx
1
2
3
4
5
6
`rpm -e --nodeps` java-1.8.0-openjdk-1.8.0.65-3.b17.el7.x86_64
`rpm -e --nodeps` java-1.7.0-openjdk-headless-1.7.0.91-2.6.2.3.el7.x86_64
`rpm -e --nodeps` java-1.8.0-openjdk-headless-1.8.0.65-3.b17.el7.x86_64
`rpm -e --nodeps` nuxwdog-client-java-1.0.3-2.el7.x86_64
`rpm -e --nodeps` java-1.7.0-openjdk-1.7.0.91-2.6.2.3.el7.x86_64
`rpm -e --nodeps` java-1.7.0-openjdk-devel-1.7.0.91-2.6.2.3.el7.x86_64

检查是否已经删除成功

在命令窗口键入java -version,如下说明已经删除成功了:

1
2
[root@localhost ~]$ java -version
-bash: java: command not found

安装 + 配置 JDK

以下方式适用于安装各版本 JDK,本文以 JDK1.8 为例

1、创建一个 java 目录

1
mkdir -p /usr/local/java

2、进入目录

1
cd /usr/local/java

3、通过rz命令或 xftp 将下载的 jdk 包上传到该目录

4、解压 jdk 压缩包

1
tar -zxvf jdk-8u271-linux-x64.tar.gz

5、配置环境变量

用 vim 或 vi 打开/etc/profile 文件

1
vim /etc/profile

6、点击键盘 i 进行编辑;

将下面内容粘贴到末尾;

1
2
3
4
JAVA_HOME=/usr/local/java/jdk1.8.0_271
CLASSPATH=$JAVA_HOME/lib/
PATH=$PATH:$JAVA_HOME/bin
export PATH JAVA_HOME CLASSPATH

注意JAVA_HOME=/home/local/java/jdk1.8.0_271就是你自己的 jdk 目录

image-20221008122404342

7、保存修改

  • Esc
  • Shift + q 进入键盘编辑
  • wq 保存并退出

8、重新加载配置文件,命令:

1
source /etc/profile

验证安装情况

1、输入:java -version

image-20221008122515861

2、输入:javac

image-20221008122544304

3、输入:java

image-20221008122556609

Reference

  1. Linux 安装 JDK 并配置环境变量 - 详细步骤

Tomcat

下载

官网 https://tomcat.apache.org/

image-20221008114200886

根据自己需求选择相应版本,不建议选择最新版本,笔者选择了8.5.82版 :apache-tomcat-8.5.82.tar.gz

上传解压

  1. 上传至 /root 目录

  2. 解压安装

    /usr/local/ 下创建 tomcat ⽂件夹并进⼊

    1
    2
    3
    cd /usr/local/
    mkdir tomcat
    cd tomcat

    将 Tomcat 安装包解压到 /usr/local/tomcat 中即可

    1
    tar -zxvf /root/apache-tomcat-8.5.55.tar.gz -C ./

    解压完之后, /usr/local/tomcat ⽬录中会出现⼀个 apache-tomcat-8.5.82 的⽬录

    image-20221008114851782

启动 TOMCAT

直接进 apache-tomcat-8.5.82 ⽬录,执⾏其中 bin ⽬录下的启动脚本即可

1
2
cd /bin
./startup.sh

image-20221008115146293

访问测试

这时候浏览器访问: 你的主机IP:8080 ,得到如下画⾯说明成功启动了

image-20221008115248203

配置快捷操作和开机启动

⾸先进⼊ /etc/rc.d/init.d ⽬录,创建⼀个名为 tomcat 的⽂件,并赋予执⾏权限

1
2
3
[root@hwzhao bin]## cd /etc/rc.d/init.d/
[root@hwzhao init.d]## touch tomcat
[root@hwzhao bin]## chmod +x tomcat

接下来编辑 tomcat ⽂件,并在其中加⼊如下内容:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
#!/bin/sh
## chkconfig: 345 99 10
## description: Auto-starts tomcat
## /etc/init.d/tomcatd
## Tomcat auto-start
## Source function library.
. /etc/init.d/functions
## source networking configuration.
. /etc/sysconfig/network
RETVAL=0

## 切换成自己的路径
export JAVA_HOME=/usr/local/java/jdk1.8.0_271
export CATALINA_HOME=/usr/local/tomcat/apache-tomcat-8.5.82
export CATALINA_BASE=/usr/local/tomcat/apache-tomcat-8.5.82

start()
{
if [ -f $CATALINA_HOME/bin/startup.sh ];
then
echo $"Starting Tomcat"
$CATALINA_HOME/bin/startup.sh
RETVAL=$?
echo " OK"
return $RETVAL
fi
}
stop()
{
if [ -f $CATALINA_HOME/bin/shutdown.sh ];
then
echo $"Stopping Tomcat"
$CATALINA_HOME/bin/shutdown.sh
RETVAL=$?
sleep 1
ps -fwwu tomcat | grep apache-tomcat|grep -v grep | grep -v PID | awk '{print $2}'|xargs kill -9
echo " OK"
## [ $RETVAL -eq 0 ] && rm -f /var/lock/...
return $RETVAL
fi
}
case "$1" in
start)
start
;;
stop)
stop
;;
restart)
echo $"Restaring Tomcat"
$0 stop
sleep 1
$0 start
;;
*)
echo $"Usage: $0 {start|stop|restart}"
exit 1
;;
esac
exit $RETVAL

这样后续对于 Tomcat 的开启和关闭只需要执⾏如下命令即可:

1
2
service tomcat start
service tomcat stop

现在将其添加到系统服务,使用命令:chkconfig --add tomcat

然后使用chkconfig --list查看服务是否添加成功最后加⼊开机启动即可【可以使用chkconfig tomcat on/off切换开机启动关闭】

1
2
chkconfig --add tomcat
chkconfig tomcat on

MySQL

宋红康 MySQL环境搭建

下载

进入 mysql 官网下载 mysql http://www.mysql.com/downloads/

滑到最下方

image-20211229202455598

根据电脑选择相应的版本

image-20211229202605788 image-20211229202708501

安装

image-20211229204032580

MySql Driver

官网

image-20220116114307281 image-20220116114526193

下载完成后解压即可

image-20220116114642693

Docker 版

拉取镜像

1
docker pull mysql:5.7

image-20221101152436271

运行 docker 命令

运行命令:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
docker run -p 3307:3306 --name mysql-master \
-v /mydata/mysql-master/log:/var/log/mysql \
-v /mydata/mysql-master/data:/var/lib/mysql \
-v /mydata/mysql-master/conf:/etc/mysql \
-e MYSQL_ROOT_PASSWORD=root \
-d mysql:5.7

#高版本MySQL
docker run -p 3308:3306 --name mysql8 \
-v /mydata/mysql8/log:/var/log/mysql \
-v /mydata/mysql8/data:/var/lib/mysql \
-v /mydata/mysql8/conf:/etc/mysql/conf.d \
-v /etc/localtime:/etc/localtime:ro \
-e MYSQL_ROOT_PASSWORD=root \
-d mysql:8.0

image-20221101153701183

安装成功。

进入容器查看配置,并进行字符集等默认配置:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
[root@hadoop-104 conf]# docker exec -it mysql /bin/bash
root@b3a74e031bd7:/# whereis mysql
mysql: /usr/bin/mysql /usr/lib/mysql /etc/mysql /usr/share/mysql

root@b3a74e031bd7:/# ls /etc/mysql
my.cnf
root@b3a74e031bd7:/# cat /etc/mysql/my.cnf
[client]
default-character-set=utf8
[mysql]
default-character-set=utf8
[mysqld]
init_connect='SET collation_connection = utf8_unicode_ci'
init_connect='SET NAMES utf8'
character-set-server=utf8
collation-server=utf8_unicode_ci
skip-character-set-client-handshake
skip-name-resolve
root@b3a74e031bd7:/#

设置启动 docker 时,即运行 mysql

1
2
3
[root@hadoop-104 ~]# docker update mysql --restart=always
mysql
[root@hadoop-104 ~]#

Redis

基于 CentOS 7
Redis 的官方网站地址:https://redis.io/

安装 Redis 依赖

Redis 是基于 C 语言编写的,因此首先需要安装 Redis 所需要的 gcc 依赖:

1
yum install -y gcc tcl

上传安装包并解压

然后将 Redis 安装包上传到虚拟机的任意目录:

image-20211211071712536

例如,我放到了/usr/local/src 目录:

image-20211211080151539

解压缩:

1
tar -xzf redis-6.2.6.tar.gz

解压后:

image-20211211080339076

进入 redis 目录:

1
cd redis-6.2.6

运行编译命令:

1
make && make install

如果没有出错,应该就安装成功了。

默认的安装路径是在 /usr/local/bin目录下:

image-20211211080603710

该目录以及默认配置到环境变量,因此可以在任意目录下运行这些命令。其中:

  • redis-cli:是 redis 提供的命令行客户端
  • redis-server:是 redis 的服务端启动脚本
  • redis-sentinel:是 redis 的哨兵启动脚本

启动

redis 的启动方式有很多种,例如:

  • 默认启动
  • 指定配置启动
  • 开机自启

默认启动

安装完成后,在任意目录输入 redis-server 命令即可启动 Redis:

1
redis-server

如图:

image-20211211081716167

这种启动属于前台启动,会阻塞整个会话窗口,窗口关闭或者按下CTRL + C则 Redis 停止。不推荐使用。

指定配置启动

如果要让 Redis 以后台方式启动,则必须修改 Redis 配置文件,就在我们之前解压的 redis 安装包下(/usr/local/src/redis-6.2.6),名字叫 redis.conf:

image-20211211082225509

我们先将这个配置文件备份一份:

1
cp redis.conf redis.conf.bck

然后修改 redis.conf 文件中的一些配置:

1
2
3
4
5
6
## 允许访问的地址,默认是127.0.0.1,会导致只能在本地访问。修改为0.0.0.0则可以在任意IP访问,生产环境不要设置为0.0.0.0
bind 0.0.0.0
## 守护进程,修改为yes后即可后台运行
daemonize yes
## 密码,设置后访问Redis必须输入密码
requirepass 123321

Redis 的其它常见配置:

1
2
3
4
5
6
7
8
9
10
## 监听的端口
port 6379
## 工作目录,默认是当前目录,也就是运行redis-server时的命令,日志、持久化等文件会保存在这个目录
dir .
## 数据库数量,设置为1,代表只使用1个库,默认有16个库,编号0~15
databases 1
## 设置redis能够使用的最大内存
maxmemory 512mb
## 日志文件,默认为空,不记录日志,可以指定日志文件名
logfile "redis.log"

启动 Redis:

1
2
3
4
## 进入redis安装目录
cd /usr/local/src/redis-6.2.6
## 启动
redis-server redis.conf

停止服务:

1
2
3
## 利用redis-cli来执行 shutdown 命令,即可停止 Redis 服务,
## 因为之前配置了密码,因此需要通过 -u 来指定密码
redis-cli -u 123321 shutdown

开机自启

我们也可以通过配置来实现开机自启。

首先,新建一个系统服务文件:

1
vi /etc/systemd/system/redis.service

内容如下:

1
2
3
4
5
6
7
8
9
10
11
[Unit]
Description=redis-server
After=network.target

[Service]
Type=forking
ExecStart=/usr/local/bin/redis-server /usr/local/src/redis-6.2.6/redis.conf
PrivateTmp=true

[Install]
WantedBy=multi-user.target

然后重载系统服务:

1
systemctl daemon-reload

现在,我们可以用下面这组命令来操作 redis 了:

1
2
3
4
5
6
7
8
## 启动
systemctl start redis
## 停止
systemctl stop redis
## 重启
systemctl restart redis
## 查看状态
systemctl status redis

执行下面的命令,可以让 redis 开机自启:

1
systemctl enable redis

Docker 版

拉取镜像

1
[root@hwServer ~]# docker pull redis:6.2.7

创建挂载目录

1
2
[root@hwServer ~]#  mkdir -p /home/redis/conf
[root@hwServer ~]# touch /home/redis/conf/redis.conf

启动 redis

1
2
3
docker run -p 6379:6379 --name redis -v /home/redis/data:/data \
-v /home/redis/conf/redis.conf:/etc/redis/redis.conf \
-d redis:6.2.7 redis-server /etc/redis/redis.conf

设置 redis 容器在 docker 启动的时候启动

1
2
3
[root@hadoop-104 ~]# docker update redis --restart=always
redis
[root@hadoop-104 ~]#

测试

1
[root@hwServer ~]# docker exec -it redis redis-cli

image-20221101165117030

Redis 客户端

安装完成 Redis,我们就可以操作 Redis,实现数据的 CRUD 了。这需要用到 Redis 客户端,包括:

  • 命令行客户端
  • 图形化桌面客户端
  • 编程客户端

Redis 命令行客户端

Redis 安装完成后就自带了命令行客户端:redis-cli,使用方式如下:

1
redis-cli [options] [commonds]

其中常见的 options 有:

  • -h 127.0.0.1:指定要连接的 redis 节点的 IP 地址,默认是 127.0.0.1
  • -p 6379:指定要连接的 redis 节点的端口,默认是 6379
  • -a 123321:指定 redis 的访问密码

其中的 commonds 就是 Redis 的操作命令,例如:

  • ping:与 redis 服务端做心跳测试,服务端正常会返回pong

不指定 commond 时,会进入redis-cli的交互控制台:

image-20211211110439353

图形化桌面客户端

GitHub 上的大神编写了 Redis 的图形化桌面客户端,地址:https://github.com/uglide/RedisDesktopManager

不过该仓库提供的是 RedisDesktopManager 的源码,并未提供 windows 安装包。

在下面这个仓库可以找到安装包:https://github.com/lework/RedisDesktopManager-Windows/releases

image-20211211111351885

安装

在课前资料中可以找到 Redis 的图形化桌面客户端:

image-20211214154938770

解压缩后,运行安装程序即可安装:

image-20211214155123841

此处略。

安装完成后,在安装目录下找到 rdm.exe 文件:

image-20211211110935819

双击即可运行:

image-20211214155406692

建立连接

点击左上角的连接到Redis服务器按钮:

image-20211214155424842

在弹出的窗口中填写 Redis 服务信息:

image-20211211111614483

点击确定后,在左侧菜单会出现这个链接:

image-20211214155804523

点击即可建立连接了:

image-20211214155849495

Redis 默认有 16 个仓库,编号从 0 至 15. 通过配置文件可以设置仓库数量,但是不超过 16,并且不能自定义仓库名称。

如果是基于 redis-cli 连接 Redis 服务,可以通过 select 命令来选择数据库:

1
2
## 选择 0号库
select 0

Docker

Docker 分为 CE 和 EE 两大版本。CE 即社区版(免费,支持周期 7 个月),EE 即企业版,强调安全,付费使用,支持周期 24 个月。

Docker CE 分为 stable testnightly 三个更新频道。

官方网站上有各种环境下的 安装指南,这里主要介绍 Docker CE 在 CentOS 上的安装。

CentOS 安装 Docker

Docker CE 支持 64 位版本 CentOS 7,并且要求内核版本不低于 3.10, CentOS 7 满足最低内核的要求,所以我们在 CentOS 7 安装 Docker。

卸载(可选)

如果之前安装过旧版本的 Docker,可以使用下面命令卸载:

1
2
3
4
5
6
7
8
9
10
11
yum remove docker \
docker-client \
docker-client-latest \
docker-common \
docker-latest \
docker-latest-logrotate \
docker-logrotate \
docker-selinux \
docker-engine-selinux \
docker-engine \
docker-ce

安装 docker

首先需要大家虚拟机联网,安装 yum 工具

1
2
3
yum install -y yum-utils \
device-mapper-persistent-data \
lvm2 --skip-broken

然后更新本地镜像源:

1
2
3
4
5
6
7
## 设置docker镜像源
yum-config-manager \
--add-repo \
https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo

sed -i 's/download.docker.com/mirrors.aliyun.com\/docker-ce/g' /etc/yum.repos.d/docker-ce.repo
yum makecache fast

然后输入命令:

1
yum install -y docker-ce

docker-ce 为社区免费版本。稍等片刻,docker 即可安装成功。

启动 docker

Docker 应用需要用到各种端口,逐一去修改防火墙设置。非常麻烦,因此建议大家直接关闭防火墙!

启动 docker 前,一定要关闭防火墙后!!

1
2
3
4
5
6
## 关闭
systemctl stop firewalld
## 禁止开机启动防火墙
systemctl disable firewalld
#查看是否关闭防火墙
systemctl status firewalld

image-20220815085443679

通过命令启动 docker:

1
2
3
4
5
systemctl start docker  ## 启动docker服务

systemctl stop docker ## 停止docker服务

systemctl restart docker ## 重启docker服务

然后输入命令,可以查看 docker 版本:

1
docker -v

如图:

image-20210418154704436

配置镜像加速

docker 官方镜像仓库网速较差,我们需要设置国内镜像服务:

参考阿里云的镜像加速文档:https://cr.console.aliyun.com/cn-hangzhou/instances/mirrors

CentOS7 安装 DockerCompose

下载

Linux 下需要通过命令下载:

1
2
## 安装
curl -L https://github.com/docker/compose/releases/download/1.23.1/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose

修改文件权限

修改文件权限:

1
2
## 修改权限
chmod +x /usr/local/bin/docker-compose

Base 自动补全命令:

1
2
## 补全命令
curl -L https://raw.githubusercontent.com/docker/compose/1.29.1/contrib/completion/bash/docker-compose > /etc/bash_completion.d/docker-compose

如果这里出现错误,需要修改自己的 hosts 文件:

1
echo "199.232.68.133 raw.githubusercontent.com" >> /etc/hosts

Docker 镜像仓库

搭建镜像仓库可以基于 Docker 官方提供的 DockerRegistry 来实现。

官网地址:https://hub.docker.com/_/registry

简化版镜像仓库

Docker 官方的 Docker Registry 是一个基础版本的 Docker 镜像仓库,具备仓库管理的完整功能,但是没有图形化界面。

搭建方式比较简单,命令如下:

1
2
3
4
5
6
docker run -d \
--restart=always \
--name registry \
-p 5000:5000 \
-v registry-data:/var/lib/registry \
registry

命令中挂载了一个数据卷 registry-data 到容器内的/var/lib/registry 目录,这是私有镜像库存放数据的目录。

访问 http://YourIp:5000/v2/\_catalog 可以查看当前私有镜像服务中包含的镜像

配置 Docker 信任地址

我们的私服采用的是 http 协议,默认不被 Docker 信任,所以需要做一个配置:

1
2
3
4
5
6
7
8
## 打开要修改的文件
vi /etc/docker/daemon.json
## 添加内容:
"insecure-registries":["http://192.168.164.129:8080"]
## 重加载
systemctl daemon-reload
## 重启docker
systemctl restart docker

带有图形化界面版本

使用 DockerCompose 部署带有图象界面的 DockerRegistry,命令如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
version: '3.0'
services:
registry:
image: registry
volumes:
- ./registry-data:/var/lib/registry
ui:
image: joxit/docker-registry-ui:static
ports:
- 8080:80
environment:
- REGISTRY_TITLE=Hello Geeks_Z
- REGISTRY_URL=http://registry:5000
depends_on:
- registry

阿里云服务器(ECS)安装 Docker

部署并使用 Docker(CentOS 8)

Nacos

Linux 或者 Mac 安装方式与 Windows 类似。

安装 JDK

见Java安装-Linux`

上传安装包

如图:

image-20210402161102887

也可以直接使用课前资料中的 tar.gz:

image-20210402161130261

上传到 Linux 服务器的某个目录,例如/usr/local/src目录下:

image-20210402163715580

解压

命令解压缩安装包:

1
tar -xvf nacos-server-1.4.1.tar.gz

然后删除安装包:

1
rm -rf nacos-server-1.4.1.tar.gz

目录中最终样式:

image-20210402163858429

目录内部:

image-20210402164414827

端口配置

与 windows 中类似

启动

在 nacos/bin 目录中,输入命令启动 Nacos:

1
sh startup.sh -m standalone

Docker安装

在docker中安装Nacos–详细教程

Docker启动安装nacos(详情讲解,全网最细)

拉取镜像

1
docker pull nacos/nacos-server:v2.0.4

image-20231115212406446

创建挂载目录

1
2
mkdir -p /home/nacos/logs/                    
mkdir -p /home/nacos/conf/

修改配置文件(没有需先行创建)

1
vim /home/nacos/conf/application.properties
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
server.contextPath=/nacos
server.servlet.contextPath=/nacos
server.port=8848

spring.datasource.platform=mysql
db.num=1
db.url.0=jdbc:mysql://ip:3306/nacos_config?characterEncoding=utf8&connectTimeout=1000&socketTimeout=3000&autoReconnect=true
db.user= #账号
db.password= #密码

nacos.cmdb.dumpTaskInterval=3600
nacos.cmdb.eventTaskInterval=10
nacos.cmdb.labelTaskInterval=300
nacos.cmdb.loadDataAtStart=false
management.metrics.export.elastic.enabled=false
management.metrics.export.influx.enabled=false
server.tomcat.accesslog.enabled=true
server.tomcat.accesslog.pattern=%h %l %u %t "%r" %s %b %D %{User-Agent}i
nacos.security.ignore.urls=/,/**/*.css,/**/*.js,/**/*.html,/**/*.map,/**/*.svg,/**/*.png,/**/*.ico,/console-fe/public/**,/v1/auth/login,/v1/console/health/**,/v1/cs/**,/v1/ns/**,/v1/cmdb/**,/actuator/**,/v1/console/server/**
nacos.naming.distro.taskDispatchThreadCount=1
nacos.naming.distro.taskDispatchPeriod=200
nacos.naming.distro.batchSyncKeyCount=1000
nacos.naming.distro.initDataRatio=0.9
nacos.naming.distro.syncRetryDelay=5000
nacos.naming.data.warmup=true
nacos.naming.expireInstance=true

启动nacos容器

1
2
3
4
5
6
7
8
9
10
11
12
docker  run \
--name nacos -d \
-p 8848:8848 \
--privileged=true \
--restart=always \
-e JVM_XMS=256m \
-e JVM_XMX=256m \
-e MODE=standalone \
-e PREFER_HOST_MODE=hostname \
-v /home/nacos/logs:/home/nacos/logs \
-v /home/nacos/conf/application.properties:/home/nacos/init.d/custom.properties \
nacos/nacos-server:v2.0.4

语句讲解

  1. docker run -d : 启动容器 -d是后台启动并返回容器id的意思
  2. –name nacos :为容器指定一个名称
  3. -p 8848:8848 -p 9848:9848 -p 9849:9849 : 指定端口映射,注意这里的p不能大写,大写是随机端口映射
  4. –privileged=true : 扩大容器内的权限,将容器内的权限变为root权限,不加的话就是普通用户权限,可能会出现cannot open directory
  5. -e JVM_XMS=256m : 为jvm启动时分配的内存
  6. -e JVM_XMX=256m : 为jvm运行过程中分配的最大内存
  7. -e MODE=standalone : 使用 standalone模式(单机模式),MODE值有cluster(集群)模式/standalone模式两种,MODE必须大写
  8. –restart=always :重启docker时,自动启动相关容器

浏览器登录访问

https:xx.xx.xx.xx:8848 账号:nacos 密码:nacos

image-20231115212820414

Nacos 的依赖

父工程的 pom 文件中的<dependencyManagement>中引入 SpringCloudAlibaba 的依赖:

1
2
3
4
5
6
7
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>2.2.5.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>

客户端:

1
2
3
4
5
6
<!-- nacos客户端依赖包 -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>

Nginx

解压 Nginx 包,并安装

1
2
3
4
tar -zxvf  nginx-1.21.6.tar.gz #解压到当前目录

cd nginx-1.21.6 #进入解压后的文件夹
ls #文件夹中的文件:auto CHANGES.ru configure html man src CHANGES conf contrib LICENSE README

安装依赖库

1
2
3
4
5
6
7
8
#安装C编译器
yum install -y gcc

#安装pcre库
yum install -y pcre pcre-devel

#安装zlib
yum install -y zlib zlib-devel

安装

1
2
3
./configure --prefix=/usr/local/nginx #使用prefix选项指定安装的目录
make
make install

启动

1
2
3
cd /usr/local/nginx/sbin
ls ## 里面是一个nginx的可执行文件
./nginx ## 启动这个可执行

关闭防火墙

1
systemctl stop firewalld

补充 Nginx 命令

1
2
3
4
./nginx -s stop #快速停止
./nginx -s quit #完成已接受的请求后,停止
./nginx -s reload #重新加载配置
./nginx -t #检查nginx配置是否正确

查看 nginx 状态

1
ps -ef|grep nginx

启动时:

image-20220501205303265

停止时:

image-20220501205333304

注册系统服务

通过系统服务的方式启动 nginx

1
vim usr/lib/systemd/system/nginx.service
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
[Unit]
Description=nginx
After=network.target remote-fs.target nss-lookup.target

[Service]
Type=forking
PIDFile=/usr/local/nginx/logs/nginx.pid
ExecStartPre=/usr/local/nginx/sbin/nginx -t -c /usr/local/nginx/conf/nginx.conf
ExecStart=/usr/local/nginx/sbin/nginx -c /usr/local/nginx/conf/nginx.conf
ExecReload=/usr/local/nginx/sbin/nginx -s reload
ExecStop=/usr/local/nginx/sbin/nginx -s stop
ExecQuit=/usr/local/nginx/sbin/nginx -s quit
PrivateTmp=true

[Install]
WantedBy=multi-user.target ## 多用户

重新加载系统服务

1
systemctl daemon-reload

启动服务

1
systemctl start nginx.service

开机启动

1
systemctl enable nginx.service

Docker

Docker 安装 Nginx 容器 (完整详细版)

寻找Nginx镜像

img

img

下载 Nginx 镜像

命令 描述
docker pull nginx 下载最新版 Nginx 镜像 (其实此命令就等同于 : docker pull nginx:latest )
docker pull nginx:xxx 下载指定版本的 Nginx 镜像 (xxx 指具体版本号)

img

检查当前所有Docker下载的镜像

1
docker images

创建 Nginx 配置文件

启动前需要先创建 Nginx 外部挂载的配置文件( /home/nginx/conf/nginx.conf)
之所以要先创建 , 是因为 Nginx 本身容器只存在/etc/nginx 目录 , 本身就不创建 nginx.conf 文件
当服务器和容器都不存在 nginx.conf 文件时, 执行启动命令的时候, docker 会将 nginx.conf 作为目录创建 , 这并不是我们想要的结果 。

1
2
3
4
# 创建挂载目录
mkdir -p /home/nginx/conf
mkdir -p /home/nginx/log
mkdir -p /home/nginx/html

复制容器文件到宿主机

1
2
3
4
5
6
7
8
# 先生成容器
docker run --name nginx -p 9001:80 -d nginx:1.24
# 将容器nginx.conf文件复制到宿主机
docker cp nginx:/etc/nginx/nginx.conf /home/nginx/conf/nginx.conf
# 将容器conf.d文件夹下内容复制到宿主机
docker cp nginx:/etc/nginx/conf.d /home/nginx/conf/conf.d
# 将容器中的html文件夹复制到宿主机
docker cp nginx:/usr/share/nginx/html /home/nginx/

image-20221103202624139

删除已启动Nginx容器

1
2
3
4
5
6
7
8
9
# 直接执行docker rm nginx或者以容器id方式关闭容器
# 找到nginx对应的容器id
docker ps -a
# 关闭该容器
docker stop nginx
# 删除该容器
docker rm nginx
# 删除正在运行的nginx容器
docker rm -f nginx

创建 Nginx 容器并运行

1
2
3
4
5
6
7
8
docker run \
-p 9002:80 \
--name nginx \
-v /home/nginx/conf/nginx.conf:/etc/nginx/nginx.conf \
-v /home/nginx/conf/conf.d:/etc/nginx/conf.d \
-v /home/nginx/log:/var/log/nginx \
-v /home/nginx/html:/usr/share/nginx/html \
-d nginx:1.24
命令 描述
–name nginx 启动容器的名字
-d 后台运行
-p 9002:80 将容器的 9002(后面那个) 端口映射到主机的 80(前面那个) 端口
-v /home/nginx/conf/nginx.conf:/etc/nginx/nginx.conf 挂载 nginx.conf 配置文件
-v /home/nginx/conf/conf.d:/etc/nginx/conf.d 挂载 nginx 配置文件
-v /home/nginx/log:/var/log/nginx 挂载 nginx 日志文件
-v /home/nginx/html:/usr/share/nginx/html 挂载 nginx 内容
nginx:1.24 本地运行的版本
\ shell 命令换行

image-20231103110403818

单行模式

1
docker run -p 80:80 --name nginx -v /home/nginx/conf/nginx.conf:/etc/nginx/nginx.conf -v /home/nginx/conf/conf.d:/etc/nginx/conf.d -v /home/nginx/log:/var/log/nginx -v /home/nginx/html:/usr/share/nginx/html -d nginx:1.22

结果检测

img

image-20221103203137410

修改内容进行展示

img

1
2
# 重启容器
docker restart nginx

img

RabbitMQ

单机部署

我们在 Centos7 虚拟机中使用 Docker 来安装。

下载镜像

方式一:在线拉取

1
docker pull rabbitmq:3-management

方式二:从本地加载

在课前资料已经提供了镜像包:

image-20210423191210349

上传到虚拟机中后,使用命令加载镜像即可:

1
docker load -i mq.tar

安装 MQ

执行下面的命令来运行 MQ 容器:

1
2
3
4
5
6
7
8
9
docker run \
-e RABBITMQ_DEFAULT_USER=zhw \
-e RABBITMQ_DEFAULT_PASS=1024 \
--name mq \
--hostname mq1 \
-p 15672:15672 \
-p 5672:5672 \
-d \
rabbitmq:3-management

安装 DelayExchange 插件

官方的安装指南地址为:https://blog.rabbitmq.com/posts/2015/04/scheduling-messages-with-rabbitmq

上述文档是基于 linux 原生安装 RabbitMQ,然后安装插件。

因为我们之前是基于 Docker 安装 RabbitMQ,所以下面我们会讲解基于 Docker 来安装 RabbitMQ 插件。

下载插件

RabbitMQ 有一个官方的插件社区,地址为:https://www.rabbitmq.com/community-plugins.html

其中包含各种各样的插件,包括我们要使用的 DelayExchange 插件:

image-20210713104511055

大家可以去对应的 GitHub 页面下载 3.8.9 版本的插件,地址为https://github.com/rabbitmq/rabbitmq-delayed-message-exchange/releases/tag/3.8.9这个对应RabbitMQ的3.8.5以上版本。

上传插件

因为我们是基于 Docker 安装,所以需要先查看 RabbitMQ 的插件目录对应的数据卷。如果不是基于 Docker 的同学,请参考第一章部分,重新创建 Docker 容器。

我们之前设定的 RabbitMQ 的数据卷名称为mq-plugins,所以我们使用下面命令查看数据卷:

1
docker volume inspect mq-plugins

可以得到下面结果:

image-20210713105135701

接下来,将插件上传到这个目录即可:

image-20210713105339785

安装插件

最后就是安装了,需要进入 MQ 容器内部来执行安装。我的容器名为mq,所以执行下面命令:

1
docker exec -it mq bash

执行时,请将其中的 -it 后面的mq替换为你自己的容器名.

进入容器内部后,执行下面命令开启插件:

1
rabbitmq-plugins enable rabbitmq_delayed_message_exchange

结果如下:

image-20210713105829435

集群部署

接下来,我们看看如何安装 RabbitMQ 的集群。

集群分类

在 RabbitMQ 的官方文档中,讲述了两种集群的配置方式:

  • 普通模式:普通模式集群不进行数据同步,每个 MQ 都有自己的队列、数据信息(其它元数据信息如交换机等会同步)。例如我们有 2 个 MQ:mq1,和 mq2,如果你的消息在 mq1,而你连接到了 mq2,那么 mq2 会去 mq1 拉取消息,然后返回给你。如果 mq1 宕机,消息就会丢失。
  • 镜像模式:与普通模式不同,队列会在各个 mq 的镜像节点之间同步,因此你连接到任何一个镜像节点,均可获取到消息。而且如果一个节点宕机,并不会导致数据丢失。不过,这种方式增加了数据同步的带宽消耗。

我们先来看普通模式集群,我们的计划部署 3 节点的 mq 集群:

主机名 控制台端口 amqp 通信端口
mq1 8081 —> 15672 8071 —> 5672
mq2 8082 —> 15672 8072 —> 5672
mq3 8083 —> 15672 8073 —> 5672

集群中的节点标示默认都是:rabbit@[hostname],因此以上三个节点的名称分别为:

  • rabbit@mq1
  • rabbit@mq2
  • rabbit@mq3

RabbitMQ 底层依赖于 Erlang,而 Erlang 虚拟机就是一个面向分布式的语言,默认就支持集群模式。集群模式中的每个 RabbitMQ 节点使用 cookie 来确定它们是否被允许相互通信。

要使两个节点能够通信,它们必须具有相同的共享秘密,称为Erlang cookie。cookie 只是一串最多 255 个字符的字母数字字符。

每个集群节点必须具有相同的 cookie。实例之间也需要它来相互通信。

我们先在之前启动的 mq 容器中获取一个 cookie 值,作为集群的 cookie。执行下面的命令:

1
docker exec -it mq cat /var/lib/rabbitmq/.erlang.cookie

可以看到 cookie 值如下:

1
FXZMCVGLBIXZCDEMMVZQ

接下来,停止并删除当前的 mq 容器,我们重新搭建集群。

1
docker rm -f mq

image-20210717212345165

准备集群配置

在/tmp 目录新建一个配置文件 rabbitmq.conf:

1
2
3
cd /tmp
## 创建文件
touch rabbitmq.conf

文件内容如下:

1
2
3
4
5
6
loopback_users.guest = false
listeners.tcp.default = 5672
cluster_formation.peer_discovery_backend = rabbit_peer_discovery_classic_config
cluster_formation.classic_config.nodes.1 = rabbit@mq1
cluster_formation.classic_config.nodes.2 = rabbit@mq2
cluster_formation.classic_config.nodes.3 = rabbit@mq3

再创建一个文件,记录 cookie

1
2
3
4
5
6
7
cd /tmp
## 创建cookie文件
touch .erlang.cookie
## 写入cookie
echo "FXZMCVGLBIXZCDEMMVZQ" > .erlang.cookie
## 修改cookie文件的权限
chmod 600 .erlang.cookie

准备三个目录,mq1、mq2、mq3:

1
2
3
cd /tmp
## 创建目录
mkdir mq1 mq2 mq3

然后拷贝 rabbitmq.conf、cookie 文件到 mq1、mq2、mq3:

1
2
3
4
5
6
7
8
9
## 进入/tmp
cd /tmp
## 拷贝
cp rabbitmq.conf mq1
cp rabbitmq.conf mq2
cp rabbitmq.conf mq3
cp .erlang.cookie mq1
cp .erlang.cookie mq2
cp .erlang.cookie mq3

启动集群

创建一个网络:

1
docker network create mq-net

docker volume create

运行命令

1
2
3
4
5
6
7
8
9
10
docker run -d --net mq-net \
-v ${PWD}/mq1/rabbitmq.conf:/etc/rabbitmq/rabbitmq.conf \
-v ${PWD}/.erlang.cookie:/var/lib/rabbitmq/.erlang.cookie \
-e RABBITMQ_DEFAULT_USER=itcast \
-e RABBITMQ_DEFAULT_PASS=123321 \
--name mq1 \
--hostname mq1 \
-p 8071:5672 \
-p 8081:15672 \
rabbitmq:3.8-management
1
2
3
4
5
6
7
8
9
10
docker run -d --net mq-net \
-v ${PWD}/mq2/rabbitmq.conf:/etc/rabbitmq/rabbitmq.conf \
-v ${PWD}/.erlang.cookie:/var/lib/rabbitmq/.erlang.cookie \
-e RABBITMQ_DEFAULT_USER=itcast \
-e RABBITMQ_DEFAULT_PASS=123321 \
--name mq2 \
--hostname mq2 \
-p 8072:5672 \
-p 8082:15672 \
rabbitmq:3.8-management
1
2
3
4
5
6
7
8
9
10
docker run -d --net mq-net \
-v ${PWD}/mq3/rabbitmq.conf:/etc/rabbitmq/rabbitmq.conf \
-v ${PWD}/.erlang.cookie:/var/lib/rabbitmq/.erlang.cookie \
-e RABBITMQ_DEFAULT_USER=itcast \
-e RABBITMQ_DEFAULT_PASS=123321 \
--name mq3 \
--hostname mq3 \
-p 8073:5672 \
-p 8083:15672 \
rabbitmq:3.8-management

测试

在 mq1 这个节点上添加一个队列:

image-20210717222833196

如图,在 mq2 和 mq3 两个控制台也都能看到:

image-20210717223057902

数据共享测试

点击这个队列,进入管理页面:

image-20210717223421750

然后利用控制台发送一条消息到这个队列:

image-20210717223320238

结果在 mq2、mq3 上都能看到这条消息:

image-20210717223603628

可用性测试

我们让其中一台节点 mq1 宕机:

1
docker stop mq1

然后登录 mq2 或 mq3 的控制台,发现 simple.queue 也不可用了:

image-20210717223800203

说明数据并没有拷贝到 mq2 和 mq3。

镜像模式

在刚刚的案例中,一旦创建队列的主机宕机,队列就会不可用。不具备高可用能力。如果要解决这个问题,必须使用官方提供的镜像集群方案。

官方文档地址:https://www.rabbitmq.com/ha.html

镜像模式的特征

默认情况下,队列只保存在创建该队列的节点上。而镜像模式下,创建队列的节点被称为该队列的主节点,队列还会拷贝到集群中的其它节点,也叫做该队列的镜像节点。

但是,不同队列可以在集群中的任意节点上创建,因此不同队列的主节点可以不同。甚至,一个队列的主节点可能是另一个队列的镜像节点

用户发送给队列的一切请求,例如发送消息、消息回执默认都会在主节点完成,如果是从节点接收到请求,也会路由到主节点去完成。镜像节点仅仅起到备份数据作用

当主节点接收到消费者的 ACK 时,所有镜像都会删除节点中的数据。

总结如下:

  • 镜像队列结构是一主多从(从就是镜像)
  • 所有操作都是主节点完成,然后同步给镜像节点
  • 主宕机后,镜像节点会替代成新的主(如果在主从同步完成前,主就已经宕机,可能出现数据丢失)
  • 不具备负载均衡功能,因为所有操作都会有主节点完成(但是不同队列,其主节点可以不同,可以利用这个提高吞吐量)

镜像模式的配置

镜像模式的配置有 3 种模式:

ha-mode ha-params 效果
准确模式 exactly 队列的副本量 count 集群中队列副本(主服务器和镜像服务器之和)的数量。count 如果为 1 意味着单个副本:即队列主节点。count 值为 2 表示 2 个副本:1 个队列主和 1 个队列镜像。换句话说:count = 镜像数量 + 1。如果群集中的节点数少于 count,则该队列将镜像到所有节点。如果有集群总数大于 count+1,并且包含镜像的节点出现故障,则将在另一个节点上创建一个新的镜像。
all (none) 队列在群集中的所有节点之间进行镜像。队列将镜像到任何新加入的节点。镜像到所有节点将对所有群集节点施加额外的压力,包括网络 I / O,磁盘 I / O 和磁盘空间使用情况。推荐使用 exactly,设置副本数为(N / 2 +1)。
nodes node names 指定队列创建到哪些节点,如果指定的节点全部不存在,则会出现异常。如果指定的节点在集群中存在,但是暂时不可用,会创建节点到当前客户端连接到的节点。

这里我们以 rabbitmqctl 命令作为案例来讲解配置语法。

语法示例:

exactly 模式
1
rabbitmqctl set_policy ha-two "^two\." '{"ha-mode":"exactly","ha-params":2,"ha-sync-mode":"automatic"}'
  • rabbitmqctl set_policy:固定写法
  • ha-two:策略名称,自定义
  • "^two\.":匹配队列的正则表达式,符合命名规则的队列才生效,这里是任何以two.开头的队列名称
  • '{"ha-mode":"exactly","ha-params":2,"ha-sync-mode":"automatic"}': 策略内容
    • "ha-mode":"exactly":策略模式,此处是 exactly 模式,指定副本数量
    • "ha-params":2:策略参数,这里是 2,就是副本数量为 2,1 主 1 镜像
    • "ha-sync-mode":"automatic":同步策略,默认是 manual,即新加入的镜像节点不会同步旧的消息。如果设置为 automatic,则新加入的镜像节点会把主节点中所有消息都同步,会带来额外的网络开销
all 模式
1
rabbitmqctl set_policy ha-all "^all\." '{"ha-mode":"all"}'
  • ha-all:策略名称,自定义
  • "^all\.":匹配所有以all.开头的队列名
  • '{"ha-mode":"all"}':策略内容
    • "ha-mode":"all":策略模式,此处是 all 模式,即所有节点都会称为镜像节点
nodes 模式
1
rabbitmqctl set_policy ha-nodes "^nodes\." '{"ha-mode":"nodes","ha-params":["rabbit@nodeA", "rabbit@nodeB"]}'
  • rabbitmqctl set_policy:固定写法
  • ha-nodes:策略名称,自定义
  • "^nodes\.":匹配队列的正则表达式,符合命名规则的队列才生效,这里是任何以nodes.开头的队列名称
  • '{"ha-mode":"nodes","ha-params":["rabbit@nodeA", "rabbit@nodeB"]}': 策略内容
    • "ha-mode":"nodes":策略模式,此处是 nodes 模式
    • "ha-params":["rabbit@mq1", "rabbit@mq2"]:策略参数,这里指定副本所在节点名称

测试

我们使用 exactly 模式的镜像,因为集群节点数量为 3,因此镜像数量就设置为 2.

运行下面的命令:

1
docker exec -it mq1 rabbitmqctl set_policy ha-two "^two\." '{"ha-mode":"exactly","ha-params":2,"ha-sync-mode":"automatic"}'

下面,我们创建一个新的队列:

image-20210717231751411

在任意一个 mq 控制台查看队列:

image-20210717231829505

测试数据共享

给 two.queue 发送一条消息:

image-20210717231958996

然后在 mq1、mq2、mq3 的任意控制台查看消息:

image-20210717232108584

测试高可用

现在,我们让 two.queue 的主节点 mq1 宕机:

1
docker stop mq1

查看集群状态:

image-20210717232257420

查看队列状态:

image-20210717232322646

发现依然是健康的!并且其主节点切换到了 rabbit@mq2 上

仲裁队列

从 RabbitMQ 3.8 版本开始,引入了新的仲裁队列,他具备与镜像队里类似的功能,但使用更加方便。

添加仲裁队列

在任意控制台添加一个队列,一定要选择队列类型为 Quorum 类型。

image-20210717234329640

在任意控制台查看队列:

image-20210717234426209

可以看到,仲裁队列的 + 2 字样。代表这个队列有 2 个镜像节点。

因为仲裁队列默认的镜像数为 5。如果你的集群有 7 个节点,那么镜像数肯定是 5;而我们集群只有 3 个节点,因此镜像数量就是 3.

测试

可以参考对镜像集群的测试,效果是一样的。

集群扩容

加入集群

1)启动一个新的 MQ 容器:

1
2
3
4
5
6
7
8
9
docker run -d --net mq-net \
-v ${PWD}/.erlang.cookie:/var/lib/rabbitmq/.erlang.cookie \
-e RABBITMQ_DEFAULT_USER=itcast \
-e RABBITMQ_DEFAULT_PASS=123321 \
--name mq4 \
--hostname mq5 \
-p 8074:15672 \
-p 8084:15672 \
rabbitmq:3.8-management

2)进入容器控制台:

1
docker exec -it mq4 bash

3)停止 mq 进程

1
rabbitmqctl stop_app

4)重置 RabbitMQ 中的数据:

1
rabbitmqctl reset

5)加入 mq1:

1
rabbitmqctl join_cluster rabbit@mq1

6)再次启动 mq 进程

1
rabbitmqctl start_app

image-20210718001909492

增加仲裁队列副本

我们先查看下 quorum.queue 这个队列目前的副本情况,进入 mq1 容器:

1
docker exec -it mq1 bash

执行命令:

1
rabbitmq-queues quorum_status "quorum.queue"

结果:

image-20210718002118357

现在,我们让 mq4 也加入进来:

1
rabbitmq-queues add_member "quorum.queue" "rabbit@mq4"

结果:

image-20210718002253226

再次查看:

1
rabbitmq-queues quorum_status "quorum.queue"

image-20210718002342603

查看控制台,发现 quorum.queue 的镜像数量也从原来的 +2 变成了 +3:

image-20210718002422365

OpenResty

安装

首先你的 Linux 虚拟机必须联网

1)安装开发库

首先要安装 OpenResty 的依赖开发库,执行命令:

1
yum install -y pcre-devel openssl-devel gcc --skip-broken

2)安装 OpenResty 仓库

你可以在你的 CentOS 系统中添加 openresty 仓库,这样就可以便于未来安装或更新我们的软件包(通过 yum check-update 命令)。运行下面的命令就可以添加我们的仓库:

1
yum-config-manager --add-repo https://openresty.org/package/centos/openresty.repo

如果提示说命令不存在,则运行:

1
yum install -y yum-utils

然后再重复上面的命令

3)安装 OpenResty

然后就可以像下面这样安装软件包,比如 openresty

1
yum install -y openresty

4)安装 opm 工具

opm 是 OpenResty 的一个管理工具,可以帮助我们安装一个第三方的 Lua 模块。

如果你想安装命令行工具 opm,那么可以像下面这样安装 openresty-opm 包:

1
yum install -y openresty-opm

5)目录结构

默认情况下,OpenResty 安装的目录是:/usr/local/openresty

image-20200310225539214

看到里面的 nginx 目录了吗,OpenResty 就是在 Nginx 基础上集成了一些 Lua 模块。

6)配置 nginx 的环境变量

打开配置文件:

1
vi /etc/profile

在最下面加入两行:

1
2
export NGINX_HOME=/usr/local/openresty/nginx
export PATH=${NGINX_HOME}/sbin:$PATH

NGINX_HOME:后面是 OpenResty 安装目录下的 nginx 的目录

然后让配置生效:

1
source /etc/profile

启动和运行

OpenResty 底层是基于 Nginx 的,查看 OpenResty 目录的 nginx 目录,结构与 windows 中安装的 nginx 基本一致:

image-20210811100653291

所以运行方式与 nginx 基本一致:

1
2
3
4
5
6
## 启动nginx
nginx
## 重新加载配置
nginx -s reload
## 停止
nginx -s stop

nginx 的默认配置文件注释太多,影响后续我们的编辑,这里将 nginx.conf 中的注释部分删除,保留有效部分。

修改/usr/local/openresty/nginx/conf/nginx.conf文件,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#user  nobody;
worker_processes 1;
error_log logs/error.log;

events {
worker_connections 1024;
}

http {
include mime.types;
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;

server {
listen 8081;
server_name localhost;
location / {
root html;
index index.html index.htm;
}
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
}
}

在 Linux 的控制台输入命令以启动 nginx:

1
nginx

然后访问页面:http://47.92.99.39:8081/,注意ip地址替换为你自己的虚拟机IP:

备注

加载 OpenResty 的 lua 模块 (添加在 nginx.conf 的 http 下面):

1
2
3
4
#lua 模块
lua_package_path "/usr/local/openresty/lualib/?.lua;;";
#c模块
lua_package_cpath "/usr/local/openresty/lualib/?.so;;";

image-20220908151000877

common.lua

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
-- 封装函数,发送http请求,并解析响应
local function read_http(path, params)
local resp = ngx.location.capture(path,{
method = ngx.HTTP_GET,
args = params,
})
if not resp then
-- 记录错误信息,返回404
ngx.log(ngx.ERR, "http not found, path: ", path , ", args: ", args)
ngx.exit(404)
end
return resp.body
end
-- 将方法导出
local _M = {
read_http = read_http
}
return _M

释放 Redis 连接 API:

1
2
3
4
5
6
7
8
9
-- 关闭redis连接的工具方法,其实是放入连接池
local function close_redis(red)
local pool_max_idle_time = 10000 -- 连接的空闲时间,单位是毫秒
local pool_size = 100 --连接池大小
local ok, err = red:set_keepalive(pool_max_idle_time, pool_size)
if not ok then
ngx.log(ngx.ERR, "放入redis连接池失败: ", err)
end
end

读取 Redis 数据的 API:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
-- 查询redis的方法 ip和port是redis地址,key是查询的key
local function read_redis(ip, port, key)
-- 获取一个连接
local ok, err = red:connect(ip, port)
if not ok then
ngx.log(ngx.ERR, "连接redis失败 : ", err)
return nil
end
-- 查询redis
local resp, err = red:get(key)
-- 查询失败处理
if not resp then
ngx.log(ngx.ERR, "查询Redis失败: ", err, ", key = " , key)
end
--得到的数据为空处理
if resp == ngx.null then
resp = nil
ngx.log(ngx.ERR, "查询Redis数据为空, key = ", key)
end
close_redis(red)
return resp
end

开启共享词典:

1
2
## 共享字典,也就是本地缓存,名称叫做:item_cache,大小150m
lua_shared_dict item_cache 150m

Canal

下面我们就开启 mysql 的主从同步机制,让 Canal 来模拟 salve

开启 MySQL 主从

Canal 是基于 MySQL 的主从同步功能,因此必须先开启 MySQL 的主从功能才可以。

这里以之前用 Docker 运行的 mysql 为例:

开启 binlog

打开 mysql 容器挂载的日志文件,我的在/tmp/mysql/conf目录:

image-20210813153241537

修改文件:

1
vi /tmp/mysql/conf/my.cnf

添加内容:

1
2
log-bin=/var/lib/mysql/mysql-bin
binlog-do-db=heima

配置解读:

  • log-bin=/var/lib/mysql/mysql-bin:设置 binary log 文件的存放地址和文件名,叫做 mysql-bin
  • binlog-do-db=heima:指定对哪个 database 记录 binary log events,这里记录 heima 这个库

最终效果:

1
2
3
4
5
6
7
[mysqld]
skip-name-resolve
character_set_server=utf8
datadir=/var/lib/mysql
server-id=1000
log-bin=/var/lib/mysql/mysql-bin
binlog-do-db=heima

设置用户权限

接下来添加一个仅用于数据同步的账户,出于安全考虑,这里仅提供对 heima 这个库的操作权限。

1
2
3
create user canal@'%' IDENTIFIED by 'canal';
GRANT SELECT, REPLICATION SLAVE, REPLICATION CLIENT,SUPER ON *.* TO 'canal'@'%' identified by 'canal';
FLUSH PRIVILEGES;

重启 mysql 容器即可

1
docker restart mysql

测试设置是否成功:在 mysql 控制台,或者 Navicat 中,输入命令:

1
show master status;

image-20200327094735948

安装 Canal

创建网络

我们需要创建一个网络,将 MySQL、Canal、MQ 放到同一个 Docker 网络中:

1
docker network create heima

让 mysql 加入这个网络:

1
docker network connect heima mysql

安装 Canal

课前资料中提供了 canal 的镜像压缩包:

image-20210813161804292

大家可以上传到虚拟机,然后通过命令导入:

1
docker load -i canal.tar

然后运行命令创建 Canal 容器:

1
2
3
4
5
6
7
8
9
10
11
docker run -p 11111:11111 --name canal \
-e canal.destinations=heima \
-e canal.instance.master.address=mysql:3306 \
-e canal.instance.dbUsername=canal \
-e canal.instance.dbPassword=canal \
-e canal.instance.connectionCharset=UTF-8 \
-e canal.instance.tsdb.enable=true \
-e canal.instance.gtidon=false \
-e canal.instance.filter.regex=heima\\..* \
--network heima \
-d canal/canal-server:v1.1.5

说明:

  • -p 11111:11111:这是 canal 的默认监听端口
  • -e canal.instance.master.address=mysql:3306:数据库地址和端口,如果不知道 mysql 容器地址,可以通过docker inspect 容器id来查看
  • -e canal.instance.dbUsername=canal:数据库用户名
  • -e canal.instance.dbPassword=canal :数据库密码
  • -e canal.instance.filter.regex=:要监听的表名称

表名称监听支持的语法:

1
2
3
4
5
6
7
8
mysql 数据解析关注的表,Perl正则表达式.
多个正则之间以逗号(,)分隔,转义符需要双斜杠(\\)
常见例子:
1. 所有表:.* or .*\\..*
2. canal schema下所有表: canal\\..*
3. canal下的以canal打头的表:canal\\.canal.*
4. canal schema下的一张表:canal.test1
5. 多个规则组合使用然后以逗号隔开:canal\\..*,mysql.test1,mysql.test2

Elasticsearch

部署单点 es

创建网络

因为我们还需要部署 kibana 容器,因此需要让 es 和 kibana 容器互联。这里先创建一个网络:

1
docker network create es-net

加载镜像

这里我们采用 elasticsearch 的 7.12.1 版本的镜像,这个镜像体积接近 1G。可以自行 pull 或者上传tar包。

1
docker pull elasticsearch:7.12.1

如果采用上传的方式,上传到虚拟机中后运行命令加载即可:

1
2
## 导入数据
docker load -i es.tar

同理还有kibana的 tar 包也需要这样做。

运行

运行 docker 命令,部署单点 es:

1
2
3
4
5
6
7
8
9
10
11
docker run -d \
--name es \
-e "ES_JAVA_OPTS=-Xms512m -Xmx512m" \
-e "discovery.type=single-node" \
-v es-data:/usr/share/elasticsearch/data \
-v es-plugins:/usr/share/elasticsearch/plugins \
--privileged \
--network es-net \
-p 9200:9200 \
-p 9300:9300 \
elasticsearch:7.12.1

命令解释:

  • -e "cluster.name=es-docker-cluster":设置集群名称
  • -e "http.host=0.0.0.0":监听的地址,可以外网访问
  • -e "ES_JAVA_OPTS=-Xms512m -Xmx512m":内存大小
  • -e "discovery.type=single-node":非集群模式
  • -v es-data:/usr/share/elasticsearch/data:挂载逻辑卷,绑定 es 的数据目录
  • -v es-logs:/usr/share/elasticsearch/logs:挂载逻辑卷,绑定 es 的日志目录
  • -v es-plugins:/usr/share/elasticsearch/plugins:挂载逻辑卷,绑定 es 的插件目录
  • --privileged:授予逻辑卷访问权
  • --network es-net :加入一个名为 es-net 的网络中
  • -p 9200:9200:端口映射配置

在浏览器中输入:http://IP:9200 即可看到 elasticsearch 的响应结果:

image-20210506101053676

部署 kibana

kibana 可以给我们提供一个 elasticsearch 的可视化界面,便于我们学习。

拉取镜像

1
docker pull kibana:7.12.1

部署

运行 docker 命令,部署 kibana

1
2
3
4
5
6
docker run -d \
--name kibana \
-e ELASTICSEARCH_HOSTS=http://es:9200 \
--network=es-net \
-p 5601:5601 \
kibana:7.12.1
  • --network es-net :加入一个名为 es-net 的网络中,与 elasticsearch 在同一个网络中
  • -e ELASTICSEARCH_HOSTS=http://es:9200":设置 elasticsearch 的地址,因为 kibana 已经与 elasticsearch 在一个网络,因此可以用容器名直接访问 elasticsearch
  • -p 5601:5601:端口映射配置

kibana 启动一般比较慢,需要多等待一会,可以通过命令:

1
docker logs -f kibana

查看运行日志,当查看到下面的日志,说明成功:

image-20210109105135812

此时,在浏览器输入地址访问:http://IP:5601,即可看到结果

DevTools

kibana 中提供了一个 DevTools 界面:

image-20210506102630393

这个界面中可以编写 DSL 来操作 elasticsearch。并且对 DSL 语句有自动补全功能。

安装 IK 分词器

在线安装 ik 插件(较慢)

1
2
3
4
5
6
7
8
9
10
## 进入容器内部
docker exec -it elasticsearch /bin/bash

## 在线下载并安装
./bin/elasticsearch-plugin install https://github.com/medcl/elasticsearch-analysis-ik/releases/download/v7.12.1/elasticsearch-analysis-ik-7.12.1.zip

#退出
exit
#重启容器
docker restart elasticsearch

离线安装 ik 插件(推荐)

1)查看数据卷目录

安装插件需要知道 elasticsearch 的 plugins 目录位置,而我们用了数据卷挂载,因此需要查看 elasticsearch 的数据卷目录,通过下面命令查看:

1
docker volume inspect es-plugins

显示结果:

1
2
3
4
5
6
7
8
9
10
11
[
{
"CreatedAt": "2022-05-06T10:06:34+08:00",
"Driver": "local",
"Labels": null,
"Mountpoint": "/var/lib/docker/volumes/es-plugins/_data",
"Name": "es-plugins",
"Options": null,
"Scope": "local"
}
]

说明 plugins 目录被挂载到了:/var/lib/docker/volumes/es-plugins/_data 这个目录中。

2)解压缩分词器安装包

解压缩 ik 分词器,重命名为ik

3)上传到 es 容器的插件数据卷中

也就是/var/lib/docker/volumes/es-plugins/_data

image-20210506110704293

4)重启容器
1
2
## 4、重启容器
docker restart es
1
2
## 查看es日志
docker logs -f es
5)测试:

IK 分词器包含两种模式:

  • ik_smart:最少切分

  • ik_max_word:最细切分

1
2
3
4
5
GET /_analyze
{
"analyzer": "ik_max_word",
"text": "黑马程序员学习java太棒了"
}

结果:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
{
"tokens": [
{
"token": "黑马",
"start_offset": 0,
"end_offset": 2,
"type": "CN_WORD",
"position": 0
},
{
"token": "程序员",
"start_offset": 2,
"end_offset": 5,
"type": "CN_WORD",
"position": 1
},
{
"token": "程序",
"start_offset": 2,
"end_offset": 4,
"type": "CN_WORD",
"position": 2
},
{
"token": "员",
"start_offset": 4,
"end_offset": 5,
"type": "CN_CHAR",
"position": 3
},
{
"token": "学习",
"start_offset": 5,
"end_offset": 7,
"type": "CN_WORD",
"position": 4
},
{
"token": "java",
"start_offset": 7,
"end_offset": 11,
"type": "ENGLISH",
"position": 5
},
{
"token": "太棒了",
"start_offset": 11,
"end_offset": 14,
"type": "CN_WORD",
"position": 6
},
{
"token": "太棒",
"start_offset": 11,
"end_offset": 13,
"type": "CN_WORD",
"position": 7
},
{
"token": "了",
"start_offset": 13,
"end_offset": 14,
"type": "CN_CHAR",
"position": 8
}
]
}

扩展词词典

随着互联网的发展,“造词运动”也越发的频繁。出现了很多新的词语,在原有的词汇列表中并不存在。比如:“奥力给”,“传智播客” 等。

所以我们的词汇也需要不断的更新,IK 分词器提供了扩展词汇的功能。

1)打开 IK 分词器 config 目录:

image-20210506112225508

2)在 IKAnalyzer.cfg.xml 配置文件内容添加:

1
2
3
4
5
6
7
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE properties SYSTEM "http://java.sun.com/dtd/properties.dtd">
<properties>
<comment>IK Analyzer 扩展配置</comment>
<!--用户可以在这里配置自己的扩展字典 *** 添加扩展词典-->
<entry key="ext_dict">ext.dic</entry>
</properties>

3)新建一个 ext.dic,可以参考 config 目录下复制一个配置文件进行修改

1
2
传智播客
奥力给

4)重启 elasticsearch

1
2
3
4
docker restart es

## 查看 日志
docker logs -f elasticsearch

image-20201115230900504

日志中已经成功加载 ext.dic 配置文件

5)测试效果:

1
2
3
4
5
GET /_analyze
{
"analyzer": "ik_max_word",
"text": "传智播客Java就业超过90%,奥力给!"
}

注意当前文件的编码必须是 UTF-8 格式,严禁使用 Windows 记事本编辑

停用词词典

在互联网项目中,在网络间传输的速度很快,所以很多语言是不允许在网络上传递的,如:关于宗教、政治等敏感词语,那么我们在搜索时也应该忽略当前词汇。

IK 分词器也提供了强大的停用词功能,让我们在索引时就直接忽略当前的停用词汇表中的内容。

1)IKAnalyzer.cfg.xml 配置文件内容添加:

1
2
3
4
5
6
7
8
9
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE properties SYSTEM "http://java.sun.com/dtd/properties.dtd">
<properties>
<comment>IK Analyzer 扩展配置</comment>
<!--用户可以在这里配置自己的扩展字典-->
<entry key="ext_dict">ext.dic</entry>
<!--用户可以在这里配置自己的扩展停止词字典 *** 添加停用词词典-->
<entry key="ext_stopwords">stopword.dic</entry>
</properties>

3)在 stopword.dic 添加停用词

1
习大大

4)重启 elasticsearch

1
2
3
4
5
6
## 重启服务
docker restart elasticsearch
docker restart kibana

## 查看 日志
docker logs -f elasticsearch

日志中已经成功加载 stopword.dic 配置文件

5)测试效果:

1
2
3
4
5
GET /_analyze
{
"analyzer": "ik_max_word",
"text": "传智播客Java就业率超过95%,习大大都点赞,奥力给!"
}

注意当前文件的编码必须是 UTF-8 格式,严禁使用 Windows 记事本编辑

部署 es 集群

部署 es 集群可以直接使用 docker-compose 来完成,不过要求你的 Linux 虚拟机至少有4G的内存空间

首先编写一个 docker-compose 文件,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
version: '2.2'
services:
es01:
image: docker.elastic.co/elasticsearch/elasticsearch:7.12.1
container_name: es01
environment:
- node.name=es01
- cluster.name=es-docker-cluster
- discovery.seed_hosts=es02,es03
- cluster.initial_master_nodes=es01,es02,es03
- bootstrap.memory_lock=true
- "ES_JAVA_OPTS=-Xms512m -Xmx512m"
ulimits:
memlock:
soft: -1
hard: -1
volumes:
- data01:/usr/share/elasticsearch/data
ports:
- 9200:9200
networks:
- elastic
es02:
image: docker.elastic.co/elasticsearch/elasticsearch:7.12.1
container_name: es02
environment:
- node.name=es02
- cluster.name=es-docker-cluster
- discovery.seed_hosts=es01,es03
- cluster.initial_master_nodes=es01,es02,es03
- bootstrap.memory_lock=true
- "ES_JAVA_OPTS=-Xms512m -Xmx512m"
ulimits:
memlock:
soft: -1
hard: -1
volumes:
- data02:/usr/share/elasticsearch/data
networks:
- elastic
es03:
image: docker.elastic.co/elasticsearch/elasticsearch:7.12.1
container_name: es03
environment:
- node.name=es03
- cluster.name=es-docker-cluster
- discovery.seed_hosts=es01,es02
- cluster.initial_master_nodes=es01,es02,es03
- bootstrap.memory_lock=true
- "ES_JAVA_OPTS=-Xms512m -Xmx512m"
ulimits:
memlock:
soft: -1
hard: -1
volumes:
- data03:/usr/share/elasticsearch/data
networks:
- elastic

volumes:
data01:
driver: local
data02:
driver: local
data03:
driver: local

networks:
elastic:
driver: bridge

Run docker-compose to bring up the cluster:

1
docker-compose up

MinIO

  1. 拉取docker镜像
1
docker pull minio/minio
  1. 设置minio用到的文件路径
1
mkdir minio

进入minio目录:

1
2
mkdir data
mkdir config
  1. 启动服务:注意,这里要单独设置console的端口,不然会报错,且无法访问

这种安装方式 MinIO 自定义 Access 和 Secret 密钥要覆盖 MinIO 的自动生成的密钥

1
2
3
4
5
6
7
8
9
10
docker run --name minio \
-p 9000:9000 \
-p 9999:9999 \
-d --restart=always \
-e "MINIO_ROOT_USER=admin" \
-e "MINIO_ROOT_PASSWORD=admin123" \
-v /home/minio/data:/data \
-v /home/minio/config:/root/.minio \
minio/minio server /data \
--console-address '0.0.0.0:9999'
  1. 防火墙设置,需要为minio开放两个端口,一个9000端口,一个静态端口,此处为9999
1
2
3
firewall-cmd --zone=public --add-port=9000/tcp --permanent
firewall-cmd --zone=public --add-port=9999/tcp --permanent
firewall-cmd --reload
  1. 登录客户端(浏览器):注意—>此处的端口,是你设置的console的端口:9999

http://ip:9999

image-20230819161451580

此处的用户名密码为启动服务时,设置的用户名密码:admin admin123:

image-20230819161548871

Reference

  1. https://github.com/hansonwang99/JavaCollection
  2. 黑马程序员
  3. 尚硅谷