use*_*550 5 java mysql hibernate
我有一个Client-Server应用程序,在我的服务器中我使用hibernate进行数据库处理.现在,我的应用程序需要在所有数据库表中,一个简单的表,其中只有一行一个Biginteger字段(这是该行中的键).这个表实际上只包含一个全局数字(从1开始),我每次用户执行某些操作时都会使用该数字,当他执行某些操作时,我需要获取此值,并在数据库中增加该值.(该表只包含一行,始终只有一个值)
我正在使用以下代码来实现这一目标:
Biginteger func() {
Session s = null;
Biginteger idToReturn=null;
try{
s=factory.openSession();
s.beginTransaction();
Query queryResult = s.createQuery("from GlobalId");
List<GlobalID> theId=queryResult.list();
idToReturn=theId.get(0).get_id(); //getting the value from db to return
GlobalID toSave=new GlobalId();
toSave.set_id(idToReturn.add(BigInteger.valueOf(1))); //incrementing the id from db inorder to save it
s.delete(theId.get(0)); //deleting old id
s.save(toSave); //saving new id
s.getTransaction().commit();
}
catch(Exception e){
throw e;
}
finally{
if (s!=null)
s.close();
return idToReturn;
}
}
Run Code Online (Sandbox Code Playgroud)
这段代码工作正常.我担心的是我是否需要使用多台服务器来接近中央数据库.在这种情况下,如果两个单独的服务器将运行此功能,我需要消除它们中的两个将获得相同值的情况.我需要确保整个读写都是"原子的",我需要锁定这个表,这样只要一个会话就能读取该值,我还需要确保会话意外结束,锁定将被删除.
我正在使用xampp包,包括MySQL 5.6数据库.
我在网上发现的关于这个问题的信息令我感到困惑 - 我发现的信息是"高级别的",我找不到任何例子.
您需要使用悲观锁定,这可以通过
setLockMode(String alias, LockMode lockMode)
Run Code Online (Sandbox Code Playgroud)
关于查询和使用LockMode.UPGRADE。
但是,如果您对此表进行大量访问,那么这肯定会破坏可伸缩性和性能。您最好使用序列或另一种策略来创建一个分配数字的服务(例如,SSB),该服务一次可以获取100个数字,更新数据库并将其分发出去。这样可以节省198次数据库访问。
更新:
您还必须稍微修改表格设计。最好有一个具有已知ID的单行,然后将要递增的数字存储在另一列中。然后,您应该更新该行,而不是删除旧行并添加新行。否则,行锁定策略将不起作用。
UPDATE2:
OP发现以下工作有效:
session.get(class.Class, id, lockOption)
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
14338 次 |
| 最近记录: |