sunyangnj
作者sunyangnj·2013-03-31 16:30
技术经理·苏宁金融研究院

浅谈DB2高可用性的各种因素(微观较多,从本源出发)

字数 4720阅读 11303评论 12赞 3
   在之前的博客中,我曾经从宏观和非数据库角度介绍过DB2数据库的高可用技术。但是,DB2数据库本身的设计和操作对高可用影响更大。所以本文着重从DB2本身出发谈谈做好高可用应该注意的方面。所以上篇为宏观,本文为微观。

1.备份
  高可用第一个因素就是备份。拥有良好可行的备份计划,以及记录清楚的备份介质,是保障数据库高可用的第一道门户。虽然我们可能有HACMP,但是如果数据库文件损坏,或者数据库存储所在磁盘损坏,我们必须要依靠备份来恢复数据库。对于小型非全天候交易型数据库,比如几十GB,在运维窗口经常性的来个全备就很好了。对于小型24*7的交易型数据库,要在业务低谷的窗口来个在线全备份即可,对于大型24*7的交易型数据库,每周来一次在线全备,每天来一次增量备份或者增量迭代备份即可。对于数据仓库,一般来说因为数据量十分庞大都是无法备份的,但是我还是要推荐备份,因为这是终极灾难恢复手段。分析性数据库(也就是数据仓库),建议1个月来一次全备份即可,因为大多数都是月底来经营分析。分析型数据库如果有离线窗口,推荐离线备份。无论什么备份,最好采取压缩模式compress,这个能大大减少对存储设备的需求,强烈推荐。备份数据最好放置在和数据库存储不同的专门的磁盘上,最好能在同机房和同城异地机房中个备一个,增加灾难发生时数据可恢复的几率,尤其是核心系统,异地也要放置。备份的很多参数从9.5之后都可以自动选择,比如并行度,缓冲区等等,我们不需要再费劲脑筋去想。在时间critical的场景,我推荐对大型交易数据库和数据仓库使用多目标路径备份(比如多个磁盘),增加并行性。

2.日志
 从高可用性角度出发,归档日志的目录最好设置和数据库存储不一样的独立磁盘,但是大多数应用部署都会忽略这一点,直接就使用相同磁盘上的逻辑卷作为归档目录,这个特别危险。对于高敏感度的OLTP数据库,可以设置镜像日志目录(和活动日志目录处于不同的磁盘),为活动日志设置双保险。因为活动日志如果损坏,数据库就会宕机。但是镜像日志目录增加了写的时间,对数据库的DML操作有性能上的影响。活动日志目录原来是在SQL0000X下面的 LOGSTREAM下面,但是我还是推荐设置一个不同的磁盘(采用RAID10构建的LUN),减少数据库目录损坏对活动日志的影响。另外,DB2数据库有个特点,如果未使用activate db xxxx显式激活数据库,那么每次所有数据库连接断开,都会归档一个日志,很不必要,我们推荐使用activate db xxx来显式激活数据库,而不是使用connect to xxxx隐式激活。日志文件大小设置对于OLTP数据很重要,如果并发交易特别频繁,推荐不要设置的太小,比如1M,推荐设置为10M这样的数量级,这样减少初始化日志文件的时间。当首次激活数据库,和当主日志不够用,初始化副日志的时候,都要做初始化日志文件的工作。主文件数目不要设置的太大几十个即可,副日志文件数目可以设置的多一点(和主日志文件一起不能超过255),不要吝啬。很多初级的系统,日志的参数都设置的非常小,甚至不做改动,导致后期有很多问题。DB2 10.1开始,将日志文件数目的初始值增加到了几十个,而不是9.7的几个,减少了不设置日志文件数目的傻瓜系统的日志满的几率。对于交易型数据库,一定要设置为归档日志模式,而且不要设置为logretain,防止活动日志目录爆掉。从10.1开始,DB2还增加了归档日志压缩模式,对减少日志存储空间有很大作用,当然日志压缩有利有弊,压缩必然意味着解压缩,都要耗CPU和内存的。但是如果CPU针对压缩/解压缩有特别优化的除外。softmax最好不要设置的过高,防止崩溃恢复需要处理较多日志文件导致不可用,我个人推荐100(一个日志文件间隔)。

3.表空间
  表空间是DB2存储的第一责任人。我们知道表空间有很多操作的命令,比如创建、增加减少容器、增加减少容器大小等等。从DB2 10.1开始,我强烈推荐使用存储器组作为表空间存储的基本单位,而不是单个设备或者文件。表空间对于DBA来说,就是麻烦越少越好,最好不要DBA干涉或者可以提供更灵活的管理方式。所以,存储器组就是你的最好选择。当数据库为归档日志模式的时候,对表做copy no的导入,会导致表所在的表空间处于backup pending状态(可读不可更新),所以推荐使用copy yes的load方法,对于只读表可以采用nonrecoverable方式减少表停顿时间。对于经常性load或者恢复的表,建议和其他表所在的表空间区分开来,放置影响其他的表的可访问性。表空间的容器很重要,对于非自动存储管理的DMS,如果被意外修改了容器名称或者路径等等,就会导致表空间 offline,所以一定要登记表空间容器和表空间以及表的对应关系,对数据库所在文件系统保持高度安全性,防止误操作。当我们发现数据库起不来的时候,有的时候就是因为某个表空间容器损坏或者被删除更名,这时只能使用restart database drop pending tablespaces删除该表空间。表空间在归档模式恢复之后会进入前滚暂挂,这时需要前滚。当重定向恢复数据库到另外的机器或者实例中,需要对非默认以及非自动存储的表空间启动重定向操作,或者用DDL修改或者用set tablespace container来重新定义表空间的容器。

4.缓冲池和内存配置相关
  缓冲池是DB2数据库最重要的地方,对于业务模式比较稳定的数据库,不建议开启STMM(可能会导致数据库去获取较大的系统内存作为缓冲池,结果获取失败,导致数据库启动异常)。经常访问的表所在表空间分配一个大缓冲池,对索引所在表空间也分配一个大型缓冲池,同时对于临时表空间也分配一个缓冲池但是不用太大,将较少访问的表所在表空间和一个较小的缓冲池相关联。数据库缓冲池总体大小不要吝啬,现在系统多为单数据库系统,可以将内存的1/3分配给缓冲池,对于分析型数据库可以分配1/2的系统内存。SORTHEAP,PACKACGE CACHE,STMT CACHE也根据实际情况调整,默认的参数肯定不行,很多系统在建库的时候,都不考虑这些参数的修改,导致事务的响应时间很慢。一般关闭 sheapthres,而打开theapthres_share,配置为sortheap倍数。缓冲池太大起不来,可以设置一个注册变量 db2_override_bpf来设置一个较少的数量。对于OLAP连续读取的业务场景,设置缓冲池的块会有较大的系统提升。

5. 运维操作对可用性的影响
正如前面所说,数据库本身的设计对于高可用来说重要性远远超过HACMP,HADR等技术。表的可用性,一方面主要体现在各种操作后的状态。比如当装入执行后完整性暂挂,需要set integrity来检查约束摆脱暂挂状态,再比如正在装入的表处于只读访问,无法修改等。离线表重组导致表无法访问,需要断开连接,停止应用,在线重组使用inplace选项大大提高了表重组期间的可访问性,但是对I/O性能有一定影响,对于较大的表,离线重组导致较大的表空间需求,这对存储提出一些要求。runstats使用allow write access不限制对表完全访问,而allow read access则限制了对表的更新和写,同时runstats对系统性能有较大影响,尤其是表非常huge的时候。我们应该针对于最经常使用的表,最受高层关注的表使用runstats命令。同时,针对于应用的sql语句,对谓词所在列和索引进行更新runstats,这样就大大限制了我们runstats 对系统的影响。其实对于大部分其他的表,更不更新统计信息真的无所谓。坚决反对使用db2自带的自动更新统计信息选项,会造成不可控。虽然自主计算是个好事情,但是在很多操作上,我们还是更相信人的判断。当然对于runstats有很多选项,需要我们根据数据的特点以及我们的需要定制参数,总之不能盲目的全部列进行全部统计更新。更新统计信息,或者新建了索引,最好rebind程序包,改变访问计划。


6.锁对数据库可用性的影响
锁主要影响在于让系统响应变慢,设置locktimeout为非-1,防止锁超时,另外启用cur_commit数据库参数(需要增大日志文件大小和数量),这个参数等同于三个之前的参数。增大locklist,maxlock的设置,防止锁升级。尽量在长事务中频繁和及早commit。应用程序中 sql语句最好按相同顺序访问表资源,可以大大降低死锁。对IUD以及表DDL语句要尽早落实。尽量降低dlchktime时间,减少应用程序所等待时间。对于只读的访问,尽量明确使用with UR,对于读写访问默认为CS,已经可以了,但是能使用UR就使用UR。在表中使用合理的索引,也可以避免表扫描,可以大大降低锁发生的概率。


7.逻辑设计对可用性的影响
尽量在初期就将表要做的结构都想明白,防止在数据加载之后,更改表结构带来的各种不可用。因为三次更改表就需要reorg table了。数值类型,比如销售额或者某个较大的数值需要给予integer或者big int,防止数值溢出。另外,能用数值类型,就不用字符类型char。尽量将表数据、索引或者大对象(如果有的话)放置到不同的表空间(增加并行性,减少争磁头,又能扩展表的大小)。表分区是一个很好的特性,使用分区索引更是理想(默认选项),在转入转出能提供比非分区索引更好的性能,分区键最好是整数等数值类型。对表数据的限制最好能用约束就用约束,少用触发器。索引的设计是表可用性最重要的一环,对谓词设置索引,多谓词时,使用选择性大的谓词作为高次序索引分项。对于包含列,将select的列作为包含列,因为这个列不参与索引排序数据,只是被查询。对于范围谓词较多的应用,设计cluster索引。查询表数据对于不同列的选择性,衡量单列索引和多列索引,比如性能和选择度差不多,就使用单列索引可以减少存储的大小。尽量使用明确的desc,asc作为列的限定词,这样可以提升列函数,比如max,min的性能。对于插入较多的表,建表时使用较大的pctfree,比如20-35,对于只读表设置为0 可以节省空间。同样的,对于插入较多的索引,也可以设置较大的pctfree。表压缩是一个重要的特性,大大减少了表数据量,但是需要reorg table,降低了表的可用性,10.1开始提供了compress yes adaptive,在IU,import,load,redistribution(数据库分区重平衡),reorg,admin_move期间都会起动压缩。对于变化快速表,使用volatile可以强制使用索引,将避免runstats更新不及时的问题。对于追加历史表的insert,可以启用表 append on,并定期reorg可以提升insert性能。另外增加一些生成列可以大幅度提升sql中复杂计算的性能。另外对于lob对象,可以使用inline 选项,降低大对象空间需求。逻辑设计中很重要一个问题就是各种名称的规范化,这个各大公司应该有各自的规范就不详细叙述,这个对表的可用性的重要性不亚于技术。合理设计表名,视图名,索引名,约束名将大大降低运维和性能调优的复杂度。MDC对于多维查询比较有用,一般用于OLAP系统。对于 OLAP,MQT很重要,对于多个大表,排序连接聚集的性能十分显著。






如果觉得我的文章对您有用,请点赞。您的支持将鼓励我继续创作!

3

添加新评论12 条评论

ly3721ly3721数据库管理员旅游
2015-01-04 10:40
很好的文章,顶一个
finixfinix数据库架构师中国银行
2014-05-28 16:56
顶一个
ironkobeironkobe系统运维工程师北京银信长远科技股份有限公司
2014-05-22 14:43
体现作者的能力水平
daoguo525daoguo525系统工程师世纪五岳(北京)科技有限公司
2013-11-10 21:33
写的真好,学习了
bygt2010bygt2010it技术咨询顾问自由空间科技公司
2013-10-17 11:28
写的真好,学习了1
1523626069815236260698研发工程师南京某软件科技公司
2013-05-27 15:58
写的不错,多多学习
liuziquanliuziquan数据库管理员金蝶软件(中国)有限公司
2013-04-22 08:39
确实是好文!
amormioslamormiosl系统工程师DC
2013-04-15 16:48
精品啊。学习了。
lsboyslsboys数据库管理员海盛科技
2013-04-15 14:12
总结的很全面,学习之
繁华如梦繁华如梦其它深圳某证券
2013-04-14 19:52
相当好的文章,浓缩了精华.这里能不能提个问题,大部分的书也都是围绕着这些观点在评论,但是作为许多读者来说可能并没有这种环境或者数据量来体会这些参数的重要性或者优化设计的思路,您能否根据实际经验来给点数据量的参考?比如多少G的数据怎样怎样..好像有点返.哈哈.
sunyangnjsunyangnj技术经理苏宁金融研究院
2013-04-11 22:34
jaminwm: 好文一篇,居然没有人回复。我顶一下。MDC这块能再将细一点吗
可以,下次有时间详细写
jaminwmjaminwm系统架构师PCI
2013-04-11 16:22
好文一篇,居然没有人回复。我顶一下。MDC这块能再将细一点吗
Ctrl+Enter 发表

作者其他文章

相关文章

相关问题

相关资料

X社区推广