随便写点:关于java操作数据库和oracle锁。。。

    昨天导数据到测试数据库,由于数据文件内容有少许地方需要改动,由此有时候进行到一半需要恢复数据到导数据之前,然后修改数据文件后再次导入。还好oracle有flashback功能:
alter table table_name disable row movement;
flashback table table_name to timestamp to_timestamp('2009-04-24 13:20:00','yyyy-mm-dd hh24:mi:ss');
    可以将表恢复到某个时间点时的状态,用起来倒也蛮方便,上次导过一次一切都还算正常,不过昨天导的时候报错后用flashback报资源被占用,以nowait方式。。。大概就那意思,似乎flashback过程中要处理的资源被占用了,偶这方面经验着实不足,看了看导数据的代码,除了异常后连接没释放外似乎也没有啥问题,都是些插入语句,况且程序结束后java程序中用到的数据库资源都应该被释放掉了饿。。。于是手动删除刚插入的数据想看看有啥效果,结果等待,看来是锁住了,
    查了下死锁: 
    select t2.username||'   '||t2.sid||'   '||t2.serial#||'   '||t2.logon_time||'   '||t3.sql_text
      from v$locked_object t1,v$session t2,v$sqltext t3
      where t1.session_id=t2.sid
      and t2.sql_address=t3.address
      order by t2.logon_time
    果然发现有记录,不过kill掉后仍然不行,
    kill锁sql语句: alter system kill session 'sid,serial#'
    于是将v$sqltext视图从上面查询语句中去掉,发现了几条记录,kill掉后便正常了。flashback时以nowait方式,于是没有等待,手动删除时等待便产生了死锁,搞的我有点头晕。。。现在还没有很明白为啥会这样子?现在又不能重复了,只能以后多注意了。希望不要是系统的问题吧。

     自己写了点代码试了试java连oracle,发现执行conn.createStatement()和 conn.prepareStatement()很多次也不会报ORA-01000: maximum open cursors exceeded.的错误,不过如果在循环里执行executeQuery、executeUpdate或execute时就会报游标exceeded错误,估计一个statement对应打开一个游标,一个statement执行很多次execute不会报错,写程序时还是注意关闭连接的好。最大cursors数可以在pfile中配置。


    网上查到:v$open_cursor视图可以看到cached cursors,看当前打开的游标可以通过下面的查询:
    select a.value, s.username, s.sid, s.serial#
    from v$sesstat a, v$statname b, v$session s
    where a.statistic# = b.statistic#  and s.sid=a.sid
    and b.name = 'opened cursors current';

不过我在程序中execute很多次,查出来的结果依然只有那么几条,倒是v$open_cursor中都包括自己打开的游标,程序结束后查到的记录恢复之前的状态。现在对这个依然有些模糊,不过查了很多都没有让我明白,看来是自己资质愚钝饿。。。

    ORA-01000错误是针对一个连接而言的,而oracle也有最大连接数,在pfile中的process项设置。如果不是用的连接池,连接不释放也会被java的GC机制给回收掉,回收statement对象时会调用其close方法,不过为保证稳定还是要注意close连接。如果用的是连接池,连接不会被关闭,statement不关闭 就很可能会导致游标超出。

      java的connection得到的是一个会话,一个连接对应多个会话。connection设置autoCommit(false)后,如果用的是连接池,调用close方法后,connection实际上并没有断开,如果异常处理块中不rollback,处理块如果有锁会没有机会释放,因此需要注意。

     讲oracle锁方面的知识的资源很多,不过偶一直没法深入去理解,也许是没有被这方面的问题锁折腾,也许是资质愚钝。我就知道select..for update返回结果集中的数据行只能被查询,而DML操作会获得RX锁,commit释放锁前,不允许更新或删除。
      外键未加索引时,删除主表时会给从表加一个表级锁,如果从表有RX锁,则会等待;有索引时则直接操作不会等待。锁的原理有些不理解。。。

     上面写的蛮多东西自己都有些不理解,当做日志记录下吧。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值