HBase系统架构与存储格式
HBase是Google Bigtable的开源实现,类似Google Bigtable利用GFS作为其文件存储系统,HBase利用Hadoop HDFS作为其文件存储系统;Google运行MapReduce来处理Bigtable中的海量数据,HBase同样利用Hadoop MapReduce来处理HBase中的海量数据;Google Bigtable利用 Chubby作为协同服务,HBase利用Zookeeper作为对应。
HBase是Google Bigtable的开源实现,类似Google Bigtable利用GFS作为其文件存储系统,HBase利用Hadoop HDFS作为其文件存储系统;Google运行MapReduce来处理Bigtable中的海量数据,HBase同样利用Hadoop MapReduce来处理HBase中的海量数据;Google Bigtable利用 Chubby作为协同服务,HBase利用Zookeeper作为对应。
获取内存淘汰配置策略
1 | 127.0.0.1:6379>config get maxmemory-policy |
Redis的延迟数据是无法从info信息中获取的。倘若想要查看延迟时间,可以用 Redis-cli工具加–latency参数运行,如:
1 | Redis-cli --latency -h 127.0.0.1 -p 6379 |
结果为查询ID、发生时间、运行时长和原命令 默认10毫秒,默认只保留最后的128条。单线程的模型下,一个请求占掉10毫秒是件大事情,注意设置和显示的单位为微秒,注意这个时间是不包含网络延迟的。
1 | 127.0.0.1:6379>slowlog get |
查看aof是否影响延迟,在info Stats中查看,数字代表有多少次fork延迟操作
1 | latest_fork_usec:1724##单位微妙 |
查看最近一次fork延迟耗时
1 | aof_delayed_fsync:0###被延迟的 fsync 调用数量 |
在运维过程中,整体断电后,集群重启后,master与slave节点分布可能会出现变化,为了保证集群master分布均匀,可使用命令主动切换master.
在需要提升为master的节点执行以下命令
1 | 127.0.0.1:6379>cluster failover |
可在redis.conf中配置
1 | cluster-migration-barrier 1 |
该参数指定slave最小数量为1,当前节点无法满足的话,会从别的节点漂移一个作为master的slave
1.新建不带namespace表
1 | create 'testTable','t1','t2' |
2.新建带namespace表
1 | create_namespace 'truman' |
1 | create_namespace 'truman:test','t1','t2' |
1 | create'reason:user_test','bs',{NUMREGIONS=>2,SPLITALGO=>'HexStringSplit'} |
1 | list |
1 | scan 'testTable' |
1 | put 'testTable','row1','t1:name','value1' |
1 | get 'testTable','row1' |
1 |
待完善
在运维过程中,会经常遇到维护的机器很多,更新软件版本比较繁杂,在此借鉴winscp与putty支持脚本的功能之上,使用window bat命令实现在window平台便捷部署linux上的应用。
此处利用winscp。updateLoadScript.txt 具体操作代码如下:
1 | option batch on |
此处主要,要提前用winscp连接到相应主机上,猜测要从缓存中取一些东西
此处利用 putty。 command.txt 具体命令如下:
1 | export JAVA_HOME=/opt/jdk1.8.0_45 |
1 | @echo off |
众所周知,jedis仅支持redis standalone mset,mget等批量操作,在最新的redis cluster中是不支持的,这个和redis cluster的设计有关,将不同的实例划分不同的槽。不同的key会落到不同的槽上,所在的实例也就不同,这就对jedis的批量操作提出问题,即无法同时支持多个实例上的批量操作。(理解可能不是很深入,希望有人看到可以指教一下)
在分布式存储产品中,哈希存储与顺序存储是两种重要的数据存储和分布方式,这两种方式不同也直接决定了批量获取数据的不同,所以这里需要对这两种数据的分布式方式进行简要说明:
分布方式 | 特点 | 典型产品 |
---|---|---|
哈希分布 | 1. 数据分散度高2.键值分布与业务无关3.无法顺序访问4.支持批量操作 | 一致性哈希memcache redisCluster其他缓存产品 |
顺序分布 | 1.数据分散度易倾斜2.键值分布与业务相关3.可以顺序访问4.支持批量操作 | BigTable Hbase |
将Mget操作(n个key)拆分为逐次执行N次get操作, 很明显这种操作时间复杂度较高,它的操作时间=n次网络时间+n次命令时间,网络次数是n,很显然这种方案不是最优的,但是足够简单。
将Mget操作(n个key),利用已知的hash函数算出key对应的节点,这样就可以得到一个这样的关系:Map<node, somekeys>,也就是每个节点对应的一些keys 。它的操作时间=node次网络时间+n次命令时间,网络次数是node的个数,很明显这种方案比第一种要好很多,但是如果节点数足够多,还是有一定的性能问题。
此方案是将方案(2)中的最后一步,改为多线程执行,网络次数虽然还是nodes.size(),但网络时间变为o(1),但是这种方案会增加编程的复杂度。它的操作时间=1次网络时间+n次命令时间
第二节提到过,由于hash函数会造成key随机分配到各个节点,那么有没有一种方法能够强制一些key到指定节点到指定的节点呢? redis提供了这样的功能,叫做hash-tag。什么意思呢?假如我们现在使用的是redis-cluster(10个redis节点组成),我们现在有1000个k-v,那么按照hash函数(crc16)规则,这1000个key会被打散到10个节点上,那么时间复杂度还是上述(1)~(3)
那么我们能不能像使用单机redis一样,一次IO将所有的key取出来呢?hash-tag提供了这样的功能,如果将上述的key改为如下,也就是用大括号括起来相同的内容,那么这些key就会到指定的一个节点上。
例如:
例如下图:它的操作时间=1次网络时间+n次命令时间
方案 | 优点 | 缺点 | 网络IO |
---|---|---|---|
串行mget | 1.编程简单2.少量keys,性能满足要求 | 大量keys请求延迟严重 | o(keys) |
串行IO | 1.编程简单2.少量节点,性能满足要求 | 大量node延迟严重 | o(nodes) |
并行IO | 1.利用并行特性2.延迟取决于最慢的节点 | 1.编程复杂2.超时定位较难 | o(max_slow(node)) |
hash tags | 性能最高 | 1.tag-key业务维护成本较高2.tag分布容易出现数据倾斜 | o(1) |
目前我们项目中采用第一种方式,使用多线程解决批量问题,减少带宽时延,提高效率,这种做法就如上面所说简单便捷(我们目前批量操作类型比较多),有效。但问题比较明显。批量操作数量不大即可满足。最近研究cachecloud发现搜狐他们采用第二点,先将key获取槽点,然后分node pipeline操作。这种做法相对比第一种做法较优。推荐第二种方法,后期对性能有要求的话,考虑修改成第二种方式。
附加cachecloud-client代码中mget追踪路径
类PipelineCluster======>mget======>类pipelineCommand=====>run=====>getPoolKeyMap====>getResult
[1]http://carlosfu.iteye.com/blog/2263813
[2]https://github.com/sohutv/cachecloud/wiki/5.%E8%AE%BE%E8%AE%A1%E6%96%87%E6%A1%A3
       Storm 是Twitter的一个开源框架。Storm一个分布式的、容错的实时计算系统。Twitter Storm集群表面上类似于Hadoop集群,Hadoop上运行的是MapReduce Jobs,而Storm运行topologies;但是其本身有很大的区别,最主要的区别在于,Hadoop MapReduce Job运行最终会完结,而Storm topologies处理数据进程理论上是永久存活的,除非你将其Kill掉。
Storm集群中包含两类节点:主控节点(Master Node)和工作节点(Work Node)。其分别对应的角色如下:
1 | 1.JDK1.8 |
详见略
1.解压
1 | tar xvf zookeeper-3.4.5-cdh5.6.0.tar.gz |
2.修改配置
添加修改vonf/zoo.cfg
1 | cp zoo_sample.cfg zoo.cfg |
修改zoo.cfg
1 | dataDir=/data/truman/zookeeper-3.4.5-cdh5.6.0/data |
在dataDir下新增myid文件,内容为相对应的server后面的数字
3.分发远程主机
1 | scp -r zookeeper-3.4.5-cdh5.6.0 root@lab30:/data/truman/ |
4.启动和停止
启动命令
1 | zkServer.sh start |
停止
1 | zkServer.sh stop |
在nimbus与supervisor节点上重复以下操作
1.修改配置
1 | storm.zookeeper.servers: |
1 | storm.local.dir: "/data/storm" |
1 | nimbus.host: "192.168.0.2" |
1 | supervisor.slots.ports: |
1 | ui.port: 8998 |
1 | nohup $STORM_HOME/bin/storm nimbus & |
#从节点,执行一下命令
1 | nohup $STORM_HOME/bin/storm supervisor & |
启动成功后,即可在192.168.0.2:8992 storm ui中查看服务
1.http://www.tianshouzhi.com/api/tutorials/storm/17
2.http://blog.csdn.net/xeseo/article/details/17678829
1.下载jkd( http://www.oracle.com/technetwork/java/javase/downloads/index.html)
对于32位的系统可以下载以下两个Linux x86版本(uname -a 查看系统版本)
264位系统下载Linux x64版本
2.安装jdk(这里以.tar.gz版本,32位系统为例)
安装方法参考http://docs.oracle.com/javase/7/docs/webnotes/install/linux/linux-jdk.html
选择要安装java的位置,如/usr/目录下,新建文件夹java(mkdir java)
将文件jdk-7u40-linux-i586.tar.gz移动到/usr/java
解压:tar -zxvf jdk-7u40-linux-i586.tar.gz
删除jdk-7u40-linux-i586.tar.gz(为了节省空间)
至此,jkd安装完毕,下面配置环境变量
3.打开
1 | /etc/profile(vim /etc/profile) |
在最后面添加如下内容:
1 | JAVA_HOME=/usr/java/jdk1.7.0_40 |
4.生效
1 | source /etc/profile |
5.验证是否安装成功:java -version
1 | hostname ****** |
在1之后,修改 /etc/sysconfig/network
本节参考:网址
1 | $ssh-keygen |
1 | $ ssh-copy-id user@host |
1 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ |
问题解决:
删除/root/.ssh/known_hosts:13行中的信息即可