]
Hepoi Ko commented on HHH-3851:
-------------------------------
I have similar experience with AS400 Database using JTOpen Library on Hibernate Core 3.3.2
with composite id.
There are two folds:
1. JDBC Specification, on 8.3 about DataTruncation. If you are using PreparedStatement and
the value is a CHAR or VARCHAR column, the JDBC may truncated your value before comparing
the database value and putting SQLWarning after the st.setString(index, value) method.
So what that means is if you have a column with CHAR(4) and have value "ABCD"
inside the database and you use SQL PreparedStatement like "select * from atable
where acolumn = ?" and st.setString(1, "ABCDE"). The JDBC drive should
truncate your "ABCDE" value and adding DataTruncation Exception into SQLWarning
for client code to track the problem.
Since the value is truncated, so the SQL Statement is valid to retrieve the row, and that
row would pass it to the client code (such as Hibernate)
2. So the second fold is that Hibernate does not check this SQLWarning at all, so it has
no idea about DataTruncation warning. And as soon as database return a row from JDBC,
Hibernate "thinks" the SQL statement is correct and it would use this row as a
resultset. Even worst I found that if you use session.get(SomeClass,
IncorrectCompositeID), it returns an entity with the IncorrectCompositeID.
I also tested other JDBC implementation such as Derby and MySQL, both of these drivers do
not truncate value and return no row, and that would work fine with Hibernate. You may be
better check with your JDBC vender (maybe oracle) to see if they are doing truncation in
CHAR value as JDBC specification stated.
Following is the request I sent to JTopen Group and find out the reason:
So for the time being, what you could do is using a UserType to specific a TrimmedString
and apply SQLWarning Check inside the nullSafeSet
method
Hope this is helpful.
object load with composite id
-----------------------------
Key: HHH-3851
URL:
http://opensource.atlassian.com/projects/hibernate/browse/HHH-3851
Project: Hibernate Core
Issue Type: Bug
Components: core
Environment: HIbernate Version : 3.3.1.GA
Database : Oracle 10g
The table column types are CHAR
Reporter: sahasra
Priority: Blocker
Original Estimate: 2 days
Remaining Estimate: 2 days
Having issues in loading, updating, deleting and querying with bind variable an entity
with composite id. The table column types are CHAR
No row with the given identifier exists
but the row exists
I replace "?" by correct values, execute it in the SQL Plus and it works.
Code in the DAO class
public BoardDefinition getBoardDefinitionById(BoardDefinitionId anId)
throws HibernateException
{
BoardDefinition instance =
(BoardDefinition)getHibernateTemplate().get(BoardDefinition.class, anId);
if (instance == null)
{
System.out.println("get successful, no instance found");
}
else
{
System.out.println("get successful, instance found");
}
return instance;
}
Generated SQL on running the test case
select boarddefin0_.STN as STN0_0_, boarddefin0_.BOARD_ID as BOARD2_0_0_,
boarddefin0_.DESCRIPTION as DESCRIPT3_0_0_, boarddefin0_.BOARD_TYPE as BOARD4_0_0_,
boarddefin0_.ACTV_FRA_RPT_FL as ACTV5_0_0_, boarddefin0_.DEACT_TRN_LINUP_FL as
DEACT6_0_0_, boarddefin0_.TMP_MOVE_RESTR_EN as TMP7_0_0_, boarddefin0_.TMP_MOVE_RESTR_TR
as TMP8_0_0_, boarddefin0_.TMP_MOVE_ALW_EN as TMP9_0_0_, boarddefin0_.TMP_MOVE_ALW_TR as
TMP10_0_0_, boarddefin0_.AUTOSHT_CL_VAC_HRS as AUTOSHT11_0_0_,
boarddefin0_.AUTOSHT_CL_VAC_MNS as AUTOSHT12_0_0_, boarddefin0_.AUTOSHT_CL_HRS as
AUTOSHT13_0_0_, boarddefin0_.AUTOSHT_CL_MNS as AUTOSHT14_0_0_, boarddefin0_.COMMENTS as
COMMENTS0_0_, boarddefin0_.WRK_RST_PROF_EN as WRK16_0_0_, boarddefin0_.WRK_RST_PROF_TR as
WRK17_0_0_, boarddefin0_.SEN_MOVE_PROF_EN as SEN18_0_0_, boarddefin0_.SEN_MOVE_PROF_TR as
SEN19_0_0_, boarddefin0_.MILES_PROF_EN as MILES20_0_0_, boarddefin0_.MILES_PROF_TR as
MILES21_0_0_, boarddefin0_.STARTS_PROF_EN as STARTS22_0_0_, boarddefin0_.STARTS_PROF_TR as
STARTS23_0_0_, boarddefin0_.BLE16_EN as BLE24_0_0_, boarddefin0_.FREE_DY_PROF_EN as
FREE25_0_0_, boarddefin0_.FREE_DY_PROF_TR as FREE26_0_0_, boarddefin0_.SGL_DY_VAC_EN as
SGL27_0_0_, boarddefin0_.SGL_DY_VAC_TR as SGL28_0_0_, boarddefin0_.LOF_RQST_ALW_EN_FL as
LOF29_0_0_, boarddefin0_.LOF_RQST_ALW_TR_FL as LOF30_0_0_, boarddefin0_.SVC_TYP_CD as
SVC31_0_0_, boarddefin0_.CRW_CONSIST_CD as CRW32_0_0_, boarddefin0_.UPD_TS as UPD33_0_0_,
boarddefin0_.USER_ID as USER34_0_0_, boarddefin0_.SPRSS_BRD_ADVRT_FL as SPRSS35_0_0_,
boarddefin0_.CRFT_TYP as CRFT36_0_0_, boarddefin0_.HDR_STN as HDR37_0_0_,
boarddefin0_.HDR_BOARD as HDR38_0_0_, boarddefin0_.NBR_TRADES_MAX as NBR39_0_0_,
boarddefin0_.TRADE_RESET_VALUE as TRADE40_0_0_, boarddefin0_.TRADE_RESET_TYPE as
TRADE41_0_0_, boarddefin0_.TRADE_RESET_DT as TRADE42_0_0_, boarddefin0_.TRADE_ALLOWED_IND
as TRADE43_0_0_, boarddefin0_.DISPLCE_CU_AWAY_FL as DISPLCE44_0_0_,
boarddefin0_.NMS_ACTIVE_FL as NMS45_0_0_, boarddefin0_.SAME_BRD_MOVE_CD as SAME46_0_0_,
boarddefin0_.TRADE_AGAINST_CD as TRADE47_0_0_, boarddefin0_.TMP_SEN_POS_PRF_EN as
TMP48_0_0_, boarddefin0_.TMP_SEN_POS_PRF_TR as TMP49_0_0_, boarddefin0_.PERM_CUT_ALLW_FL
as PERM50_0_0_, boarddefin0_.AUTO_PX_STN1 as AUTO51_0_0_, boarddefin0_.AUTO_PX_BRD1 as
AUTO52_0_0_, boarddefin0_.AUTO_PX_STN2 as AUTO53_0_0_, boarddefin0_.AUTO_PX_BRD2 as
AUTO54_0_0_, boarddefin0_.TRADE_TYPE_CD as TRADE55_0_0_, boarddefin0_.SPRS_BRD_ADVRT_DYS
as SPRS56_0_0_, boarddefin0_.BUMP_PX_STN as BUMP57_0_0_, boarddefin0_.BUMP_PX_BOARD as
BUMP58_0_0_, boarddefin0_.BUMP_OPEN_ASG_FL as BUMP59_0_0_, boarddefin0_.BUMP_MOST_JR_FL as
BUMP60_0_0_, boarddefin0_.CUTOFF_STN as CUTOFF61_0_0_, boarddefin0_.CUTOFF_BOARD as
CUTOFF62_0_0_, boarddefin0_.METRA_BOARD_FL as METRA63_0_0_, boarddefin0_.ADVRT_BID_FL as
ADVRT64_0_0_, boarddefin0_.STAND_BID_FL as STAND65_0_0_, boarddefin0_.SEN_MOVE_FL as
SEN66_0_0_, boarddefin0_.FORCED1_FB_FL as FORCED67_0_0_, boarddefin0_.FORCED2_FB_FL as
FORCED68_0_0_, boarddefin0_.AUTO_DH_TU_FL as AUTO69_0_0_, boarddefin0_.RDE_BLGENBID_EN_FL
as RDE70_0_0_, boarddefin0_.RDE_BLGENBID_TR_FL as RDE71_0_0_,
boarddefin0_.SEN_MOVE_ALLOW_CD as SEN72_0_0_, boarddefin0_.DISP_ON_DUTY_FL as DISP73_0_0_,
boarddefin0_.TRAINING_BOARD_FL as TRAINING74_0_0_ from BOARD_DEFINITION boarddefin0_ where
boarddefin0_.STN=? and boarddefin0_.BOARD_ID=?
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD
3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated Apr 3, 2009 1:57:04 PM by Hibernate Tools 3.2.4.CR1 -->
<hibernate-mapping>
<class name="com.pstechnology.persistence.hibernate.BoardDefinition"
table="BOARD_DEFINITION">
<composite-id name="id"
class="com.pstechnology.persistence.hibernate.BoardDefinitionId">
<key-property name="stn" type="string">
<column name="STN" length="6" />
</key-property>
<key-property name="boardId" type="string">
<column name="BOARD_ID" length="4" />
</key-property>
</composite-id>
<property name="description" type="string">
<column name="DESCRIPTION" length="25"
not-null="true" />
</property>
<property name="boardType" type="java.lang.Character">
<column name="BOARD_TYPE" length="1" />
</property>
<property name="actvFraRptFl"
type="java.lang.Character">
<column name="ACTV_FRA_RPT_FL" length="1" />
</property>
</class>
</hibernate-mapping>
CREATE TABLE BOARD_DEFINITION
(
STN CHAR(6) NOT NULL,
BOARD_ID CHAR(4) NOT NULL,
DESCRIPTION VARCHAR2(25) NOT NULL,
BOARD_TYPE CHAR(1) NULL,
ACTV_FRA_RPT_FL CHAR(1) NULL,
constraint BOARD_DEFINITION_PK primary key (STN, BOARD_ID)
);
Code snippet of the generated POJOs
import java.math.BigDecimal;
import java.util.Date;
/**
* BoardDefinition generated by hbm2java
*/
public class BoardDefinition
implements java.io.Serializable
{
private BoardDefinitionId id;
private String description;
private Character boardType;
private Character actvFraRptFl;
-------
-------
-----
}
/**
* BoardDefinitionId generated by hbm2java
*/
public class BoardDefinitionId
implements java.io.Serializable
{
private String stn;
private String boardId;
public BoardDefinitionId()
{
}
--
This message is automatically generated by JIRA.
-
If you think it was sent incorrectly contact one of the administrators: