Skip to content

OneToOne mapping is not projected #2369

Open
@joheb-mohemian

Description

@joheb-mohemian

Hi,

I've set up an example project here that showcases what seems to be a bug in Spring Data projections: https://github.com/joheb-mohemian/gs-accessing-data-jpa/tree/primary-key-join-column-projection-bug/complete

I have a Customer entity that has a OneToOne mapping to an Address entity:

@Entity
public class Customer {

	@Id
	@GeneratedValue(strategy=GenerationType.AUTO)
	private Long id;
	private String firstName;
	private String lastName;

	@OneToOne(mappedBy = "customer", cascade = CascadeType.ALL)
	@PrimaryKeyJoinColumn
	private Address address;

//...
}
@Entity
public class Address {

	@Id
	@Column(name = "customer_id")
	private Long id;

	@OneToOne
	@MapsId
	@JoinColumn(name = "customer_id")
	private Customer customer;

	private String street;
//...
}

Then there are simple projection interfaces:

public interface CustomerProjection {

	String getFirstName();

	String getLastName();

	AddressProjection getAddress();
}
public interface AddressProjection {

    String getStreet();
}

But when I try to fetch a projected entity from a repository method like this one:

public interface CustomerRepository extends CrudRepository<Customer, Long> {
        //...
	<T> T findById(long id, Class<T> type);
}

, getAddress() on the projection will be null, whereas getAddress() when fetching the entity type is populated correctly. Of these two unit tests, only testEntityWithOneToOne()will be successful:

        @BeforeEach
	void setUpData() {
		customer = new Customer("first", "last");
		Address address = new Address(customer, "street");
		customer.setAddress(address);
		entityManager.persist(address);
		entityManager.persist(customer);
	}

	@Test
	void testEntityWithOneToOne() {
		Customer customerEntity = customers.findById(customer.getId().longValue());
		assertThat(customerEntity.getAddress()).isNotNull();
	}

	@Test
	void testProjectionWithOneToOne() {
		CustomerProjection customerProjection = customers.findById(customer.getId(), CustomerProjection.class);
		assertThat(customerProjection.getAddress()).isNotNull();
	}

What's the problem here? Thanks for looking into it.

Metadata

Metadata

Assignees

No one assigned

    Labels

    status: blockedAn issue that's blocked on an external project change

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions