【问题标题】:cassandra table looks empty in cqlsh, but nodetool cfstats thinks otherwisecassandra 表在 cqlsh 中看起来是空的,但 nodetool cfstats 不这么认为
【发布时间】:2016-01-15 19:40:30
【问题描述】:

使用 nodetool cfstats 我可以看到一个特定的表 (table1) 正在使用 59mb 并且有 545597 个键。另一个相关的表(table2)使用 568mb 并且有 2,506,141 个键。

使用 cqlsh,当我执行 select count( * ) from table1 时,它会暂停大约 7 秒,然后返回计数 0。但是,如果我执行 select count( * ) from table2,它会暂停更长的时间,然后返回 2,481,669 的计数。

我也试过select * from table1select * from table2。第一个需要 7 秒,然后什么也不返回。第二个立即开始对结果进行分页。

我很清楚这些都是昂贵的操作,但是这是在一个只有这个 Cassandra 实例的单个开发服务器上。它是 1 的集群,不用于生产。我只是想弄清楚为什么 table1 中的值是不可见的。

table1 是否可能实际上没有值?这不应该是不可能的,因为我刚刚跑了一份工作来为它添加一堆值。我还运行了“nodetool compact”,所以应该已经消除了所有的墓碑,cfstats 应该显示实际存在的内容,对吧?这是我运行nodetool compact 后table1 的cfstats:

            SSTable count: 1
            Space used (live): 59424392
            Space used (total): 59424392
            Space used by snapshots (total): 73951087
            Off heap memory used (total): 806762
            SSTable Compression Ratio: 0.28514022725059224
            Number of keys (estimate): 545597
            Memtable cell count: 393204
            Memtable data size: 17877650
            Memtable off heap memory used: 0
            Memtable switch count: 3
            Local read count: 5
            Local read latency: 0.252 ms
            Local write count: 545804
            Local write latency: 0.013 ms
            Pending flushes: 0
            Bloom filter false positives: 0
            Bloom filter false ratio: 0.00000
            Bloom filter space used: 611792
            Bloom filter off heap memory used: 611784
            Index summary off heap memory used: 180202
            Compression metadata off heap memory used: 14776
            Compacted partition minimum bytes: 216
            Compacted partition maximum bytes: 310
            Compacted partition mean bytes: 264
            Average live cells per slice (last five minutes): 1.0
            Maximum live cells per slice (last five minutes): 1
            Average tombstones per slice (last five minutes): 6.0
            Maximum tombstones per slice (last five minutes): 7

如果有帮助,我在 linux 服务器上使用 apache cassandra 2.2.0。

【问题讨论】:

  • 我发现这些值实际上已经过期了。异步插入失败并且错误消息没有传播出去,因为期货被忽略了。 (愚蠢的错误)。我假设所有记录都过期了(它们都有一个 ttl)。但是,我仍然想了解这些日志的含义,以便将来能够识别这一点。这些日志如何以任何方式指示一个空表?

标签: cassandra


【解决方案1】:

Cassandra 将所有数据保存在文件 (sstables) 中。为了速度,在文件末尾写入附加数据(索引当然工作方式不同,但它们没有描述这些功能如何......)

数据的删除(或在您的情况下过期)不会从文件中删除数据,否则这将意味着大量的大移动和大量的 I/O。因此,他们不只是将条目标记为“死亡”(因此它们被称为墓碑)。

有时,压缩系统会出现(假设您没有针对该表关闭它)并压缩表。这意味着它从文件的开头读取并将活动条目移到死条目上。或多或少,假设 B 在某个时间点被删除(从左到右的列代表不同的时间点),类似这样的事情:

Creation    Deletion       Compaction

A           A              A
B           B-tombstone    C
C           C

如果你的表有太多的墓碑,压缩可能会失败(我不明白为什么它会失败,但这就是我读到的)。压缩失败的表被标记为“永远不要压缩”,如果你问我,这是一个大问题。一个有 50 万个键的表很可能会失败。

虽然表处于“删除”状态(包括墓碑),但越过墓碑的 SELECT 仍会创建一个 TombStone 内存对象(不要问我为什么,我不知道,它看起来像否则,Cassandra 将无法正常工作...)因此,需要 7 秒来读取所有墓碑并为每个墓碑创建 Java 对象。

CQL 界面包含一个TRACE 功能,可用于查看表中的墓碑数量。它会打印出一堆你想知道的东西。

TRACE ON;
SELECT COUNT( * ) FROM table1;

【讨论】:

    猜你喜欢
    • 2016-10-07
    • 2016-04-07
    • 2017-04-21
    • 2014-01-16
    • 2015-03-13
    • 2012-05-22
    • 2016-10-26
    • 2015-01-26
    • 2012-05-06
    相关资源
    最近更新 更多