1

Hallo all. I have this set of classes:

@Entity
@Table(name = "S_MC_CC_RAPPORTI")
@Inheritance(strategy=InheritanceType.JOINED)
@DiscriminatorColumn(name="COD_TIPORAPPORTO",
                     discriminatorType=DiscriminatorType.CHAR, length=1)
public abstract class Rapporto implements Serializable {

  private static final long serialVersionUID = -5567166522882040440L;
 
  @Id
  @Column(name = "COD_RAPPORTO")  
  protected Long codiceRapporto;

And this sublass:

@Entity
@Table(name="S_MC_CC_CCCLIENTI")
@DiscriminatorValue("1 ")
public class ContoCorrente extends Rapporto {
  private static final long serialVersionUID = -3380622649760983262L;

  @Column(name = "DESC_DIVISA")
  private String divisa;

The problem is on the discriminator value: on the table the column is CHAR(2).

When I make the getItemById on the subclass all works fine: this is the generated eclipselink sql: (I replaced the column definition with * for easy to read)

[EL Fine]: 2011-01-16 16:01:14.531--ServerSession(5230193)--Connection(11601738)--Thread(Thread[main,5,main])--  SELECT * FROM S_MC_CC_RAPPORTI t0, S_MC_CC_CCCLIENTI t1 WHERE ((t0.COD_RAPPORTO = ?) AND ((t1.COD_RAPPORTO = t0.COD_RAPPORTO) AND (t0.COD_TIPORAPPORTO = ?)))
 bind => [1120676, 1 ]

If I change the @DiscriminatorValue("1") removing the space the data is not found: this is the relative generated sql

[EL Fine]: 2011-01-16 16:03:46.671--ServerSession(5230193)--Connection(11601738)--Thread(Thread[main,5,main])--SELECT * FROM S_MC_CC_RAPPORTI t0, S_MC_CC_CCCLIENTI t1 WHERE ((t0.COD_RAPPORTO = ?) AND ((t1.COD_RAPPORTO = t0.COD_RAPPORTO) AND (t0.COD_TIPORAPPORTO = ?)))
 bind => [1120676, 1]

Note that the two queries work fine with TOAD: both the t0.COD_TIPORAPPORTO = '1 ' one, even the t0.COD_TIPORAPPORTO = '1'.

OK: so I think that the @DiscriminatorValue("1 ") is correct.

Now I make an association many-to-many with the super class Rapporto as described here

If I mantain the @DiscriminatorValue("1 ") I get

[EL Warning]: 2011-01-16 16:09:33.421--ServerSession(29839159)--Thread(Thread[main,5,main])--Exception [EclipseLink-43] (Eclipse Persistence Services - 2.1.2.v20101206-r8635): org.eclipse.persistence.exceptions.DescriptorException
Exception Description: Missing class for indicator field value [1] of type [class java.lang.String].
Descriptor: RelationalDescriptor(it.alten.intesasanpaolo.contratto.domain.core.rapporto.Rapporto --> [DatabaseTable(S_MC_CC_RAPPORTI)])

If I change the @DiscriminatorValue("1") removing the space all work fine but I receive no data (even If the data is present on DB).

I dunno what to do.... Any idea?

Kind regards

Massimo

Community
  • 1
  • 1
Massimo Ugues
  • 4,373
  • 8
  • 43
  • 56
  • Have you tried DiscriminatorType.STRING? String "1 " not equals "1" for sure. If eclipselink thinks otherwise, there must be some trimming options in eclipselink configuration i believe. Other options are using table views or @NamedNativeQuery instead of @Table. – andbi Jan 17 '11 at 10:30

2 Answers2

2

It appears that the values in your database contain a trailing space. I'd suggest to run a query against the table and remove the trailing whitespace. Then have the discriminator value be "1" (no space)

In fact, if you are going to use numbers anyway, you should use DiscriminatorType.INTEGER

Bozho
  • 588,226
  • 146
  • 1,060
  • 1,140
  • The column table is defined as CHAR(2). I tried to remove it but is not like a varchar, so in effect I don't think this is possible. I need to say to JPA to make a TRIM when it handle that column. Do you think is possible? Kind regards – Massimo Ugues Jan 16 '11 at 15:34
  • can't you change it to varchar? Or perhaps - get the values out, delete the column completely, and create a new column, inserting the values. The new column better be of a numeric type. – Bozho Jan 16 '11 at 15:37
  • What a pity, I cannot. I have a legacy database with 5 millions of record; is a not admitted operation. – Massimo Ugues Jan 16 '11 at 16:01
  • I tried to change the column type in Number, and now all work fine. So the problem is really the column definition (Char(2)). I cannot change the column type: any idea? I need to make a trim on that column. – Massimo Ugues Jan 17 '11 at 09:53
2

Your database seems to have an issue with char comparison with spaces when using binding. What database are you using?

There are several possible solutions, first I would check with your JDBC driver to see if it has any fixes or options to solve this.

One option is to set "eclipselink.jdbc.bind-parameters"="false" in your persistence.xml, this should resolve the issue.

Another solution is to disable char trimming in EclipseLink, (this one does not seem to be exposed to JPA persistence properties (please log a bug), so you need to use a SessionCustomizer to set it) session.getLogin().setShouldTrimStrings(false);

A more involved solution is to use a DescriptorCustomizer to set your own ClassExtractor on the descriptor to use you own code to determine the class.

If you can change the data, then I would recommend just updating any '1 ' to '01' then you can just use '01' as the indicator.

James
  • 17,965
  • 11
  • 91
  • 146
  • Oracle 10g. I'm using jdbc oracle driver 10.2. I tried the eclipselink.jdbc.bind-parameters"="false" and now it works. ;) Great. I will try also the others solutions. Kind regards. Massimo – Massimo Ugues Jan 17 '11 at 21:46
  • _Another solution is to disable char trimming in EclipseLink, (this one does not seem to be exposed to JPA persistence properties (please log a bug), so you need to use a SessionCustomizer to set it) session.getLogin().setShouldTrimStrings(false);_ I tried this way and I wrote my SessionCustomizer: now how must I configure it in myu application? Kind regards. Massimo – Massimo Ugues Feb 03 '11 at 20:42