2016-01-20 37 views
4

introduction course of Cassandra DataStax中,他们说Cassandra群集节点的所有时钟必须同步,以防止对“旧”数据进行READ查询。为什么Cassandra集群需要同步节点之间的时钟?

如果一个或多个节点都关闭他们不能得到更新,但只要他们回来了 - 他们将更新并没有问题......

那么,为什么卡桑德拉集群之间需要同步时钟节点?

+0

我的想法是,同步依赖于知道更改的时间。如果一个节点知道它在给定时间同步,那么另一个节点用较早的时间戳写入数据,第一个节点将不知道它需要重新同步该数据。然后使用该第一个节点的人将读取旧数据。我不确定为什么一个节点被关闭了。如果发生故障,没有人可以对其进行更改,以确保其他人需要同步。当它恢复时,它会知道它上次同步的时间,并根据它们的更改同步到其他时间。 – RosieC

回答

8

一般来说,让服务器时钟保持同步总是一个好主意,但节点之间需要时钟同步的主要原因是Cassandra使用一种名为'Last Write Wins'的概念来解决冲突并确定哪种突变代表最正确的最新数据状态。这在Why cassandra doesn't need vector clocks中有解释。

每当您在cassandra中“变更”(写入或删除)列时,协调器将处理您的请求分配一个时间戳。该时间戳记与单元格中的列值一起写入。

当读取请求发生时,cassandra会生成结果,查找您的查询条件的突变,并且当它看到表示同一列的多个单元格时,它将选择具有最近时间戳的单元格(读取路径比此更复杂但在这种情况下,您只需要知道这一点)。

当节点的时钟不同步时,情况开始变得有问题。正如我所提到的,处理您的请求的协调节点会分配时间戳。如果对同一列进行多重变异并分配了不同的协调员,则可以创建一些情况,即过去发生的写入被返回而不是最新的。

这里是描述基本方案:

假设我们有与节点A 2节点集群和B.让我们假设,其中A是在时间t10和B是在时间t5的初始状态。

  1. 用户执行DELETE C FROM tbl WHERE key=5。节点A协调请求并分配时间戳t10
  2. 第二次通过,用户执行​​。节点B协调请求并为其分配时间戳t6
  3. 用户执行查询SELECT C from tbl where key=5。由于步骤1中的DELETE具有更新的时间戳(t10 > t6),因此不会返回任何结果。

请注意,较新版本的datastax驱动程序将开始默认使用客户端时间戳让客户端应用程序为请求生成并分配时间戳,而不依赖于C *节点来分配它们。从3.0开始的datastax java-driver现在默认为客户端时间戳(请参阅'Client-side generation'的更多内容)。如果所有请求都来自同一个客户端,这非常好,但是如果您有多个应用程序写入cassandra,则您现在必须担心保持客户端时钟同步。

+0

很好的答案,谢谢! – Rada

+1

很好的解释。让我们考虑一下我在一个DC内的Amazon EC2中的集群中有4个节点。我已将Simple Snitch配置为SimpleSnitch。我没有使用任何客户端时间戳机制(通过假定服务器本身应该处理时间),并且我没有使用任何NTP服务,但默认情况下,所有4 EC2实例将具有相同的时间。这种情况会影响数据的一致性吗? –

+0

时钟已知会漂移,尤其是在EC2等虚拟化环境中(请参阅:http://unix.stackexchange.com/questions/29220/why-is-my-ec2-servers-time-off-by-10-seconds-每天)。因此,即使您的时钟现在同步,如果您不使用ntpd来同步时钟,也可能会遇到同样的问题。 –

相关问题