1
resposta

Duvida Spring data

Estou tentando fazer uma consulta que me retorne somente um item da lista em uma consulta usando uma JPQL, porém até agora não obtive sucesso:

Para contextualizar, eu tenho uma gasto e dentro dele a uma lista de gastosCategorizado, eu quero que quando eu for pesquisar pela categoria do gastoCategorizado so me traga na lista o gastoCategorizado referente aquela Categoria e não todos os GastosCategorizados daquele gasto.

Segue os codigos

Gasto:

@Entity
public class Gasto extends AbstractEntity {

    @NotEmpty(message = "A descrição não pode ser vazia")
    private String descricao;

    @NotNull
    @JsonFormat(pattern = "dd/MM/yyyy")
    @Convert(converter = LocalDateAttributeConverter.class)
    private LocalDate data;

    @Digits(fraction=2,message="O valor só pode conter dois digitos após a virgula",integer = 9)
    @DecimalMin(message = "O Valor não pode ser menor ou igual a 0.00", value = "0.00", inclusive = false)
    private BigDecimal valor;

    @NotEmpty
    @OneToMany(cascade = CascadeType.ALL)
    private List<GastoCategorizado> gastosCategorizados;

    public Gasto(String descricao, LocalDate data, List<GastoCategorizado> gastosCategorizados) {
        this.valor = new BigDecimal("0.00");
        gastosCategorizados.forEach(gastos -> this.valor = this.valor.add(gastos.getValor()));
        this.descricao = descricao;
        this.data = data;
        this.gastosCategorizados = new ArrayList<>(gastosCategorizados);
    }

    public Gasto() {
    }

    public Gasto(Long id, String descricao, LocalDate data, List<GastoCategorizado> gastosCategorizado) {
        this(descricao,data,gastosCategorizado);
        this.id = id;
    }


    getters e setters

GastoCategorizado

@Entity
public class GastoCategorizado extends AbstractEntity {

    @ManyToOne(fetch = FetchType.EAGER)
    private Categoria categoria;

    @Digits(fraction=2,message="O valor so pode conter dois digitos após a virgula",integer = 9)
    @DecimalMin(message = "O Valor não pode ser negativo", value = "0.00", inclusive = false)
    private BigDecimal valor;

    public GastoCategorizado(Categoria categoria, BigDecimal valor) {
        this.categoria = categoria;
        this.valor = valor;
    }

    public GastoCategorizado() {
    }

  getters e setters

GastoRepository

@Repository
@Transactional
public interface GastoRepository extends PagingAndSortingRepository<Gasto, Long> {

    @Query("select g from Gasto g join g.gastosCategorizados gc join gc.categoria c where c = :categoria")
    Page<Gasto> findByCategoria(@Param("categoria") Categoria categoria, Pageable pageable);

    Page<Gasto> findByDataBetween(LocalDate dataInicial, LocalDate dataFinal, Pageable pageable);

Teste Que não passa

 public void deveTrazerGastosPelaCategoria() {
        List<GastoCategorizado> gastosCategorizados = new ArrayList<>();

        Categoria carro = new Categoria(1L,"Carro");

        Categoria moto = new Categoria(2L,"Moto");

        this.categoriaRepository.save(carro);

        this.categoriaRepository.save(moto);

        gastosCategorizados.add(new GastoCategorizado(carro, new BigDecimal("32.50")));

        gastosCategorizados.add(new GastoCategorizado(moto, new BigDecimal("11.50")));

        Gasto gasto = new Gasto("Gasolina", LocalDate.now(), gastosCategorizados);

        this.gastoRepository.save(gasto);

        List<Gasto> gastos = gastoRepository.findByCategoria(carro, null).getContent();

        assertThat(gastos.get(0).getGastosCategorizados().size()).isEqualTo(1);
        assertTrue(gastos.get(0).getValor().equals(new BigDecimal("44.00")));
        assertTrue(gastos.get(0).getGastosCategorizados().get(0).getValor().equals(new BigDecimal("32.50")));

    }
1 resposta

Realmente não vi nada errado no seu código.. aquele join não é necessário, basta que você navegue pela relação, chegando no gastoCategorizado.