大家都知道 Docker 是个非常好用的容器工具,但是很多人对这个工具怎么在自己的服务器上安装和启动都比较陌生,因为 Docker 现在很多人都使用的是 Windows 的,尽管这个工具有很多公司对他抱有反对的态度,但是技术嘛,我们还是要学习一下的,今天我们就学一下 Docker 的安装,和安装镜像,并且实现一个小功能。
安装Docker
1.在线安装
curl -fsSL https://get.docker.com | bash -s docker --mirror Aliyun
在线安装方式二
curl -sSL https://get.daocloud.io/docker | sh
3.查看Docker
yum list docker-ce --showduplicates | sort -r
Installed Packages
docker-ce.x86_64 3:20.10.8-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.8-3.el8 @docker-ce-stable
docker-ce.x86_64 3:20.10.7-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.6-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.5-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.4-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.3-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.2-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.1-3.el8 docker-ce-stable
docker-ce.x86_64 3:20.10.0-3.el8 docker-ce-stable
docker-ce.x86_64 3:19.03.15-3.el8 docker-ce-stable
docker-ce.x86_64 3:19.03.14-3.el8 docker-ce-stable
docker-ce.x86_64 3:19.03.13-3.el8 docker-ce-stable
4.查看Docker版本
docker version
Client: Docker Engine - Community
Version: 20.10.8
API version: 1.41
Go version: go1.16.6
Git commit: 3967b7d
Built: Fri Jul 30 19:53:39 2021
OS/Arch: linux/amd64
Context: default
Experimental: true
Server: Docker Engine - Community
Engine:
Version: 20.10.8
API version: 1.41 (minimum version 1.12)
Go version: go1.16.6
Git commit: 75249d8
Built: Fri Jul 30 19:52:00 2021
OS/Arch: linux/amd64
Experimental: false
containerd:
Version: 1.4.9
GitCommit: e25210fe30a0a703442421b0f60afac609f950a3
runc:
Version: 1.0.1
GitCommit: v1.0.1-0-g4144b63
docker-init:
Version: 0.19.0
GitCommit: de40ad0
5.启动Docker
systemctl start docker
6.测试Docker是否启动成功
(1).拉取HelloWorld的镜像
docker pull hello-world
Using default tag: latest
latest: Pulling from library/hello-world
Digest: sha256:7d91b69e04a9029b99f3585aaaccae2baa80bcf318f4a5d2165a9898cd2dc0a1
Status: Image is up to date for hello-world:latest
docker.io/library/hello-world:latest
(2).运行hello-world镜像
docker run hello-world
看到下面的图就证明安装成功了
代码语言:javascript复制
Hello from Docker!
This message shows that your installation appears to be working correctly.
To generate this message, Docker took the following steps:
1. The Docker client contacted the Docker daemon.
2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
(amd64)
3. The Docker daemon created a new container from that image which runs the
executable that produces the output you are currently reading.
4. The Docker daemon streamed that output to the Docker client, which sent it
to your terminal.
To try something more ambitious, you can run an Ubuntu container with:
$ docker run -it ubuntu bash
Share images, automate workflows, and more with a free Docker ID:
https://hub.docker.com/
For more examples and ideas, visit:
https://docs.docker.com/get-started/
Docker 安装各种开发必备内容
1.Docker 安装 Redis
- 查看 Redis 的版本
docker search redis
2.取最新版的 Redis 镜像
docker pull redis:latest
3.查看本地镜像
docker images
4.运行容器(这是只能本地访问,但是我们需要进行外网访问)
docker run -itd --name redis-test -p 6379:6379 redis
-p 6379:6379:映射容器服务的 6379 端口到宿主机的 6379 端口。外部可以直接通过宿主机ip:6379 访问到 Redis 的服务。
5.通过 redis-cli 连接测试使用 redis 服务。
docker exec -it redis-test /bin/bash
6.查看 Redis是否启动成功
ps aux | grep redis-server
出现如下,则为成功
代码语言:javascript复制systemd 27456 0.4 0.6 52976 12932 ? Ssl 17:29 0:00 redis-server *:6379
root 27495 0.0 0.0 12112 1088 pts/1 S 17:30 0:00 grep --color=auto redis-server
上面的方法只能本地访问,我们需要的是外网访问redis
4.创建conf 和 data 文件夹
mkdir /usr/local/docker/conf
/usr/local/docker/data
然后再conf下创建redis.conf 的配置文件
放入如下内容,密码可不用配置
代码语言:javascript复制#bind 127.0.0.1 //允许远程连接
protected-mode no
appendonly yes //持久化
requirepass 123456 //密码
- 创建redis容器并启动
docker run --privileged=true --name redis-server -p 6379:6379 -v /usr/local/docker/data:/data -v /usr/local/docker/conf/redis.conf:/etc/redis/redis.conf -d redis redis-server /etc/redis/redis.conf
6.查看Redis是否启动
docker ps
就可以看到redis了,如果状态是UP,那么就可以确定是安装成功了,启动完成之后,把云服务器的6379端口出入打开,就可以看到了。
这时候我们就可以去使用外部工具进行连接了。
直接在本地就可以连接我们在服务器上装好的 Redis了。
Redis装好了,我们就来写个小代码实现一下 Redis 排行榜的功能把。
Redis怎么去实现排行榜的功能呢?这实际上也是非常有意思的一个需求,我们先来确定一下 Redis 实现排行榜都需要准备什么样子的工作。
Redis实现排行榜
为什么 Redis 可以实现排行榜的功能呢?
这也是和数据结构有一定的关系,因为我们大家的认知里面,都知道 Redis 支持各种数据类型的存储,有 String 有 List,还有 Set ,而 Redis 中就是因为有了这个 Set 所以实现排行榜就相对来说比较简单了,因为 Set 是有序的。
Sorted Sets数据类型就像是set和hash的混合,与sets一样,Sorted Sets是唯一的,不重复的字符串组成。可以说Sorted Sets也是Sets的一种。
Sorted Sets是通过Skip List(跳跃表)和hash Table(哈希表)的双端口数据结构实现的,因此每次添加元素时,Redis都会执行O(log(N))操作。所以当我们要求排序的时候,Redis根本不需要做任何工作了,早已经全部排好序了。元素的分数可以随时更新。
使用 Redis 实现排行榜
我们使用 Springboot 来整合一下 Redis 然后使用 Sorted Sets 来实现一下我们想做的这个排行榜。
- 创建 Springboot 项目,导入依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.68</version>
</dependency>
我们在这里就使用 RedisTemplate,
2.增加配置
代码语言:javascript复制server:
port: 9001
spring:
redis:
#这个地址可以用自己刚才在 Docker 上安装的地址,阿粉就不给大家放了,毕竟自己的云服务器,大家都懂
host: 127.0.0.1
port: 6379
password: 123456
jedis:
pool:
max-active: 8
max-wait: -1
max-idle: 500
min-idle: 0
lettuce:
shutdown-timeout: 0
给 Redis 中存数据信息
代码语言:javascript复制@Test
public void batchAdd() {
Set<ZSetOperations.TypedTuple<String>> tuples = new HashSet<>();
long start = System.currentTimeMillis();
for (int i = 0; i < 100000; i ) {
DefaultTypedTuple<String> tuple = new DefaultTypedTuple<>("chuyikeji" i, 1D i);
tuples.add(tuple);
}
System.out.println("循环时间:" ( System.currentTimeMillis() - start));
Long num = redisTemplate.opsForZSet().add(SCORE_RANK, tuples);
System.out.println("批量新增时间:" (System.currentTimeMillis() - start));
System.out.println("受影响行数:" num);
}
运行我们的测试可以看到
代码语言:javascript复制循环时间:56
批量新增时间:1015
受影响行数:100000
获取前10名(根据分数倒序)
代码语言:javascript复制@Test
public void list() {
Set<String> range = redisTemplate.opsForZSet().reverseRange(SCORE_RANK, 0, 10);
System.out.println("获取到的排行列表:" JSON.toJSONString(range));
Set<ZSetOperations.TypedTuple<String>> rangeWithScores = redisTemplate.opsForZSet().reverseRangeWithScores(SCORE_RANK, 0, 10);
System.out.println("获取到的排行和分数列表:" JSON.toJSONString(rangeWithScores));
}
这时候我们就能看到数据信息
代码语言:javascript复制
获取到的排行列表:["chuyikeji99999","chuyikeji99998","chuyikeji99997","chuyikeji99996","chuyikeji99995","chuyikeji99994","chuyikeji99993","chuyikeji99992","chuyikeji99991","chuyikeji99990","chuyikeji99989"]
获取到的排行和分数列表:[{"score":100000.0,"value":"chuyikeji99999"},{"score":99999.0,"value":"chuyikeji99998"},{"score":99998.0,"value":"chuyikeji99997"},{"score":99997.0,"value":"chuyikeji99996"},{"score":99996.0,"value":"chuyikeji99995"},{"score":99995.0,"value":"chuyikeji99994"},{"score":99994.0,"value":"chuyikeji99993"},{"score":99993.0,"value":"chuyikeji99992"},{"score":99992.0,"value":"chuyikeji99991"},{"score":99991.0,"value":"chuyikeji99990"},{"score":99990.0,"value":"chuyikeji99989"}]
我们在开头使用了批量新增的方式直接给把所有的数据都填充进去了,实际上肯定不是这个样子的,因为大部分的数据我们肯定都是一条记录一条记录增加的,比如现在有个新人 aaaa 他的得分是777 这时候我们要插入到 Redis 中
代码语言:javascript复制
@Test
public void add() {
redisTemplate.opsForZSet().add(SCORE_RANK, "aaaa", 777);
}
这时候我们获取一下 aaaa 的排名情况。
代码语言:javascript复制
@Test
public void find(){
Long rankNum = redisTemplate.opsForZSet().reverseRank(SCORE_RANK, "aaaa");
System.out.println("aaaa的个人排名:" rankNum);
Double score = redisTemplate.opsForZSet().score(SCORE_RANK, "aaaa");
System.out.println("aaaa的分数:" score);
}
这时候我们看一下打印出来的结果
代码语言:javascript复制aaaa的个人排名:99224
aaaa的分数:777.0
如果我们在其中想查询 700分到800分之间的人数?
代码语言:javascript复制@Test
public void count(){
Long count = redisTemplate.opsForZSet().count(SCORE_RANK, 701, 800);
System.out.println("统计700-800之间的人数:" count);
}
代码语言:javascript复制统计700-800之间的人数:101
这样是不是就实现了一个简易版的排行榜的功能呢?不过这种简单的代码,阿粉相信各位读者一定是可以完成的,但是对于刚入行的新人来说,还是有一点帮助的,你说是不是呢?