Hibernae的一个小问题。。。

 <many-to-one not-null="true" column="report_type_id" name="reportType" class="net.gbicc.csrc.console.model.ReportType"/>
建了一个many-to-one 的关系。

 

<hibernate-mapping>
  <class dynamic-update="true" table="csrc_date_limit" name="net.gbicc.csrc.console.model.DateLimit" dynamic-insert="true">
    <id type="string" column="date_limit_id" length="32" name="idStr">
      <generator class="uuid"/>
    </id>
    <property name="reportYear" not-null="true" length="4" type="string" column="report_year"/>
    <many-to-one not-null="true" column="report_type_id" name="reportType" class="net.gbicc.csrc.console.model.ReportType"/>
    <property name="startDateTime" not-null="true" type="calendar" column="start_datetime"/>
    <property name="endDateTime" not-null="true" type="calendar" column="end_datetime"/>
    <property name="createDateTime" not-null="true" type="calendar" column="create_datetime"/>
    <property name="updateDateTime" not-null="true" type="calendar" column="update_datetime"/>
  </class>
</hibernate-mapping>

 

                                DateLimit dateLimit = new DateLimit();
        dateLimit.setReportYear(reportYear);
        dateLimit.setReportType(new ReportType(reportTypeId));
        dateLimit.setStartDateTime(DateTimeUtils
                .strDateTime2Calendar(startDateTime));
        dateLimit.setEndDateTime(DateTimeUtils
                .strDateTime2Calendar(endDateTime));
  
dateLimitSave = dateLimitManager.save(dateLimit); //插入到数据库 后台sql语句都打出来了
System.out.pringtln(dateLimitSave.getReportType().getReportDesp());打出来是null 请问哪位高手跟我解释一下? 为什么没值。

 

[quote]恩 写在save之后。。看样子只能查了。。当时没想那么多。。。。谢谢你。。让我一下子想通了。。。我还以为是哪里没配置好。。[/quote]
不是配置的问题,如果你想在缓存中拿东西也必须是在同一个session中才行,因为session关闭了一级缓存也就清空了,你想拿也不行了。

[quote]dateLimit.setReportType(new ReportType(reportTypeId));[/quote]

你new的ReportType根本没有存进数据库中,也就是说在数据库不存在DateLimit对应的ReportType,在many-to-one上加上cascade="save-update"属性。

[quote]您好,进了数据库。你刚刚说的我也配置了,主要是延迟加载不起作用?[/quote]
那你查看了数据库中对应的那个reportType的reportDesp值了吗?你这new ReportType(reportTypeId),也没见你设置了reportDesp的值?

你确定你有级联插入?
[code="java"]
dateLimit.setReportType(new ReportType(reportTypeId));
[/code]
这个不代表ReportType就被插进去了吧 你看看这个表里有没数据

请搜索关键字 “cascade inverse 级联”

[quote]System.out.pringtln(dateLimitSave.getReportType().getReportDesp());打出来是null 请问哪位高手跟我解释一下? 为什么没值。 [/quote]
那请问你这步是哪里执行的呢?和前面你构造DateLimit和保存DateLimit是在一个方法中还是什么?

[quote]System.out.pringtln(dateLimitSave.getReportType().getReportDesp());[/quote]

这是在哪执行的?

[quote]主要是延迟加载不起作用?[/quote]
应该不是延迟加载,要是延迟加载的话会抛出exception吧

另外 试试加上

[code="java"]

[/code]

[quote]dateLimitSave = dateLimitManager.save(dateLimit);[/quote]
你save后返回的这个dateLimitSave是传进去的dateLimit还是保存以后又查找了一次出来的呢?

[quote]我没查。如果查了,肯定会出来。我保存完之后,直接用的保存的对象点的。[/quote]

那我想很有可能就是你这个dateLimitSave还是你保存前的状态,这时reportDesp根本没有值。

[code="java"]
我保存完之后,直接用的保存的对象点的。
System.out.pringtln(dateLimitSave.getReportType().getReportDesp());
[/code]
你试试getID看看哟没有值
[code="java"]
System.out.pringtln(dateLimitSave.getReportType().getReportTypeId());
[/code]

我觉得直接save返回值有问题 一般save操作不都是void 没有返回值的嚒。。。

[quote] 哦。。。但是它主键ID都有了?[/quote]

因为你new的时候构造函数传进去的。。。。

[code="java"]dateLimit.setReportType(new ReportType(reportTypeId)); [/code]
就是这里的ID传进去的

结论应该就是还是dateLimitSave还是旧的那个 没有返回新的值吧

[quote]哦 我懂了。。new的时候,给这对象已经指定了一引用。。意思就是这样的情况,没办法解决哦。[/quote]
我不理解你为什么要在save后返回这个对象呢?如果两步操作是处在同一个session时,我觉得是可以的,因为这时dateLimit已经从瞬时态转为持久态了,如果你事务是只加在save上的话,那我想是不可以的。

你可以不用new
直接用ReportType的DAO

ReportType type = ReportTypeDAO.findById(reportTypeId); 先把ReportType取出来
再set
dateLimitSave.setReportType(type );

[quote]dateLimitManager.save(dateLimit);[/quote]
写在save方法里面?如果你不想这样做,那我的建议是再查找出来吧

[quote]我就是不想多写这代码?我想直接从缓存中拿[/quote]

你想从缓存中拿那也得你的这几步操作是在同一个session中才行三。

[quote]是的。。save提交后?事物就关闭了。。session也换了?不是同一个session了?是的吧?[/quote]
嗯,是这样的。

额 其实我还是建议再查的或者前面说的 先读取ReportType 。。。。

从代码以后的维护上来说。。。不应该把查数据放到save方法里去的。。。

其实也就几句代码的 =。=