Skip to content

Commit 11b2512

Browse files
committed
Convert Iterable<ID> to Collection<ID> for deleteAllByIdInBatch.
Even though Spring Data Commons has deleteAllById(Iterable<ID>), some JPA providers require a Collection<ID> instead. So we need to convert if the incoming argument isn't already. See #2242.
1 parent 5166c0d commit 11b2512

File tree

3 files changed

+58
-9
lines changed

3 files changed

+58
-9
lines changed

spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/SimpleJpaRepository.java

+12-1
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,8 @@
3838
import java.util.Map;
3939
import java.util.Optional;
4040
import java.util.function.Function;
41+
import java.util.stream.Collectors;
42+
import java.util.stream.StreamSupport;
4143

4244
import org.springframework.dao.EmptyResultDataAccessException;
4345
import org.springframework.data.domain.Example;
@@ -223,7 +225,16 @@ public void deleteAllByIdInBatch(Iterable<ID> ids) {
223225
entityInformation.getIdAttribute().getName());
224226

225227
Query query = em.createQuery(queryString);
226-
query.setParameter("ids", ids);
228+
/**
229+
* Some JPA providers require {@code ids} to be a {@link Collection} so we must convert if it's not already.
230+
*/
231+
if (Collection.class.isInstance(ids)) {
232+
query.setParameter("ids", ids);
233+
} else {
234+
Collection<ID> idsCollection = StreamSupport.stream(ids.spliterator(), false)
235+
.collect(Collectors.toCollection(ArrayList::new));
236+
query.setParameter("ids", idsCollection);
237+
}
227238

228239
query.executeUpdate();
229240
}

spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/support/EclipseLinkJpaRepositoryTests.java

+8-4
Original file line numberDiff line numberDiff line change
@@ -27,10 +27,14 @@
2727
class EclipseLinkJpaRepositoryTests extends JpaRepositoryTests {
2828

2929
@Override
30-
/**
31-
* Ignored until https://bugs.eclipse.org/bugs/show_bug.cgi?id=349477 is resolved.
32-
*/
30+
@Disabled("https://bugs.eclipse.org/bugs/show_bug.cgi?id=349477")
3331
void deleteAllByIdInBatch() {
34-
super.deleteAllByIdInBatch();
32+
// disabled
33+
}
34+
35+
@Override
36+
@Disabled("https://bugs.eclipse.org/bugs/show_bug.cgi?id=349477")
37+
void deleteAllByIdInBatchShouldConvertAnIterableToACollection() {
38+
// disabled
3539
}
3640
}

spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/support/JpaRepositoryTests.java

+38-4
Original file line numberDiff line numberDiff line change
@@ -17,16 +17,18 @@
1717

1818
import static org.assertj.core.api.Assertions.*;
1919

20-
import java.util.Arrays;
21-
import java.util.Optional;
22-
2320
import jakarta.persistence.EntityManager;
2421
import jakarta.persistence.PersistenceContext;
2522

23+
import java.util.Arrays;
24+
import java.util.Iterator;
25+
import java.util.List;
26+
import java.util.Optional;
27+
28+
import org.jetbrains.annotations.NotNull;
2629
import org.junit.jupiter.api.BeforeEach;
2730
import org.junit.jupiter.api.Test;
2831
import org.junit.jupiter.api.extension.ExtendWith;
29-
3032
import org.springframework.data.jpa.domain.sample.PersistableWithIdClass;
3133
import org.springframework.data.jpa.domain.sample.PersistableWithIdClassPK;
3234
import org.springframework.data.jpa.domain.sample.SampleEntity;
@@ -128,6 +130,38 @@ void deleteAllByIdInBatch() {
128130
assertThat(repository.findAll()).containsExactly(two);
129131
}
130132

133+
@Test // GH-2242
134+
void deleteAllByIdInBatchShouldConvertAnIterableToACollection() {
135+
136+
SampleEntity one = new SampleEntity("one", "eins");
137+
SampleEntity two = new SampleEntity("two", "zwei");
138+
SampleEntity three = new SampleEntity("three", "drei");
139+
repository.saveAll(Arrays.asList(one, two, three));
140+
repository.flush();
141+
142+
// List<SampleEntityPK> ids = Arrays.asList(new SampleEntityPK("one", "eins"),
143+
// new SampleEntityPK("three", "drei"));
144+
145+
Iterable<SampleEntityPK> ids = new Iterable<SampleEntityPK>() {
146+
147+
/**
148+
* Wrap a {@link List} inside an {@link Iterable} to verify that {@link SimpleJpaRepository} can properly
149+
* convert a pure {@link Iterable} to a {@link Collection}.
150+
**/
151+
private List<SampleEntityPK> ids = Arrays.asList(new SampleEntityPK("one", "eins"),
152+
new SampleEntityPK("three", "drei"));
153+
154+
@NotNull
155+
@Override
156+
public Iterator<SampleEntityPK> iterator() {
157+
return ids.iterator();
158+
}
159+
};
160+
161+
repository.deleteAllByIdInBatch(ids);
162+
assertThat(repository.findAll()).containsExactly(two);
163+
}
164+
131165
private interface SampleEntityRepository extends JpaRepository<SampleEntity, SampleEntityPK> {
132166

133167
}

0 commit comments

Comments
 (0)