如何将 redis 数据库从一台服务器移动到另一台服务器?

Posted

技术标签:

【中文标题】如何将 redis 数据库从一台服务器移动到另一台服务器?【英文标题】:How do I move a redis database from one server to another? 【发布时间】:2011-08-25 16:24:34 【问题描述】:

我目前有一个在云实例上运行的实时 redis 服务器,我想将此 redis 服务器迁移到一个新的云实例并将该实例用作我的新 redis 服务器。如果是 mysql,我会从旧服务器导出数据库并将其导入新服务器。我应该如何用redis做到这一点?

P.S.:我不打算设置复制。我想将redis服务器完全迁移到一个新的实例上。

【问题讨论】:

多年后......在处理了各种与redis相关的事情之后,我建议使用Tom Clarkson's approach设置一个slave实例,让它与master同步,然后将slave提升为master。与我接受的答案相比,这将导致更短的停机时间,特别是如果您正在处理几 GB 的 redis 数据。如果你可以在这个组合中加入一个 redis 哨兵,你可以进行几乎零停机时间的迁移。 我有一个远程 Redis 服务器,并且想将其数据复制到我本地运行的 Redis 服务器...使用 dump.rdb 可能会很棘手,因为我必须通过网络移动该数据.. 【参考方案1】:

也可以使用 SLAVEOF 命令迁移数据:

SLAVEOF old_instance_name old_instance_port

检查您是否收到带有KEYS * 的密钥。您也可以通过任何其他方式测试新实例,完成后只需将复制:

SLAVEOF NO ONE

由于建议使用 Redis 5.0 使用 REPLICAOF,因为 SLAVEOF 已弃用 - see manual

【讨论】:

这是最无痛的方法! 从 Redis 5.0 开始,SLAVEOF 命令被替换为 REPLICAOF @ThomasLecavelier 感谢您的提醒,我已经更新了答案。根据手册,它仍然有效,但不鼓励,所以我相应地更新了它【参考方案2】:

零停机迁移的关键要素是:

复制 (http://redis.io/commands/SLAVEOF) 可以在应用程序切换期间写入从站 (CONFIG SET slave-read-only no)

简而言之:

    将目标 redis(空)设置为源 redis 的从属(使用您的数据) 等待复制完成 允许写入目标 redis(当前是从属) 将您的应用切换到目标 redis 等待从主机到从机的完成数据流 将目标 redis 从 master 转为 slave

此外,redis 还具有允许在分离目标后立即禁用源 redis 以接受写入的选项:

min-slaves-to-write min-slaves-max-lag

本主题涵盖

http://redis.io/topics/admin#upgrading-or-restarting-a-redis-instance-without-downtime

RedisLabs 团队 https://redislabs.com/blog/real-time-synchronization-tool-for-redis-migration 非常好的解释(使用 web.archive.org)

甚至他们的交互式迁移工具:https://github.com/RedisLabs/redis-migrate

【讨论】:

【参考方案3】:

通过从命令行运行BGSAVESAVE 将数据库的快照保存到dump.rdb。这将在与您的 redis 服务器相同的文件夹中创建一个名为 dump.rdb 的文件。查看所有服务器列表commands。

将此 dump.rdb 复制到您要迁移到的其他 redis 服务器。当 redis 启动时,它会寻找这个文件来初始化数据库。

【讨论】:

这让我猜测了几件事:SAVE 命令将其转储放在哪里? Redis 在哪里寻找“dump.rdb”文件来加载启动?我的 redis 配置将 dbfilename 设置为 /var/db/redis/redis_state.rdb ...这是我用来代替“dump.rdb”的文件名吗? 另外请注意,您不能在服务器运行时进行此交换,因为在正在运行的服务器上调用 SHUTDOWN 会将其内存内容保存到其转储文件中,从而覆盖您刚刚放置在那里的副本。首先关闭服务器。然后覆盖转储文件。然后重新启动服务器。 如果使用 AOF 日志记录(在 redis.conf 中,appendonly = yes),请在启动 Redis 服务器之前将其设置为no——否则将不会加载新数据集。数据集加载到内存后,在内存 (config set appendonly yes) 和配置文件中重新打开它。 在 Ubuntu 上,Redis conf 文件存储在/etc/redis/redis.conf,您可以通过它搜索您的.rdb 文件在哪里:cat /etc/redis/redis.conf | grep "rdb"。就我而言,它是/var/lib/redis redis-cli config get dir 将为您提供存储.rdb 的目录。【参考方案4】:

我发现导出/备份 Redis 数据(创建转储文件)的简单方法是通过带有 slaveof 标志的命令行启动服务器并创建活动副本,如下所示(假设源 Redis 在端口 6379 上是 1.2.3.4) :

/usr/bin/redis-server --port 6399 --dbfilename backup_of_master.rdb --slaveof 1.2.3.4 6379

【讨论】:

我有一个在我可以访问的 Linux 机器上运行的 redis。我的 Windows 机器上有一个 redis。这种组合可以复制数据吗? 如果两者版本相同,我相信你可以 是的,我还需要检查版本。但据我所知,Windows 发行版不高于 3.0【参考方案5】:

首先,在服务器 A 上创建一个转储。

A$ redis-cli
127.0.0.1:6379> CONFIG GET dir
1) "dir"
2) "/var/lib/redis/"
127.0.0.1:6379> SAVE
OK

这确保dump.rdb 是完全最新的,并向我们显示它的存储位置(在本例中为/var/lib/redis/dump.rdb)。 dump.rdb 也会定期自动写入磁盘。

接下来,将其复制到服务器 B:

A$ scp /var/lib/redis/dump.rdb myuser@B:/tmp/dump.rdb

停止B上的Redis服务器,复制dump.rdb(保证权限和之前一样),然后启动。

B$ sudo service redis-server stop
B$ sudo cp /tmp/dump.rdb /var/lib/redis/dump.rdb
B$ sudo chown redis: /var/lib/redis/dump.rdb
B$ sudo service redis-server start

B 上的 Redis 版本必须大于或等于 A 的版本,否则你可以打compatibility issues。

【讨论】:

比接受的答案好得多,包含所有细节。 这显示导入到 redis 是通过将转储放入 redis 文件夹来完成的,从而为我节省了很多时间 在 Mac 上,redis 备份存储在 /usr/local/var/db/redis/ @DonovanThomson 谢谢。 (我使用 homebrew 在 mac 上安装 redis)...查找路径的更通用方法是使用 redis 命令CONFIG GET dir,它返回"/usr/local/var/db/redis" 那么在这个过程中对 A 的写操作是怎么做的呢?【参考方案6】:

redis-dump 终于为我工作了。它的文档提供了一个如何转储 Redis 数据库并将数据插入另一个数据库的示例。

【讨论】:

这个包没有维护,不起作用【参考方案7】:

我刚刚向 npm 和 github 发布了一个命令行界面实用程序,它允许您将与给定模式(甚至 *)匹配的键从一个 Redis 数据库复制到另一个。

您可以在此处找到该实用程序:

https://www.npmjs.com/package/redis-utils-cli

【讨论】:

【参考方案8】:

我也想做同样的事情:将一个数据库从一个独立的 redis 实例迁移到另一个 redis 实例(redis sentinel)。

由于数据不是关键(会话数据),我会尝试https://github.com/yaauie/redis-copy。

【讨论】:

【参考方案9】:

在导入redis数据时检查dump.rdb必须放在哪里,

启动客户端

$redis-cli

然后

redis 127.0.0.1:6379> CONFIG GET *
 1) "dir"
 2) "/Users/Admin"

这里 /Users/Admin 是从服务器读取的 dump.rdb 的位置,因此这是必须替换的文件。

【讨论】:

【参考方案10】:

现在您还可以使用 MIGRATE,自 2.6 起可用。

我不得不使用它,因为我只想将数据移动到一个数据库中,而不是全部。这两个 Redis 实例位于两台不同的机器上。

如果无法从 Redis-1 直接连接到 Redis-2,请使用 ssh 端口绑定:

 ssh user@redis-2.foo.com -L 1234:127.0.0.1:6379

使用 KEYS 循环所有键并 MIGRATE 每个键的小脚本。这是 Perl,但希望你能明白:

 foreach ( $redis_from->keys('*') ) 

    $redis_from->migrate(
        $destinationhost,    # localhost in my example
        $destinationport,    # 1234
        $_,                    # The key
        $destinationdb,
        $destinationtimeout 
    );
 

请参阅http://redis.io/commands/migrate 了解更多信息。

【讨论】:

你要迁移到的远程redis有密码吗?【参考方案11】:

你也可以使用rdd

它可以转储和恢复正在运行的 redis 服务器并允许过滤/匹配/重命名转储键

【讨论】:

【参考方案12】:

如果您有服务器之间的连接,最好设置复制(与 SQL 不同,这很简单),将新实例作为从节点 - 然后您可以使用单个命令将新节点切换为主节点并执行零停机时间。

【讨论】:

我确实有连接。所以我可以在新服务器中使用slaveof配置,并将其设置为旧服务器的IP地址。但是我怎么知道主从之间的数据传输何时完成呢?之后,如何将slave提升为master? 我认为 INFO 命令会告诉你它什么时候准备好。但是,这并不重要 - 因为它是复制而不是一次性副本,所以在关闭旧节点之前,您可以将两个节点保留在原位。 SLAVEOF NONE 是将新节点提升为主节点的命令。 听起来是个不错的解决方案——如果有一些命令示例就好了!

以上是关于如何将 redis 数据库从一台服务器移动到另一台服务器?的主要内容,如果未能解决你的问题,请参考以下文章

如何将 Jenkins 从一台 PC 移动到另一台 PC

如何使用 ASP.NET 将文件从一台机器移动到另一台机器?

如何将弹性数据从一台服务器传输到另一台服务器

将所有内容从一台服务器移动到另一台服务器

如何将lvm卷移动到另一台服务器中

如何将大型 MySQL 数据库从一台服务器迁移到另一台服务器?