0
votes

I get the following error whenever I try to persist a child objects to a existing father object in JPA:

Caused by: javax.validation.ConstraintViolationException: Validation failed for classes [store.entidades.Sucursal] during persist time for groups [javax.validation.groups.Default, ] List of constraint violations:[ ConstraintViolationImpl{interpolatedMessage='Por favor ingrese un valor en direccion', propertyPath=direccion, rootBeanClass=class store.entidades.Sucursal, messageTemplate='Por favor ingrese un valor en direccion'} ConstraintViolationImpl{interpolatedMessage='Por favor ingrese un valor en telefono', propertyPath=telefono, rootBeanClass=class store.entidades.Sucursal, messageTemplate='Por favor ingrese un valor en telefono'} ]

This is the parent entity class that Im using:

    @Entity
    public class Sucursal {

        @Id
        @GeneratedValue(strategy = GenerationType.AUTO)
        private int id;

        // nombre del encargado de esa sucursal
        private String subgerente;

        @NotNull(message = "Por favor ingrese un valor en direccion")
        @Column(length = 120)
        private String direccion;

        @NotNull(message = "Por favor ingrese un valor en telefono")
        @Column(length = 36, unique = true)
        private String telefono;

        @OneToMany(cascade = CascadeType.MERGE, fetch = FetchType.EAGER, orphanRemoval = true)
        @JoinColumn(name = "producto_sucursal", referencedColumnName = "id")
        private List<Producto> producto = new ArrayList<Producto>();

        //getters and setters

This is the child entity class that Im using:

 @Entity
    public class Producto {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private int id;

    @NotNull(message = "Por favor ingrese un valor")
    private String nombre;

    @NotNull(message = "Por favor ingrese un valor")
    @Column(length = 140)
    private String descripcion;

    @NotNull(message = "Por favor ingrese un valor")
    private double precio;

    @NotNull(message = "Por favor ingrese un valor")
    private String imagen1;
    @NotNull(message = "Por favor ingrese un valor")
    private String imagen2;
    @NotNull(message = "Por favor ingrese un valor")
    private String imagen3;

    private int megusta;
    private int nomegusta;

    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, orphanRemoval = true)
    @JoinColumn(name = "comentario_producto", referencedColumnName = "id")
    private List<Comentario> comentario = new ArrayList<Comentario>();//

    @ManyToOne(cascade = CascadeType.MERGE, fetch = FetchType.EAGER)
    @JoinColumn(name = "producto_subcategoria")
    private Subcategoria subcategoria = new Subcategoria();

    @ManyToOne(cascade = CascadeType.MERGE, fetch = FetchType.EAGER)
    @JoinColumn(name = "producto_categoria")
    private Categoria categoria = new Categoria();

    @ManyToOne(cascade = CascadeType.MERGE, fetch = FetchType.EAGER)
    @JoinColumn(name = "producto_sucursal")
    private Sucursal sucursal = new Sucursal();

    //getters and setters

My DAO class for Sucursal looks like this:

@Stateless
public class SucursalDAO implements Serializable {

    @Inject
    private EntityManager entityManager;

    public void save(Sucursal sucursal) {
        if (entityManager.find(Sucursal.class, sucursal.getId()) == null) {
            insertar(sucursal);

        } else {
            update(sucursal);
        }
    }

    // ...
}

Whenever I click on a save button in front end it calls this method:

public void guardar() {

    System.out.println(newSucursal.getDireccion());
    System.out.println(newSucursal.getTelefono());

    for (int i = 0; i < listproductos.size(); i++) {

        // listproductos.get(i).setSucursal(newSucursal);
        System.out.println(listproductos.get(i).toString());

        newSucursal.getProductos().add(listproductos.get(i));
    }

    sucursalDAO.save(newSucursal);
}

When I call this save method I add the new child Productos to my Sucursales but when I try to persist the Parent it give me the error I posted above. I have tried many things but cant seem to figure out what the problem is? Is there another way of saving child entities to existing parent entities?

EDIT

This is the code that fixed my problem for my save method:

public void guardar() {

        System.out.println(newSucursal.getDireccion());
        System.out.println(newSucursal.getTelefono());

        for (int i = 0; i < listproductos.size(); i++) {

            listproductos.get(i).setSucursal(newSucursal);

            Categoria cat = new Categoria();
            cat = categoriaDAO.read(listproductos.get(i).getCategoria().getId());
            listproductos.get(i).setCategoria(cat);

            Subcategoria subcat = new Subcategoria();
            subcat = subcategoriaDAO.read(listproductos.get(i).getSubcategoria().getId());
            listproductos.get(i).setSubcategoria(subcat);

            System.out.println(listproductos.get(i).toString());

            newSucursal.getProductos().add(listproductos.get(i));
        }

        // newSucursal.setProductos(listproductos);

        sucursalDAO.save(newSucursal);
    }
1
How could the values be getting emptied if I use my postconstruct to fetch them from the database ? I even printed them out on screen right before I call my save method and they are not nullBryam Ulloa
Your @ViewScoped class and @Entity classes do not implement Serializable.Geinmachi
I added the implements Serializable, still same error.Bryam Ulloa

1 Answers

1
votes

The crux of your problem is that you need to assign both sides of your relationships:

public void guardar() {

    System.out.println(newSucursal.getDireccion());
    System.out.println(newSucursal.getTelefono());

    for (int i = 0; i < listproductos.size(); i++) {

        listproductos.get(i).setSucursal(newSucursal);
        System.out.println(listproductos.get(i).toString());

        newSucursal.getProductos().add(listproductos.get(i));
    }

    sucursalDAO.save(newSucursal);
}

which you have commented out for some reason.

Also, all of your @ManyToOne relationships are initialised with new objects like:

@ManyToOne(cascade = CascadeType.MERGE, fetch = FetchType.EAGER)
@JoinColumn(name = "producto_subcategoria")
private Subcategoria subcategoria = new Subcategoria();

which is asking for trouble because (again) the opposite sides of these relationships are never set.