【计算基础|Redis01】【上手】安装连接、配置与通用命令
很多人学 Redis 的第一步就走错:直接 docker run 起个容器,然后对着 redis-cli 瞎敲一通,连密码怎么带、中文为什么是一串十六进制、KEYS * 能不能在生产用都不知道,就急着上业务。Redis 上手其实半天就够,但安装、连接、配置、key 的通用命令这几块是地基,地基不牢后面全是玄学。
这篇把"把 Redis 跑起来 → 连上 → 看懂配置 → 用通用命令操作 key → 事务和发布订阅"整条链路在 Docker 里真跑一遍,每条命令都给语法→实例→预期输出→易错点,照着敲就能干活。所有输出来自 Redis 7.4 真实实例。
环境:Docker Desktop,官方镜像
redis:7(实跑版本 redis-server / redis-cli 7.4.11),macOS。容器内端口仍是 6379;为避免和本机其他容器冲突,我把宿主机端口映成了 16379,你照着敲用默认 6379 即可。
一、Docker 起一个 Redis:别装系统包
结论先给:学习和开发一律用 Docker 起 Redis ,别 apt install / brew install------版本不好控、删不干净、和生产对不上。一条命令的事。
1.1 最简启动
bash
docker run -d --name redis7 -p 6379:6379 redis:7
| 部分 | 含义 |
|---|---|
-d |
后台运行 |
--name redis7 |
容器名,后面 docker exec 靠它找容器 |
-p 6379:6379 |
宿主机 6379 → 容器内 6379 |
redis:7 |
用 7.x 最新稳定版(实跑为 7.4.11),生产建议锁小版本如 redis:7.4 |
进容器里用自带的 redis-cli 连:
bash
docker exec -it redis7 redis-cli
-it 是开交互式终端。进去后就是 127.0.0.1:6379> 的提示符,直接敲命令。不想进交互,也可以一条一条地跑(本文后面的输出都这么采):
bash
docker exec redis7 redis-cli PING
text
PONG
✅ 成功标志 :PING 返回 PONG。这是 Redis 的心跳,以后"连上没"一律先敲 PING。
1.2 看日志、看版本
bash
docker logs redis7 # 看启动日志
docker exec redis7 redis-cli --version
docker exec redis7 redis-cli INFO server | grep -E "redis_version|tcp_port|uptime_in_days"
实跑输出:
text
redis-cli 7.4.11
# INFO server 截取
redis_version:7.4.11
os:Linux 7.0.14-linuxkit aarch64
tcp_port:6379
uptime_in_days:0
🔴 排障第一步永远是这三样:docker logs 看是不是启动就崩了,INFO server 看版本/端口/运行时长。连不上时别瞎猜,先看日志。
1.3 带密码启动(生产必做)
裸奔的 Redis 谁都能连,生产等于把数据库挂在公网上。加密码:
bash
docker run -d --name redis7 -p 6379:6379 redis:7 --requirepass redis123
注意 redis:7 后面的 --requirepass redis123 是传给 redis-server 的参数,不是 docker 的参数。
连的时候带密码:
bash
docker exec -it redis7 redis-cli -a redis123
不带密码直接操作会被拒:
text
NOAUTH Authentication required.
⚠️ -a 的坑 :密码会出现在进程列表里(ps 能看到)。实跑有警告:
text
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
更安全的做法是用环境变量 REDISCLI_AUTH,命令行里完全不出现密码:
bash
docker exec -e REDISCLI_AUTH=redis123 -it redis7 redis-cli
实跑:
bash
docker exec -e REDISCLI_AUTH=redis123 redis-cli PING # PONG,且无警告
1.4 远程连接参数
redis-cli 默认连 127.0.0.1:6379,连远程机器用 -h(host)和 -p(port):
bash
redis-cli -h 192.168.1.10 -p 6379 -a redis123
1.5 --raw:中文不乱码的关键
交互式 redis-cli 里,中文等非 ASCII 字节默认会转义成十六进制 显示(比如 \xe5\xbc\xa0),看起来像乱码。加 --raw 就按原样输出:
bash
docker exec redis7 redis-cli --raw GET user:1
本文是通过脚本批量抓输出(非 TTY),中文直出。你自己在终端里交互时,遇到一串
\x..别慌,加--raw即可。
二、配置:redis.conf 在哪、怎么改、改完生不生效
结论:Redis 的配置有三种改法------启动时指定配置文件、命令行参数、运行时 CONFIG SET 。前两种重启后还在,CONFIG SET 立刻生效但重启丢失,要持久化得 CONFIG REWRITE。
2.1 配置文件位置
官方 redis:7 镜像默认不带 redis.conf (启动参数就是 redis-server,全用默认值)。实跑验证:
bash
docker exec redis7 sh -c 'ls /usr/local/etc/redis/redis.conf /etc/redis/redis.conf'
text
ls: cannot access '/usr/local/etc/redis/redis.conf': No such file or directory
ls: cannot access '/etc/redis/redis.conf': No such file or directory
所以 Docker 里一般这么干:把宿主机的 redis.conf 挂进容器,再用它启动:
bash
docker run -d --name redis7 -p 6379:6379 \
-v /my/redis.conf:/usr/local/etc/redis/redis.conf \
redis:7 redis-server /usr/local/etc/redis/redis.conf
最后那个参数就是"用这份配置启动"。
2.2 常用配置项速查表
| 配置项 | 作用 | 默认值(实跑) | 动态生效? |
|---|---|---|---|
port |
监听端口 | 6379 |
否,重启 |
bind |
绑定网卡 | * -::*(容器内) |
否 |
protected-mode |
保护模式 | 容器内 no |
是 |
requirepass |
访问密码 | 空 | 是 |
daemonize |
是否后台守护 | no(容器内别开) |
否 |
maxmemory |
最大内存上限 | 0(不限) |
是 |
maxmemory-policy |
内存满了的淘汰策略 | noeviction(不淘汰,写报错) |
是 |
appendonly |
是否开启 AOF 持久化 | no |
是 |
save |
RDB 快照规则 | 默认 3600s/1 次等 | 是 |
databases |
逻辑库个数 | 16 |
否,重启 |
logfile |
日志文件路径 | 空(打 stdout) | 否 |
timeout |
空闲连接秒数断开 | 0(不断) |
是 |
tcp-keepalive |
TCP 保活秒 | 300 |
是 |
2.3 运行时查看与修改(CONFIG 命令)
不用重启、不用改文件,在线看、在线改:
bash
# 查看:CONFIG GET 参数名(支持 * 通配)
docker exec redis7 redis-cli CONFIG GET maxmemory
docker exec redis7 redis-cli CONFIG GET maxmemory-policy
text
maxmemory
0
maxmemory-policy
noeviction
动态修改(立刻生效):
bash
docker exec redis7 redis-cli CONFIG SET maxmemory 104857600
docker exec redis7 redis-cli CONFIG GET maxmemory
text
OK
maxmemory
104857600
⚠️ 不是所有参数 CONFIG SET 都完全生效 。比如 appendonly yes 实跑返回 OK(会后台开始写 AOF),但像 port、databases 这类必须重启。改之前查上表或官方文档。
想把这次运行时的改动写回配置文件 ,用 CONFIG REWRITE:
bash
docker exec redis7 redis-cli CONFIG REWRITE
text
ERR The server is running without a config file
🔴 上面这行报错是预期内 ------官方镜像没挂配置文件,Redis 不知道往哪写。只有当你是"用 redis.conf 启动"的,REWRITE 才有用。别看到报错以为坏了。
三、通用 key 命令:所有数据类型共用的那批
Redis 是个大 key-value 仓库,下面这些命令不管你的 value 是字符串还是集合都能用,是日常用得最多的。
3.1 基本读写与删除
| 命令 | 语法 | 作用 | 返回 |
|---|---|---|---|
| SET | SET key value |
写 | OK |
| GET | GET key |
读 | 值 / 不存在返回空 |
| DEL | DEL key [key...] |
删 | 删掉的个数 |
| EXISTS | EXISTS key |
判断存在 | 1 存在 / 0 不存在 |
实跑:
bash
docker exec redis7 redis-cli SET name "redis"
docker exec redis7 redis-cli GET name
docker exec redis7 redis-cli SET tmp 1
docker exec redis7 redis-cli EXISTS tmp # 1
docker exec redis7 redis-cli DEL tmp # (integer) 1
docker exec redis7 redis-cli EXISTS tmp # 0
text
OK
redis
OK
1
1
0
3.2 过期时间:EXPIRE / TTL / PERSIST
这是 Redis 当缓存的命根子------key 到点自动删。
| 命令 | 语法 | 作用 |
|---|---|---|
| EXPIRE | EXPIRE key seconds |
设 N 秒后过期 |
| PEXPIRE | PEXPIRE key ms |
毫秒版 |
| TTL | TTL key |
查剩余秒数 |
| PERSIST | PERSIST key |
取消过期,变成永久 |
实跑:
bash
docker exec redis7 redis-cli SET session:1 "user=alice"
docker exec redis7 redis-cli EXPIRE session:1 60 # 返回 1 表示设置成功
docker exec redis7 redis-cli TTL session:1 # 60
docker exec redis7 redis-cli PERSIST session:1 # 1 表示成功取消
docker exec redis7 redis-cli TTL session:1 # -1
text
OK
1
60
1
-1
🔴 TTL 返回值三态 :>0 剩余秒数;-1 永久不过期;-2 key 不存在。写代码时别只判"有没有",要分清 -1 和 -2。
3.3 TYPE:看 key 是什么类型
bash
docker exec redis7 redis-cli SET strkey "hello"
docker exec redis7 redis-cli TYPE strkey # string
docker exec redis7 redis-cli LPUSH listkey a b c
docker exec redis7 redis-cli TYPE listkey # list
text
OK
string
list
⚠️ 对不存在的 key,TYPE 返回 none。
3.4 KEYS vs SCAN:千万别在生产用 KEYS
| 命令 | 语法 | 说明 |
|---|---|---|
| KEYS | KEYS pattern |
一把梭返回所有匹配 key,O(N),阻塞 |
| SCAN | SCAN cursor [MATCH p] [COUNT n] |
增量游标遍历,不阻塞 |
bash
docker exec redis7 redis-cli MSET user:1 "张三" user:2 "李四" user:3 "王五" order:1001 "paid"
docker exec redis7 redis-cli KEYS "user:*"
text
user:1
user:2
user:3
⚠️ KEYS * 在生产是事故级命令 。Redis 单线程,库里有几百万 key 时,KEYS 一把全扫,期间整个 Redis 卡死、所有请求超时。线上要遍历一律用 SCAN:
bash
docker exec redis7 redis-cli SCAN 0 MATCH "user:*" COUNT 10
text
0
user:3
user:2
user:1
SCAN 的返回第一行是下一轮的游标 。这次返回 0 表示遍历完了;如果不是 0,就把这个游标作为下一次 SCAN 的入参接着遍历,直到游标回 0。COUNT 10 是"建议每次扫 10 个",不是"只返回 10 个"的硬限制。
3.5 RENAME、DBSIZE
bash
docker exec redis7 redis-cli RENAME strkey strkey_renamed
docker exec redis7 redis-cli GET strkey_renamed # hello
docker exec redis7 redis-cli DBSIZE # 当前库 key 总数
⚠️ RENAME 的 newkey 如果已存在,会被静默覆盖,先确认目标名不撞车。
3.6 SELECT 多逻辑库
Redis 自带"数据库分库",默认 16 个(0~15),用 SELECT 切换:
bash
docker exec redis7 redis-cli SET dbmark "in-db0" # 在 db0
docker exec redis7 redis-cli -n 5 SELECT 5
docker exec redis7 redis-cli -n 5 SET mark5 "yes"
docker exec redis7 redis-cli -n 5 GET mark5 # yes
docker exec redis7 redis-cli -n 0 GET dbmark # in-db0
实跑还试了越界的 16 号库:
bash
docker exec redis7 redis-cli -n 16 SELECT 16
text
ERR DB index is out of range
⚠️ 三个坑:
- 默认就 16 个库,
SELECT 16直接报DB index is out of range(实跑如上)。 - 生产基本不用多库做隔离 ------它不是真正的隔离,一个 RDB/AOF 文件全装下,一个
FLUSHALL全没。隔离用独立实例。 - 🔴 Redis Cluster 模式只允许用 db0,SELECT 别的库直接报错。
3.7 FLUSHDB / FLUSHALL:高危,看着敲
bash
FLUSHDB # 清空当前库
FLUSHALL # 清空所有库
⚠️ 这俩删数据不可恢复,没有二次确认 。本文只在沙箱容器里演示。生产环境建议直接在配置里 rename-command FLUSHALL "" 把它禁掉,防止手滑。
四、事务:MULTI / EXEC / DISCARD
很多人以为 Redis 事务像 MySQL 那样"要么全成要么全回滚"。不是。 Redis 事务是"把命令打包,一次性顺序执行",它的原子性和你想的不一样。
4.1 正常事务
bash
MULTI # 开事务,之后的命令先入队,不立刻执行
SET a 1
INCR counter
GET counter
EXEC # 一次性把队列里的命令全执行
text
OK
QUEUED
QUEUED
QUEUED
OK
11
11
QUEUED 表示"入队成功,先存着"。EXEC 后才真正执行,返回每步结果(OK、11、11)。
4.2 两种错误:一种全拒,一种不回滚
🔴 Redis 事务不提供回滚,分两种情况:
① 入队时就语法错(命令都不认识)→ EXEC 整体拒绝:
bash
MULTI
SET a 1
BADCOMMAND x # 这命令不存在
EXEC
text
OK
QUEUED
ERR unknown command 'BADCOMMAND', with args beginning with: 'x'
EXECABORT Transaction discarded because of previous errors.
② 入队时语法对、运行时才出错 → 不回滚,前面成功的照样生效:
bash
SET mykey 5
MULTI
SET mykey "hello" # 语法对,入队成功
INCR mykey # 运行时才发现"hello"不是整数,报错
GET mykey
EXEC
text
OK
QUEUED
QUEUED
QUEUED
OK # SET 真的生效了
ERR value is not an integer or out of range # INCR 失败
hello # mykey 被改成了 hello,没有回滚!
⚠️ 看最后一行:SET mykey "hello" 成功了,INCR 失败了,但 SET 没有被回滚。这就是 Redis 事务和关系数据库最大的区别------它只管"命令要么排队要么不排",运行期错误它不负责回滚。想要"出错撤销"得靠 Lua 脚本(后面的篇章讲)。
4.3 DISCARD:放弃事务
bash
MULTI
SET x 1
DISCARD # 不入队了,整个事务取消
EXISTS x # 0,x 根本没写进去
text
OK
QUEUED
OK
0
4.4 WATCH:乐观锁
WATCH key 在事务前盯一个 key。从 WATCH 到 EXEC 之间,只要这个 key 被任何客户端改过,这次 EXEC 就放弃执行(返回 nil),常用于"先读再写"的并发场景。
实跑:A 连接 WATCH stock 后,B 连接把 stock 从 100 改成 50,A 再 MULTI / DECRBY stock 10 / EXEC:
text
OK # A: WATCH stock
--- B 客户端把 stock 改成 50 ---
OK # B: SET stock 50
OK # A: MULTI
QUEUED # A: DECRBY 入队
# EXEC 返回空(nil) ------ 事务被放弃
50 # 最终 GET stock = 50,DECRBY 没执行
🔴 结论:EXEC 返回空 = 监视期间 key 被别人动过,你的"读-改-写"要重试。这就是 Redis 版的乐观锁。
五、发布订阅:PUBLISH / SUBSCRIBE
就是个"广播":一个频道,订阅了的人都能收到消息。
终端 A 订阅:
bash
redis-cli SUBSCRIBE news
text
subscribe
news
1
终端 B 发布:
bash
redis-cli PUBLISH news "hello-redis"
redis-cli PUBLISH news "second message"
text
1
1
终端 A 立刻收到:
text
message
news
hello-redis
message
news
second message
PUBLISH 返回 1 表示这条消息发给了 1 个订阅者。
⚠️ Pub/Sub 不是消息队列 :消息发出去就完了,不持久化。订阅者中途断线、或者发布时没在线,这条消息就永久丢了,收不到补发。要可靠投递用 List(做简单队列)或专门的 MQ(Kafka/RocketMQ),Redis Stream 才是它家的正经消息流方案(后面篇章讲)。
六、可视化:RedisInsight
命令行看久了眼花,官方有个免费可视化工具 RedisInsight,一眼看清 key、内存、命令曲线:
bash
docker run -d --name redisinsight -p 8001:8001 redis/redisinsight:latest
浏览器打开 http://localhost:8001,添加连接填 host=宿主机IP/容器名, port=6379, 密码(如有),就能图形化浏览 key、看内存占用、慢查询。本地调试用它比纯命令行舒服得多。
七、一次跑通:完整实操脚本
把本篇串起来,你可以照这个顺序在容器里过一遍:
bash
# 起容器
docker run -d --name redis7 -p 6379:6379 redis:7
docker exec -it redis7 redis-cli
# 进去后依次敲
PING # PONG
SET session:1 "user=alice" # OK
EXPIRE session:1 60 # 1
TTL session:1 # 60
TYPE session:1 # string
SCAN 0 MATCH "*" COUNT 10 # 增量遍历
MULTI
SET a 1
INCR counter
EXEC # 事务执行
# 另开一个终端:
# redis-cli SUBSCRIBE news
# 本终端:PUBLISH news "hello" # 发布
CONFIG GET maxmemory # 看配置
能一路敲通、输出和本文对得上,01 就算过关了。
总结:你真正需要记住的 10 件事
- 学习用 Docker 起 Redis:
docker run -d --name redis7 -p 6379:6379 redis:7,进去docker exec -it redis7 redis-cli。 - 连不上先
PING(PONG)、docker logs、INFO server看版本端口。 - 生产必加密码
--requirepass,客户端用REDISCLI_AUTH环境变量别用-a(密码进进程列表)。 - 中文显示成
\x..是没加--raw,交互时带上就好。 - 配置三种改法:配置文件启动 / 命令行参数 /
CONFIG SET;运行时改了要CONFIG REWRITE才持久化。 KEYS *生产禁用(阻塞),遍历用SCAN游标;FLUSHALL/FLUSHDB高危。TTL三态:>0剩余、-1永久、-2不存在。- 多库
SELECT 0~15,Cluster 只许 db0,别拿它做隔离。 - Redis 事务 = MULTI 入队 + EXEC 一次性执行,运行期错误不回滚 ;
WATCH是乐观锁,key 被改则 EXEC 放弃。 - Pub/Sub 消息不持久化、断线即丢,不是可靠消息队列。
验证清单
- 能用 Docker 起一个 Redis 7 容器,并
PING出PONG - 能起一个带密码的实例,并用
REDISCLI_AUTH免警告连上 - 会用
INFO server说出当前 redis 版本和端口 - 会用
CONFIG GET/SET在线查看并修改maxmemory - 能完成 SET → EXPIRE → TTL → PERSIST 全流程,并说清
-1/-2的区别 - 知道为什么生产不能用
KEYS *,会用SCAN遍历 - 能复现"事务里运行期错误不回滚"(SET 成功、INCR 失败但 SET 不撤销)
- 能开两个终端演示一次 Pub/Sub,并说清它为什么不是 MQ
- 能启动 RedisInsight 并连上自己的容器
参考资源
- Redis 官方命令文档(按字母索引,每条命令权威出处)redis.io/commands/
- Redis 官方配置手册 redis.conf 说明 redis.io/docs/latest...
- 事务(Transactions)官方说明 redis.io/docs/latest...
- 发布订阅(Pub/Sub)官方说明 redis.io/docs/latest...
- Docker 官方 redis 镜像 hub.docker.com/_/redis
- RedisInsight 可视化工具 redis.io/insight/
下一篇《【上手】五大数据类型命令逐条实操》:String / List / Hash / Set / ZSet 每条命令配语法→实例→输出→易错点,并用五个真实业务场景(库存扣减、消息队列、用户对象、共同关注、排行榜)把它们串起来跑一遍。