2006/5/16

hibernate中session.delete(sql),3.1与2.0的区别,导致的错误

今天使用session.delete(sql);报下面的错误:
 
org.hibernate.MappingException: Unknown entity: java.lang.String
 at org.hibernate.impl.SessionFactoryImpl.getEntityPersister(SessionFactoryImpl.java:569)
 at org.hibernate.impl.SessionImpl.getEntityPersister(SessionImpl.java:1086)
 at org.hibernate.event.def.DefaultDeleteEventListener.onDelete(DefaultDeleteEventListener.java:63)
 at org.hibernate.impl.SessionImpl.delete(SessionImpl.java:579)
 
查查终于知道原因:
 
    session.delete(sql)是2.0的接口,3.1中已经废弃,同时废弃的有:
    find()、iterate()、filter()和delete(String hqlSelectQuery),saveOrUpdateCopy()
 
  如果要使用的话,可以采用以下方式创建Session实例: 

      org.hibernate.classic.Session session=sessionFactory.openSession(); 
 
      org.hibernate.classic.Session保留了2.0的接口
 
下面是3.1的reference里面这样写的,我使用了,但是还是报错,郁闷:
 
1) Hibernate3.0执行批量删除的程序代码: 
Session session = sessionFactory.openSession(); 
Transaction tx = session.beginTransaction(); 
String hqlDelete = "delete Customer where name = :oldName"; 
int deletedEntities = s.createQuery( hqlDelete ) 
.setString( "oldName", oldName ) 
.executeUpdate(); 
tx.commit(); 
session.close();
 
2)Hibernate3.0执行批量更新的程序代码: 
Session session = sessionFactory.openSession(); 
Transaction tx = session.beginTransaction(); 
String hqlUpdate = "update Customer set name = :newName where name = :oldName"; 
int updatedEntities = s.createQuery( hqlUpdate ) 
.setString( "newName", newName ) 
.setString( "oldName", oldName ) 
.executeUpdate(); 
tx.commit(); 
session.close(); 
 
我按照上面的写法,运行后报错如下:

org.hibernate.QueryException: query must begin with SELECT or FROM: delete [delete Resource r where r.nodeId=:nodeId and r.devId is not null ]
 at org.hibernate.hql.classic.ClauseParser.token(ClauseParser.java:83)
 at org.hibernate.hql.classic.PreprocessingParser.token(PreprocessingParser.java:108)
 at org.hibernate.hql.classic.ParserHelper.parse(ParserHelper.java:28)
 at org.hibernate.hql.classic.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:176)
 at org.hibernate.hql.classic.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:152)
 at org.hibernate.impl.SessionFactoryImpl.getQuery(SessionFactoryImpl.java:427)
 at org.hibernate.impl.SessionImpl.getQueries(SessionImpl.java:884)
 at org.hibernate.impl.SessionImpl.executeUpdate(SessionImpl.java:865)
 at org.hibernate.impl.QueryImpl.executeUpdate(QueryImpl.java:89)


昨天的问题解决了

又把hibernate3的手册仔细的看了一遍,确认自己的写法是没错的,然后又上hibernate的论坛,几乎没有人有我的这个问题,这才想到是不是同事在hibernate.hbm.xml中设置了什么参数,使得我不能使用3.0的特性呢?
      看了,果真如此,郁闷哦~
     里面有一句:
     <property name="hibernate.query.factory_class">org.hibernate.hql.classic.ClassicQueryTranslatorFactory</property>
     这样就使用了2.0的接口.郁闷啊.
     把这句去掉就OK了.
 
     附:
      因为使用了中文拼装的hql后,中文会变成问号,大致如下:
 
      String hql="from user u where u.name like %"+userName+"%";
 
      3.0版本是:
      Query query = session.createQuery("from user u where u.name like :username").setString("username",userName);




现在要通过一个主键id去数据库中删除对应的一条记录,我该怎样做?如果是将参数delId传递进来的话,那该怎么处理? 我这样做的,但是报了错 public void delfun(String delId) throws DatastoreException { Session session = HibernateUtil.getSession(); Transaction tx = null; try{ tx = session.beginTransaction(); Info info = (Info)session.load(Info.class,id); //出错行 session.delete(delId); tx.commit(); } catch(Exception ex) { HibernateUtil.rollbackTransaction(tx); throw DatastoreException.datastoreError(ex); } finally { HibernateUtil.closeSession(session); } } 错误信息为: com.framework.exceptions.DatastoreException.datastoreError(DatastoreException.java:28) com.service.NpisServiceImpl.delGyinfo(NpisServiceImpl.java:131)
回复人:pdvv(我爱花猫) 2006-3-1 17:32:22得分:0
?
你给出的异常应该属于你自己框架的信息吧,没有多少参考价值。 使用Session.load()要确保数据一定存在,还是用get()吧; 或者直接session.delete("from INFO where ID = 1");
Top
回复人:yuanjian0211(元剑) 2006-3-1 17:46:04得分:0
?
错误提示信息为: Hibernate: select gyinfo0_.id as id0_, info0_.userid as userid0_, info0_.tit le as title0_,info0_.descript as descript0_ from Info info0_ where info0_.id=? 请指点
Top
回复人:yuanjian0211(元剑) 2006-3-1 17:56:29得分:0
?
id在数据库表中为bigint型 在对象中为long型
Top
回复人:iori_powermax() 2006-03-02 01:06:00得分:0
?
我也在学习hibernate,不知道说的对不对. 你删除的应该是整个对象,而不是一个id,所以应该为: Info info = (Info)session.load(Info.class,id); session.delete(info); 或者还有一种删除记录的方法: info=(Info)sn.creatQuery("from Info as a where a.ID= '"+delId+"'").uniqueResult(); sn.delete(info); 另外想问一下大家: hibernate的creatSQLQuery()是不是只支持查询?好象增删改都不可以
Top
回复人:ymfhcn(这痞子真帅) 2006-03-02 08:06:00得分:0
?
creatSQLQuery()是执行sql语句的,不过稍微有些改动,里面什么SQL语句都可以写



 | = | 一般分类 | 仙侠修真 | VBScript | .NET | 面试题 | 存储过程 | Hibernate | JavaScript | J2EE | Struts
自我介绍
切换风格
订阅我的Blog
博客日历
文章归档...
最新发表...
博客统计...
网站链接...
资源
===========================================================
Hibernate 的 session.delete(obj
===========================================================

session.delete(obj)将obj的状态变为transient。两种情况
1)obj是session的cache里边的cache没有的,比如:
session.delete(new Employee(4));
2)obj存在于session的cache中,比如:
Employee employee = (Employee)session.load(Employee.class, new Integer(4));
session.delete(employee);

这两种情况都是允许的,hibernate都会发送一条delete语句给数据库。

delete执行之后,如果调用了session.load(), 又可以分为两种情况:1)在session.flush()之前,如:
tx.beginTransaction();
    session.delete(new Employee(4));
session.load(Employee.class, new Integer(4));//发生在session.flush()之前
tx.commit();
那么hibernate会抛出ObjectDeletedException:The object with that id was deleted:

2)在session.flush()之后,如:
tx.beginTransaction();
    session.delete(new Employee(4));
session.load(Employee.class, new Integer(4));
tx.commit();

tx.beginTransaction();
session.load(Employee.class, new Integer(4));//同一个session中,上面的tx.commit()将session flush了一次。
tx.commit();
那么这个时候hibernate仅仅会抛出ObjectNotFoundException:No row with the give...
表示找不到该object。如果第二个tx里边采用session.get()也就不会抛出exception了。

delete执行之后,如果调用了session.save(obj):
tx.beginTransaction();
Employee employee = (Employee)session.load(Employee.class, new Integer(4));
    session.delete(employee);
System.out.println(employee);
session.save(employee);
System.out.println(employee);
tx.commit();
这种情况是完全合理的,合法的。
delete将employee从persistent的状态变为transient的状态。
save将employee从transient状态变为persistent的状态。
save一个被delete的obj的时候,在save处hibernate强制执行session.flush(),发送delete语句,然后按照常规的save流程来进行。为什么要这么做,还没有完全想明白。

delete执行之后,如果对obj对象属性的修改,tx.commit()时不会进行dirtyChecking。
这个道理比较显然。

- 作者: HairRoot 2005年05月




hibernate连接sqlserver2000问题的解决

这几天在进行数据库的移植,将oracle数据库的东西移植到mssqlserver 2000上
 
其中运行一个查询的时候,报如下的错误:
 
 [Microsoft][SQLServer 2000 Driver for JDBC]Can't start a cloned connection while in manual transaction mode.
 
解决办法:
   <property name="connection.url">
     jdbc:microsoft:sqlserver://192.168.1.110:2433;SelectMethod=cursor
  </property>
 
(红色为增加的)
 
原因:
   1.    处于手动事务状态,并且使用direct模式,因为hibernate默认为direct模式,
         即 SelectMethod=direct
   2.    在一个SQL SERVER的JDBC连接上执行多个STATEMENTS的操作


超强的贴,每句都是经典
水至清则无鱼,人至贱则无敌! 走自己的路,让别人打车去吧。穿别人的鞋,走自己的路,让他们找去吧。打台湾我捐一个月的生活费,打美国我捐一年的生活费, 打日本我捐他妈的一条命! 我不是随便的人,我随便起来不是人。女人无所谓正派,正派是因为受到的引诱不够;男人无所谓忠诚,忠诚是因为背叛的筹码太低…… 骑白马的不一定是王子,可能是唐僧;带翅膀的也不一定是天使,有时候是鸟人。 俺的最低奋斗目标:农妇,山泉,有点田。再过几十年,我们来相会,送到火葬场,全部烧成灰,你一堆,我一堆,谁也不认识谁,全部送到农村做化肥




http://iceling2008.itpub.net/category/13270/23134好东西         阿法萨
http://comsmall.spaces.live.com/PersonalSpace.aspx?_c02_owner=1


遇到 "Automation服务器不能创建对象"

运行 Regsvr32 scrrun.dll。