db2数据库常见问题处理
db2数据库常见问题处理
1 数据库实例挂起
现象:
数据库操作无返回,应用程序无响应,查看数据库实例发现挂起。
分析:
1、执行ps -ef|grep db2sysc 确认系统中是否存在db2sysc 进程,判断数据库实例是否出现异常。
2、执行db2gcf -s -p 分区号-i 实例名确认实例状态是否为Available。
处理:
1、执行如下命令收集db2fodc -hang 数据:
db2fodc –hang –alldbs
2、如果收集的时间过长,可适当减小收集范围:
db2pd –stack all –repeat 5
db2pd –latch –repeat 5
3、使用DB2 数据库系统用户执行db2_kill 命令杀掉DB2 进程,使用ps –ef|grep db2 命令确认DB2 进程已全部清除,然后执行db2start 命令启动数据库,再执行
db2 connect to db_name;
db2 “select * from syscat.bufferpools”
验证DB2 数据库操作正常。
4、重新启动DB2 后再使用db2support 收集相关信息:
db2support /tmp/db2data -d <db_name> -a -g -l -r -s
5、在AIX 系统中可执行snap -gc 命令、在Linux 系统可执行support –a 命令收集操作系统信息,以帮助分析数据库实例进程为何出现异常。
2 数据库实例崩溃
现象:
DB2 进程异常结束,无法提供服务。
分析:
执行ps –ef |grep db2sysc 发现DB2 进程消失。
处理:
1、使用DB2 数据库系统用户执行db2start 命令启动数据库,并执行
db2 connect to db_name;
db2 “select * from syscat.bufferpools”
验证DB2 数据库操作正常。
2、执行db2support . –d db_name -c –s –f 命令收集数据,执行
db2trc on -t -f server.dmp;
db2trc fmt server.dmp server.fmt;
db2trc flw -t server.dmp server.flw
命令开启db2trc,监控问题是否重现,收集trace 数据。
3 数据库连接数满
现象:
应用程序连接数据库时出现SQL1040N The maximum number of applications is already connected to the database 报错,无法建立新的数据库连接。
分析:
1、执行db2 get db cfg for sample | grep –i maxappls 查看当前数据库maxappls 参数值。
2、执行db2pd –db db_name –app 或者db2 list applications |wc –l 检查应用程序的总连接数是否已超过数据库最大允许连接数。
处理:
执行db2 update db cfg for sample using maxappls automatic 命令更新maxappls 参数,使之自动增长。
4 数据库事务日志满
现象:
单个交易处理数据量大,导致日志满情况发生。
分析:
执行如下查询,可检查占用日志较大的交易:
db2 “SELECT SUBSTR(DB_NAME,1,8) AS DB_NAME, AGENT_ID, ROWS_READ,ROWS_WRITTEN, UOW_LOG_SPACE_USED, UOW_START_TIME, UOW_STOP_TIME,ELAPSED_EXEC_TIME_S FROM SYSIBMADM.SNAPAPPL”
处理:
1、若数据库日志满,DB2 将强制回滚事务。可通过db2pd –db db_name –apinfo 数据库名察看应用状态,应该处于rollback 状态。
2、DB2 数据库有2 个参数可以控制每个交易使用的日志量,避免单个交易占用索引日志情况, 可执行
db2 update dbm cfg using MAX_LOG 80 和db2 update dbm cfg usingNUM_LOG_SPAN 80
设置该参数为80%,避免单个大交易的情况。
3、规避方法:
当数据库日志空间存在用尽风险时,可以通过在线增加logsecond 参数来增加可用的日志空间,避免出现日志空间满的情况。在扩展此参数前,需确认数据库日志所在的文件系统有空闲空间。
确认数据库的日志路径:
db2 get db cfg for
增加logsecond:
单分区环境:
db2 update db cfg using logsecond
注:num 为参数logsecond 的新的值。
多分区环境:
db2_all “db2 update db cfg using logsecond
注:num 为参数logsecond 的新的值。
5 数据库事务日志误删
现象:
数据库活动日志被误删除。
分析:
进入DB2 活动日志目录下,检查发现日志文件已经被误删除。
处理:
通过最新的数据库备份进行恢复,执行恢复之后前滚日志。命令:
db2 RESTORE DATABASE 数据库名 FROM 备份文件位置" TAKEN AT 时间戳 to 待恢复的实例名" logtarget 日志目录REPLACE EXISTING redirect
注:日志重置后,强烈建议数据库重建,避免存在隐患。
6 数据库表空间满
现象:
巡检发现数据库日志中出现如下错误信息:
FUNCTION: DB2 UDB, buffer pool services, sqlbDMScheckObjAlloc, probe:830
MESSAGE : ZRC=0x85020021=-2063466463=SQLB_END_OF_CONTAINER “DMS Containerspace full”
分析:
1、执行如下SQL 语句,确认表空间使用率:
$db2 “connect to 数据库名 user 用户 using 密码
$db2 “select substr(a.tbsp_name,1,18) as name,substr(a.tbsp_type,1,10) as
tbstype,a.TBSP_USING_AUTO_STORAGE as AUTO_STORAGE,substr(a.tbsp_state,1,8) as
state,a.tbsp_total_size_kb/1024 as TotalMB ,a.TBSP_PAGE_TOP*a.TBSP_PAGE_SIZE/1024/1024 as
top_size_mb,a.tbsp_used_size_kb/1024 as UsedMB, a.TBSP_UTILIZATION_PERCENT as
UsedPer ,b.CONTAINER_NAME from sysibmadm.tbsp_utilization a, sysibmadm.SNAPCONTAINER
b where tbsp_type=‘DMS’ and a.TBSP_ID=b.TBSP_ID order by AUTO_STORAGE,UsedPer desc”
2、执行如下命令确认容器类型:
单分区环境
$db2pd -d
多分区环境:
$db2_all “db2pd -d
处理:
执行
$db2 “alter tablespace
扩容表空间。
注:表空间增加的大小为容器数量*N,N 为每个容器增加的大小。
7 数据库表空间状态异常
现象:
系统监控报警数据库表空间状态异常。
分析:
1、由于存储、操作或者权限等原因,会导致DB2 表空间状态异常。此时,可查询表空间16 进制的状态值。命令:
$db2 list tablespaces show detail|grep -i state
2、根据返回的16 进制值,确认表空间状态。命令:
$db2tbst
3、表空间状态信息对应的描述:
Return code | Description | 描述 |
0x0 | Normal | 正常 |
0x1 | Quiesced: SHARE | 静止态共享 |
0x2 | Quiesced: UPDATE | 静止态更新 |
0x4 | Quiesced: EXCLUSIVE | 静止态排它 |
0x8 | Load pending | 载入挂起 |
0x10 | Delete pending | 删除挂起 |
0x20 | Backup pending | 备份挂起 |
0x40 | Roll forward in progress | 正在回滚 |
0x80 | Roll forward pending | 回滚挂起 |
0x100 | Restore pending | 存储挂起 |
0x100 | Recovery pending (not used) | 恢复挂起 |
0x200 | Disable pending | 禁用挂起 |
0x400 | Reorg in progress | 正在重组 |
0x800 | Backup in progress | 正在备份 |
0x1000 | Storage must be defined | 存储器未被指定 |
0x2000 | Restore in progress | 正在恢复 |
0x4000 | Offline and not accessible | 表空间不可访问 |
0x8000 | Drop pending | 删除挂起 |
0x2000000 | Storage may be defined | 存储器需被指定 |
0x4000000 | StorDef is in ‘final’ state | 存储器终止 |
0x8000000 | StorDef was changed prior to rollforward | 存储器被改变至回滚状态 |
0x10000000 | DMS rebalancer is active | 表空间的容器重新分布 |
0x20000000 | TBS deletion in progress | 表空间删除 |
0x40000000 | TBS creation in progress | 表空间建立 |
处理:
常见异常状态的处理方式:
状态 | 状态值 | 原因 | 状态描述及处理方式 |
Backup Pending | 0x20 | 归档日志下进行LOAD 操作导致 | 对状态异常的表空间执行备份,命令: db2 backup database db_name tablespace(syscatspace, userspace1) to/dbbackupdir |
Offline and Not Accessible | 0x4000 | 1.表空间使用的物理设备不可访问 2.物理设备权限不对 | 修复物理设备问题,保证权限正确,然后修改表空间为online 状态,命令: db2 ALTER TABLESPACE |
Restore Pending | 0x100 | 恢复过程中,表空间对应的物理设备不可用,表空间就处于这种状态。 | 必须恢复单个表空间(或者是整 个数据库)。命令: db2 restore database db_name tablespace (XXX) 如果是归档日志,则前滚日志,命令: db2 rollfoward db db_name to end of logs and complete |
Roll Forward Pending | 0x80 | 由于物理设备不可用或者权限问题, 导致CRASH RECOVERY 时日志无法前滚,出现上述问题; | 必须前滚数据库,命令: db2 rollfoward db db_name to end of logs and complete |
Storage Must be Defined | 0x1000 | 在将恢复操作重定向到新数据库期间,如果省略了设置表空间容器的阶段,或者,如果在设置表空间容器的阶段期间无法获得指定的容器,那么数据库的表空间就会处于这种状态。 | 需要重新制定表空间使用的容器,命令: db2 SET TABLESPACE CONTAINERS FOR 1 USING (容器名) |
8 数据库表或数据误删
现象:
数据库中的表或数据被误删除。
分析:
与操作人员确认误删除发生的时间以及被删除的数据内容。
处理:
1、如果该表或数据所在的表空间不大,恢复时间较短,且该表所在的表空间已启用DROPPED TABLE RECOVERY 选项,建议采用数据库前滚恢复的方式恢复表或数据。可通过如下命令查询字典表SYSCAT.TABLESPACES 来验证表空间是否已开启DROPPED TABLE RECOVERY选项:
db2 “select tbspace,drop_recovery from syscat.tablespaces”
TBSPACE DROP_RECOVERY
SYSCATSPACE N
TEMPSPACE1 N
USERSPACE1 Y
ALANSPACE1 Y
ALANSPACE2 Y
SYSTOOLSPACE Y
2、尝试恢复数据库:
(a)、执行db2 restore database irmdb from D:\IBM\alanbak taken at 20100628154742 into irmdb命令,将会显示SQL2539W 警告!正在复原至与备份映像数据库相同的现有数据库。
数据库文件将被删除。想要继续吗?(y/n)
回答Y。
DB20000I RESTORE DATABASE 命令成功完成。
(b)、执行db2 list history dropped table all for irmdb从历史文件中检索已经丢失表对象的ID。列示irmdb 的历史记录文件:
匹配的文件条目数= 1
Op 对象时间戳记+序列类型设备最早日志当前日志备份标识
D T 20100628154949 000000000000f40200030004
“DB2ADMIN”.“ALANTEST1” 驻留在1 表空间中:00001 ALANSPACE1
注释:DROP TABLE
开始时间:20100628154949
结束时间:20100628154949
状态:A
EID:13
DDL: CREATE TABLE “DB2ADMIN”.“ALANTEST1” ( “ID” INTEGER , “NAME” VARCHAR(10) ) IN “ALANSPACE1” ;
其中我们可以查看一下备份标识:000000000000f40200030004,这个信息对于恢复表非常重要。
(c)、Rollforward数据库到日志结尾,同时生成恢复导入文件(我们需要利用上面的备份标识000000000000f40200030004来恢复数据库,同时准备出一个导出目录D:\IBM\exporttab)。执行如下命令:
db2 “rollforward database irmdb to end of logs and stop tablespace (alanspace1) online recover
dropped table 000000000000f40200030004 to D:\IBM\exporttab”
前滚状态
输入数据库别名= irmdb
节点数已返回状态= 1
节点号= 0
前滚状态= 未暂挂
下一个要读取的日志文件=
已处理的日志文件= S0000002.LOG - S0000004.LOG
上次落实的事务= 2010-06-28-07.49.50.000000 UTC
DB20000I ROLLFORWARD 命令成功完成。
(d)、此时我们可以看到在D:\IBM\exporttab\NODE0000目录下生成了一个data文件,内容就是我们表中丢失的数据。然后,我们用LIST HISTORY中的DDL来重建表结构并IMPORT相应的数据,如下:
DDL: CREATE TABLE “DB2ADMIN”.“ALANTEST1” ( “ID” INTEGER , “NAME” VARCHAR(10) ) IN “ALANSPACE1” ;
db2 CREATE TABLE “DB2ADMIN”.“ALANTEST1” ( “ID” INTEGER , “NAME” VARCHAR(10) )
DB20000I SQL 命令成功完成。
db2 import from D:\IBM\exporttab\NODE0000\data of del insert into db2admin.alantest1
SQL3109N 实用程序正在开始从文件"D:\IBM\exporttab\NODE0000\data” 装入数据。
SQL3110N 实用程序已完成处理。从输入文件读了"5" 行。
SQL3221W …开始COMMIT WORK。输入记录计数= “5”。
SQL3222W …对任何数据库更改的COMMIT 都成功。
SQL3149N 处理了输入文件中的"5" 行。已将"5" 行成功插入表中。拒绝了"0" 行。
读取行数= 5
跳过行数= 0
插入行数= 5
更新行数= 0
拒绝行数= 0
落实行数= 5
3、如果该表所在的表空间很大,恢复时间远大于停机窗口,建议根据之前的建表语句重建表,并利用最新的逻辑备份导入最新的备份数据,手工补做数据丢失的时间段业务。
9 死锁或超时,导致当前事务回滚
现象:
当前事务因死锁或超时而回滚,提示信息如下:
SQL0911N The current transaction has been rolled back because of a deadlock or timeout. Reason code “2”
分析:
根据报错的具体信息,可以判定,原因为死锁导致超时。
处理:
为了帮助避免死锁或锁定超时,可以采用如下两种方法
1、对长时间运行的应用程序或有可能遇到死锁的应用程序频繁发出COMMIT 操作(若有可能的话)。
2、修改数据库参数,适当地增大锁超时时间(此处60 秒为例),命令如下:
db2 update db cfg using LOCKTIMEOUT 60