Spring CrudRepository findByInventoryIds (List <Long> InventIdList) - equivalente alla clausola IN


169

In Spring CrudRepository, abbiamo il supporto per "clausola IN" per un campo? cioè qualcosa di simile al seguente?

 findByInventoryIds(List<Long> inventoryIdList) 

Se tale supporto non è disponibile, quali opzioni eleganti possono essere prese in considerazione? Le query di attivazione per ciascun ID potrebbero non essere ottimali.

Risposte:


283

findByInventoryIdIn(List<Long> inventoryIdList) dovrebbe fare il trucco.

Il formato del parametro di richiesta HTTP sarebbe così:

Yes ?id=1,2,3
No  ?id=1&id=2&id=3

L'elenco completo delle parole chiave del repository JPA è disponibile nell'elenco di documentazione corrente . Mostra che IsInè equivalente - se preferisci il verbo per leggibilità - e che JPA supporta anche NotIne IsNotIn.


Grazie, era esattamente quello che stavo cercando. Lo hanno documentato nella pagina CrudRepository o lo scoprono leggendo il codice?
Espresso

1
In realtà è elencato nella documentazione di riferimento .
Oliver Drotbohm,

Grazie. Quel "gioiello è nascosto nell'appendice B", giustamente :)
Espresso,

11
URL dei documenti di riferimento modificato
Mayjak

1
Per la firma del metodo: List <Person> findByIdIn (List <Integer> ids); Ottengo l'errore: causato da: java.lang.NumberFormatException: per stringa di input: "(1, 2)"
user64141

103

Per qualsiasi metodo in un Spring CrudRepository dovresti essere in grado di specificare tu stesso @Query. Qualcosa del genere dovrebbe funzionare:

@Query( "select o from MyObject o where inventoryId in :ids" )
List<MyObject> findByInventoryIds(@Param("ids") List<Long> inventoryIdList);

Grazie, funziona. Stavo cercando una soluzione "più pulita", ovvero senza scrivere @Query.
Espresso

3
Oliver Gierke è l'uomo che avrebbe saputo la risposta a questo e ha la soluzione "più pulita". Dovresti accettare la sua risposta.
digitaljoel,

1
Grande! Ho usato un Set<String>parametro, ha funzionato bene.
BlueBird,

cosa succede se voglio passare 2 parametri al mio metodo un elenco e l'altro una stringa normale, funzionerà? in caso
affermativo,

22

Sì, è supportato.

Controlla la documentazione fornita qui per le parole chiave supportate all'interno dei nomi dei metodi.

È possibile semplicemente definire il metodo nell'interfaccia del repository senza utilizzare l' annotazione @Query e scrivere la query personalizzata. Nel tuo caso sarebbe come segue:

List<Inventory> findByIdIn(List<Long> ids);

Presumo che tu abbia l' entità Inventory e l' interfaccia InventoryRepository . Il codice nel tuo caso dovrebbe essere simile al seguente:

L'entità

@Entity
public class Inventory implements Serializable {

  private static final long serialVersionUID = 1L;

  private Long id;

  // other fields
  // getters/setters

}

Il repository

@Repository
@Transactional
public interface InventoryRepository extends PagingAndSortingRepository<Inventory, Long> {

  List<Inventory> findByIdIn(List<Long> ids);

}

Funziona con tutte le interfacce che stanno estendendo l' interfaccia CrudRepository .
Dzinot,

1
Questo non funzionerà se la dimensione degli ID è superiore a 1000 o determinate dimensioni a seconda del DB. Cosa ne pensi di questo? Elenco <Inventory> findByIdIn (Elenco <Long> ID, paginabile pagable);
Julie
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.