欢迎投稿

今日深度:

深入浅出cassandra 3 例子背后的模型,深入浅出c

深入浅出cassandra 3 例子背后的模型,深入浅出cassandra


/**    * author: ahuaxuan(张荣华)    * date 2010-2-25    */


深入浅出cassandra 3 例子背后的模型

在上一篇文章中,ahuaxuan和大家一起写了一个cassandra的insert和get的例子。从这个例子中我们也得知了操作cassandra的最基本流程, 除此之外我们也初步了解了cassandra中的数据模型,但是只是肤浅的了解了一下,那么我们接着上一篇的话题,继续阐述这个问题。


在我们操作数据的代码中:

1.<span style="font-size: small;"> String table = "Keyspace1";  
2.        String row = "row007";  
3.        ColumnPath col = new ColumnPath("Standard1", null, "ahuaxuan".getBytes());  
4.  
5.  
6.        cassandraClient.insert(table, row, col, " first cassandra sample of ahuaxuan".getBytes(), 1, 1);  
7.</span> 

我们遇到了三个概念,第一个是keyspace, 第二个是ColumnFamily, 第三个是Row。 前面两个属性,我们将可以看成是数据库和表的关系,那么第三个属性呢? 在cassandra文中写道:ColumnFamily的数据是排序后存放在单独的文件中的,row就是排序因子,那个row其实就可以是我们的key, 事实上在cassandra的源代码中row就是key,比如我们看这段源代码:


看上面这个方法的第二个参数,其实就是key.


所以看到这里,我们基本上确定了cassandra中的存储模型,为: Keyspace1--row007--Standard1,可以确定某个keyspace下的某个key的某个ColumnFamily, 然后再创建某个Column, 包括Column Name和Column Value, 还包含一个timestamp.


这里有一点需要注意, 那就是相同的key中,且在相同的ColumnFamily中,column的名字必须唯一,如果重复,那么可能会产生覆盖。我们来看一段代码
1.public static void main(String[] args) throws TException, TimedOutException, InvalidRequestException, UnavailableException, NotFoundException {  
2.        init();  
3.        String table = "Keyspace1";  
4.        String row = "row007";  
5.        ColumnPath col = new ColumnPath("Standard1", null, "ahuaxuan".getBytes());  
6.        ColumnPath col2 = new ColumnPath("Standard2", null, "ahuaxuan".getBytes());  
7.  
8.  
9.        cassandraClient.insert(table, row, col, " first cassandra sample of ahuaxuan".getBytes(), 3, 1);  
10.        cassandraClient.insert(table, row, col2, " second cassandra sample of ahuaxuan ".getBytes(), 4, 1);  
11.        Column column = cassandraClient.get(table, row, col, 1).column;  
12.        Column column2 = cassandraClient.get(table, row, col2, 1).column;  
13.  
14.  
15.        System.out.println("read row " + row);  
16.        System.out.println("column name: " + new String(column.name));  
17.        System.out.println("column value" + ": " + new String(column.value));  
18.        System.out.println("column timestamp" + ":" + (column.timestamp));  
19.  
20.  
21.        System.out.println("\r\nread row " + row);  
22.        System.out.println("column name: " + new String(column2.name));  
23.        System.out.println("column value" + ": " + new String(column2.value));  
24.        System.out.println("column timestamp" + ": " + (column2.timestamp));  
25.    }   



第一次放到Keyspace1--row007--Standard1中,列名为ahuaxuan,列值为first cassandra sample of ahuaxuan,timestamp为3, 接着我更新Keyspace1--row007--Standard1中,列名为ahuaxuan,列值为second cassandra sample of ahuaxuan,timestamp为2 结果更新不成功,但是如果我把timestamp改成4,更新可以成功。


而且从上面这段例子中,我们还可以看出,如果keyspace---row---columnfamily中有一个不一样,那么就不会产生覆盖问题。


所以我们说这里可能产生覆盖,而是否覆盖时由代码中的那个timestamp决定的,如果说当前cassandra中的那条数据的timestamp大于要插入的数据,那么则不会产生覆盖,反之,则产生覆盖 但是本质上未必是覆盖,因为在bigtable的论文中写的很清楚,以前的版本将会被保留,也就是说老的数据还是会存在,当然,我们不能保持所有的老版本数据,那么就一定有一个阈值来 控制具体要保持多少个老版本。其论文写道:


我们对每一个列族支持两个设定,以便于Bigtable对表项的版本自动进行垃圾清除。用户可以指明只保留表项的最后n个版本,或者只保留足够新的版本(比如,只保留最近7天的内容)。


就这样写一个毫无实际意义的例子会让人感觉到比较空洞,所以这里ahuaxuan忍不住引用bigtable论文中的一个例子来描述以下这个模型适用的场景.



如上图所示

 这 是一个存储Web网页的范例列表片断。行名是一个反向URL{即com.cnn.www}。contents列族{原文用 family,译为族,详见列族} 存放网页内容,anchor列族存放引用该网页的锚链接文本。CNN的主页被Sports Illustrater{即所谓SI,CNN的王牌体育节目}和MY-look的主页引用,因此该行包含了名叫“anchor:cnnsi.com”和 “anchhor:my.look.ca”的列。每个锚链接只有一个版本{由时间戳标识,如t9,t8};而contents列则有三个版本,分别由时间 戳t3,t5,和t6标识。

当然可以使用这种数据模型的场景很多,很多时候我们可以把它当作key-value系统来使用,由于有版本号的特征,所以它也能解决一部分数据一致性的问题(这个问题非常重要,我们会在后面的文章中详细阐述).


那么接下来的问题是:cassandra是如何实现这个模型的呢,请您接着往下看


to be continued

www.htsjk.Com true http://www.htsjk.com/cassandra/11277.html NewsArticle 深入浅出cassandra 3 例子背后的模型,深入浅出cassandra /**    * author: ahuaxuan(张荣华)    * date 2010-2-25    */ 深入浅出cassandra 3 例子背后的模型 在上一篇文章中,ahuaxuan和大家一起写了一个...
评论暂时关闭