Announcement Announcement Module
Collapse
No announcement yet.
CrudRepository Samples for Compound Key Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • CrudRepository Samples for Compound Key

    Hello, does anyone have any samples they can share with having a CrudRepository derived repository modelling a table with a compound key?

    I am trying to model a table with three fields that make the compound key and save data as part of a JUnit test.

    I'm encountering issues on trying to use the "save" method. The test doesn't fail, but the output shows Hibernate using a "select" rather an perform an "insert" operation.


    Consider the following:


    :: DB ::

    Member
    + user_id (PK)
    + role_id (PK)
    + job_id (PK)
    + member_status

    :: Java ::
    Code:
    @Embeddable
    public class MemberKey implements Serializable  {
    	
    	private static final long serialVersionUID = 3702768837501941651L;
    	
    	@Column(name = "user_id", nullable = false)
    	private Long userId;
    	
    	@Column(name = "role_id", nullable = false)
    	private Long roleId;
    	
    	@Column(name = "job_id", nullable = false)
    	private Long jobId;
    
    	// cut
    }
    
    
    @Entity
    public class Member implements Serializable {
    
    	@EmbeddedId
    	private MemberKey memberKey;
    
    	@Column(name = "member_status", nullable = false)
    	private String memberStatus;
    	
    	// cut
    }
    
    public interface MemberRepository extends CrudRepository<Member, MemberKey> {
    	
    }
    
    @RunWith(SpringJUnit4ClassRunner.class)
    @ContextConfiguration(locations = "classpath:application-context.xml")
    @Transactional
    public class MemberRepositoryTest  {
    	
    	private Member member;
    	
    	@Autowired
    	private MemberRepository memberRepository;
    	
    	@Before
    	public void setUp() {
    		member = new Member();
    		MemberKey memberKey = new MemberKey();
    		memberKey.setUserId(1L);
    		memberKey.setRoleId(1L);
    		memberKey.setJobId(1L);
    		member.setMemberKey(memberKey);
    		member.setMemberStatus("foo");
    	}
    	
    	@Test
    	public void saveMemberRepository() {
    		Member newMember = memberRepository.save(member);
    		assertTrue("There must be a new member now", newMember!= null);
    	}
    
    }
    :: Config ::

    Spring 3.1.0.RELEASE
    Spring Data 1.1.0.RELEASE
    Hibernate 4.1.4.Final
    Hibernate JPA 1.0.1.Final
    MySQL 5.1.20

    :: JUnit Output ::

    INFO : org.springframework.test.context.transaction.Trans actionalTestExecutionListener - Began transaction (1): transaction manager [org.springframework.orm.jpa.JpaTransactionManager@ fdc252]; rollback [true]

    Hibernate: select member0_.job_id as job1_3_0_, member0_.role_id as role2_3_0_, member0_.user_id as user3_3_0_, member0_.member_status as member7_3_0_, from member member0_ where member0_.job_id=? and member0_.role_id=? and member0_.user_id=?



    Is there an issue w/ the annotations I have setup on the @Entity class? Are there any conflicts w/ using CrudRepository for a table w/ a compound key? I've used similar JUnit tests to verify my usage of the "save" method of the CrudRepository interface w/ a simple numeric key and it works as expected.


    Any input would be greatly appreciated!

  • #2
    If someone can even just confirm that they've created a CrudRepository successfully with a compound key, that would be greatly helpful. That way I can ensure it is something in my code rather than a limitation of the CrudRepository interface.

    Haven't found much documentation around this nor other posts with similar issues.

    Any input would be greatly appreciated.


    Thx!

    Comment


    • #3
      Hi thushan,

      I observed this behaviour also on entities w/ a single PK field:

      Code:
      [INFO] TransactionalTestExecutionListener - Began transaction (4): transaction manager [org.springframework.orm.jpa.JpaTransactionManager@106c6be]; rollback [true]
      [TRACE] SQL - <t 11251596, conn 22669023> executing prepstmnt 26122975 SELECT t0.geburtsdatum, t0.geschlecht, t0.nachname, t0.id, t0.hausnr, t0.ort, t0.plz, t0.strasse, t0.email, t0.fax, t0.telefon, t0.vorname FROM PR.TJF9040N t0 WHERE t0.id = ? [params=?]
      [TRACE] SQL - <t 11251596, conn 22669023> [0 ms] spent
      [TRACE] SQL - <t 11251596, conn 22669023> executing prepstmnt 15801826 INSERT INTO PR.TJF9010N (id, name, email, fax, telefon, hausnr, ort, plz, strasse) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?) [params=?, ?, ?, ?, ?, ?, ?, ?, ?]
      [TRACE] SQL - <t 11251596, conn 22669023> [0 ms] spent
      [TRACE] SQL - <t 11251596, conn 22669023> executing prepstmnt 3720195 INSERT INTO PR.TJF9030N (id, abteilung, typ, userId, FIRMA_ID, email, fax, telefon, PERSON_ID) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?) [params=?, ?, ?, ?, ?, ?, ?, ?, ?]
      [TRACE] SQL - <t 11251596, conn 22669023> [0 ms] spent
      [TRACE] SQL - <t 11251596, conn 22669023> executing prepstmnt 16145243 INSERT INTO PR.TJF9040N (id, geburtsdatum, geschlecht, nachname, vorname, hausnr, ort, plz, strasse, email, fax, telefon) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?) [params=?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?]
      [TRACE] SQL - <t 11251596, conn 22669023> [0 ms] spent
      [TRACE] SQL - <t 11251596, conn 22669023> executing prepstmnt 27790938 INSERT INTO PR.TJF9020N (id, name, hausnr, ort, plz, strasse, FIRMA_ID, email, fax, telefon) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?) [params=?, ?, ?, ?, ?, ?, ?, ?, ?, ?]
      [TRACE] SQL - <t 11251596, conn 22669023> [0 ms] spent
      If you have a look at SimpleJpaRepository#save ...

      Code:
      	@Transactional
      	public <S extends T> S save(S entity) {
      
      		if (entityInformation.isNew(entity)) {
      			em.persist(entity);
      			return entity;
      		} else {
      			return em.merge(entity);
      		}
      	}
      ... you will see that depending on some "new" state persist() or merge() is called on the entity manager.

      I had no time for further investigation. I'm using Spring Data JPA 1.1.0-RELEASE and OpenJPA 2.2.0.

      HTH
      Tobias

      Comment

      Working...
      X