首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Cassandra DB中的日期插入:重要的1小时移位问题

Cassandra DB中的日期插入:重要的1小时移位问题
EN

Stack Overflow用户
提问于 2014-04-15 09:49:57
回答 2查看 1.5K关注 0票数 0

我对这个问题有点绝望。我不知道该怎么面对它。

下面是一个更简单的处理这个问题的方法:

如果插入cql查询是:

“开始批处理,使用一致性一插入到my_table(id,'2014-04-11 8:00‘,.,'2014-04-15 10:00:00')值('2036548',3.15,...,4.11)批处理”

...and我的数据请求cql查询是:

“从my_table where id=2036548中选择头100000 '2014-04-01 0:00:00‘.’2014-04-16 0:00:00‘”

...why将其从卡桑德拉拉出时,插入日期2014-04-15 10__:00:00是否更改为2014-04-15 11__:00:00?

vb.net中的日期拖放代码是:

代码语言:javascript
复制
Public Shared Function getCassandraDate(ByVal value As Byte()) As Date
    Dim buffer As Byte() = New Byte(value.Length - 1) {}
    value.CopyTo(buffer, 0)
    Array.Reverse(buffer)
    Dim ticks As Long = BitConverter.ToInt64(buffer, 0)
    Dim dateTime As New System.DateTime(1970, 1, 1, 0, 0, 0, _
         0)

    dateTime = dateTime.AddMilliseconds(ticks)
    Return dateTime.ToLocalTime
End Function

PHP中的...same:

代码语言:javascript
复制
date_default_timezone_set("Europe/Paris");
$time = $this->unpackDate($packed_time);
$str_time = date('Y-m-d H:i:s',$time); //TODO : to local time

private function unpackDate($data, $is_name=null)
{
    $arr = unpack('N2', $data);

    // If we are on a 32bit architecture we have to explicitly deal with
    // 64-bit twos-complement arithmetic since PHP wants to treat all ints
    // as signed and any int over 2^31 - 1 as a float
    if (PHP_INT_SIZE == 4) {

        $hi = $arr[1];
        $lo = $arr[2];
        $isNeg = $hi  < 0;

        // Check for a negative
        if ($isNeg) {
            $hi = ~$hi & (int)0xffffffff;
            $lo = ~$lo & (int)0xffffffff;

            if ($lo == (int)0xffffffff) {
                $hi++;
                $lo = 0;
            } else {
                $lo++;
            }
        }

        // Force 32bit words in excess of 2G to pe positive - we deal wigh sign
        // explicitly below

        if ($hi & (int)0x80000000) {
            $hi &= (int)0x7fffffff;
            $hi += 0x80000000;
        }

        if ($lo & (int)0x80000000) {
            $lo &= (int)0x7fffffff;
            $lo += 0x80000000;
        }

        $value = $hi * 4294967296 + $lo;

        if ($isNeg)
            $value = 0 - $value;

    } else {
        // Upcast negatives in LSB bit
        if ($arr[2] & 0x80000000)
            $arr[2] = $arr[2] & 0xffffffff;

        // Check for a negative
        if ($arr[1] & 0x80000000) {
            $arr[1] = $arr[1] & 0xffffffff;
            $arr[1] = $arr[1] ^ 0xffffffff;
            $arr[2] = $arr[2] ^ 0xffffffff;
            $value = 0 - $arr[1]*4294967296 - $arr[2] - 1;
        } else {
            $value = $arr[1]*4294967296 + $arr[2];
        }
    }
    return $value / 1e3;
}

详细信息

处理链:

(1)。通过.NET插入卡桑德拉

(2)。卡桑德拉数据存储

(3)。从PHP或.NET中提取数据

问题:

就今天而言,第(1)步的日期为2014-04-15 10__:00:00,第(3)步为2014-04-15 11__:00:00。

详细信息:

(关于此链中的日期格式)

(1)。当地时间.NET (时区:“欧洲/巴黎”)。正在执行的插入cql:"BEGIN BATCH USING CONSISTENCY ONE insert into my_table(id,'2014-04-11 8:00:00',...,'2014-04-15 10:00:00') values ('2036548',3.15,...,4.11) APPLY BATCH"

(2)。???我不知道卡桑德拉在这里做什么。???

(3)。获取数据的cql查询示例:"Select FIRST 100000 '2014-04-01 0:00:00'..'2014-04-16 0:00:00' from my_table where id=2036548"。In php:date_default_timezone_set("Europe/Paris"); $str_time = date('Y-m-d H:i:s',$time);。在.NET:dateTime.ToLocalTime中。

附加信息:

我认为在几个星期前夏令时间改变之前,它运行得很好。但我不能肯定。

如果在第(1)步中,如果我在插入日期之前将日期更改为de date,那么2014-04-15 10__:00:00将变成2014-04-15 08__:00:00,输出将是2014-04-15 09__:00:00,这仍然不正确。

我高度怀疑这里的诀窍是在步骤(1)和(2)之间,也就是说,我无法理解Cassandra如何对待约会。

Edit1:

@Ananth的问题:

卡桑德拉和客户端都在同一个数据中心运行?

这是很复杂的:

  • 在.NET中插入server1,这是一个不同于服务器的服务器-cassandra(数据中心).
  • 运行在服务器上的PHP (以获取数据)--cassandra。
  • .NET (提取数据)在server1上运行,而不是在服务器上运行-cassandra。
  • PHP和.NET使用相同的结果。

你能在这里发布你的模式吗?

就是这里

代码语言:javascript
复制
CREATE TABLE tsmeasures (
  id int PRIMARY KEY
) WITH
  comment='' AND
  comparator=timestamp AND
  read_repair_chance=0.100000 AND
  gc_grace_seconds=0 AND
  default_validation=double AND
  min_compaction_threshold=4 AND
  max_compaction_threshold=32 AND
  replicate_on_write='true' AND
  compaction_strategy_class='SizeTieredCompactionStrategy' AND
  compression_parameters:sstable_compression='SnappyCompressor';

Edit2:

经过一步一步的测试,结果如下:

  • 实际日期: 2014-04-15 17:00(当地时间)
  • cql文本:“2014-04-15:00:00”( UTC,通过.NET完成)
  • PHP解压缩此日期的=> $ticks = 1397577600 (*)解压缩是用前面显示的代码完成的

刻度转换(通过http://www.epochconverter.com/ )

  • GMT: Tue,
  • 2014年4月15日16:00格林尼治时间: 4/ 15 /2014 6:00 GMT+2

这些结果对我来说毫无意义..。

更多详细信息:

cql插入:

“开始批处理使用一致性一插入到TS量值(id,'2014-04-11 15:00:00',.,'2014-04- 15 :00:00')值('2036548',0,...,4.85)批处理”

cql提取:

“(2036548,2036479,20364 174,650877)”从“措施”(2036548,2036479,20364 174,650877)中选择“2014-04-10 16:00:00”

因此,“2014-04-15:00:00”包含在提取范围内,我可以识别它,因为它是最高值。

我会继续挖掘..。

EN

回答 2

Stack Overflow用户

发布于 2014-04-15 12:46:43

这似乎是时区问题。在存储时标或检索时间戳时,您似乎都没有指定时区。根据文档,卡桑德拉应用协调器节点的时区,如果客户端没有提供时区,则处理写入请求。如果时间戳在写入和读取它们之间发生了变化,这可能意味着您的Cassandra节点没有为与客户端相同的时区进行配置。

票数 1
EN

Stack Overflow用户

发布于 2014-04-15 12:19:18

编辑前

你的客户和卡桑德拉之间有时钟同步问题吗?我严格建议在您的客户端和cassandra安装之间运行NTP。

邮政编辑

代码语言:javascript
复制
CREATE TABLE tsmeasures (
  id int PRIMARY KEY
) WITH
  comment='' AND
  comparator=timestamp AND
  read_repair_chance=0.100000 AND
  gc_grace_seconds=0 AND
  default_validation=double AND
  min_compaction_threshold=4 AND
  max_compaction_threshold=32 AND
  replicate_on_write='true' AND
  compaction_strategy_class='SizeTieredCompactionStrategy' AND
  compression_parameters:sstable_compression='SnappyCompressor';

从你所给予的情况来看,你似乎是在试图获得插入时间。

您的问题可能是由于不同时钟周期运行的客户端与cassandra有关。Cassandra只是为每一次写入放置一个unix时间戳。

所以,从我所看到的来看,这里发生了什么。

您可以使用时间戳X(datastax驱动程序设置此插入时间戳)从客户端写入。卡桑德拉用X写。

您使用时间戳Y. Cassandra尝试使用时间戳Y进行读取(因此,按照您的解释,PHP客户端位于不同的位置)。

这两个a必然会有所不同。

解决方案1

尝试在整个设置之间设置一个全局NTP,以便客户端时钟周期与cassandra同步。

解决方案2

插入名为时间戳的列,该列是用户驱动的,并根据该列进行范围扫描。

解决方案3

在DML操作中设置插入时间。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/23080188

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档