problem in saving the foreign key in spring data rest - spring

How to save(POST) the new student in this case
Student.java
#Entity
#Table(name = "student")
public class Student {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "firstname")
private String firstName;
#Column(name = "lastname")
private String lastName;
#Column(name = "email")
private String email;
#ManyToOne(cascade = {CascadeType.DETACH, CascadeType.MERGE, CascadeType.PERSIST,
CascadeType.REFRESH})
#JoinColumn(name = "deptid")
private Department department;
Department.java
#Entity
#Table(name = "department")
public class Department {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "deptname")
private String deptName;
#Column(name = "depthod")
private String deptHOD;
#OneToMany(mappedBy = "department",
fetch = FetchType.LAZY,
cascade = {CascadeType.DETACH, CascadeType.MERGE,
CascadeType.PERSIST, CascadeType.REFRESH})
private List<Student> students;
when tried to save department it's saving but when tried to save the new student it throws an error
(deptid could not be null)
I tried to save like this
{
"firstName" : "ker",
"lastName" : "ope",
"email" : "ker#gmail.com",
"department" : 6
}
Please help me in this case how to save the new student and update the student
*Here the foreign key is deptid in the student table(Entity)

Your property departament is a object not int.
Try select your departament by id and set at student object.
Department department = departmentReṕository.findById(6);
//do validations if ok
student.setDepartment(department);

In your case, you'll have to send whole object of Department with the object of student in your Request body.
Something like below!
{
"firstName" : "ker",
"lastName" : "ope",
"email" : "ker#gmail.com",
"department" : {
"id" : 6,
"deptName" : "dept1",
"deptHOD" : "hod1"
}
}

Related

JPA onetomany mapping showing nested data many times

I have two table user(id,name) and user_mails(id,email,user_id) user to user_mails have one to many relation.
I have created following entity in spring boot
User
#Entity
#Table(name = "user")
public class User {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(name = "id")
private int id;
#Column(name = "name", nullable = false)
private String name;
#OneToMany(mappedBy = "user", cascade = CascadeType.ALL)
private Set<UserMail> userMails =new HashSet<UserMail>(0);
//Getter setter and constructor
}
UserMail
#Entity
#Table(name = "user_mails")
public class UserMail {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private int id;
#Column(name = "email", nullable = false)
private String name;
#ManyToOne(fetch = FetchType.LAZY, optional = false)
#JoinColumn(name = "user_id")
private User user;
It is showing following output on calling controller
[{"id":1,"name":"Ram","userMails":[{"id":2,"name":"ram#b.com","user":{"id":1,"name":"Ram","userMails":[{"id":2,"name":"ram#b.com","user":{"id":1,"name":"Ram","userMails":[{"id":2,"name":"ram#b.com","user":{"id":1,"name":"Ram","userMails":[{"id":2,"name":"ram#b.com","user":{"id":1,"name":"Ram","userMails":[{"id":2,"name":"ram#b.com","user":{"id":1,"name":"Ram","userMails":[{"id":2,"name":"ram#b.com","user":{"id":1,"name":"Ram","userMails":
and more
I want to access all users with all mail ids also want to acces mail id with user details
What changes should I do to get proper result

JPA, Simple One-To-Many Relationship Fetching Problem

Simple Fetch Problem I'm facing in a straight-forward OneToMany Relationship: One Author Many Books.
Here's Author :
#Entity
#Table(name = "authors")
public class AuthorEntity {
#Id
#GeneratedValue
private UUID id;
#Column(name = "first_name")
private String firstName;
#Column(name = "last_name")
private String lastName;
#OneToMany(
mappedBy = "author",
orphanRemoval = true,
fetch = FetchType.EAGER
)
private List<BookEntity> books; // Getters and Setters
}
Here's Book:
#Entity
#Table(name = "books")
public class BookEntity {
#Id
#Column(name = "id")
#GeneratedValue
private UUID id;
#Column(name = "title")
private String title;
#ManyToOne(optional = false)
#JoinColumn(
name = "author_id",
referencedColumnName = "id"
)
private AuthorEntity author;
// Getters and Setters
}
I saved an author and a book through their respective repositories and I checked everything is fine, and here's my query to fetch the author :
SELECT a FROM AuthorEntity a JOIN a.books WHERE a.id = :authorId
Now when I try to access author.getBooks() it says it is null, why doesn't it fetch ? Why do I always have to fetch the books separately ? What's the right query ?

JPA - How to update child object in OneToMany relationship?

I have a Customer class where each customer can have multiple Products. The class is as follow:
#Entity
#Table(name = "customer")
public class Customer {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private Long id;
#Column(name = "firstName")
private String firstName;
#Column(name = "lastName")
private String lastName;
#OneToMany(targetEntity=Product.class, mappedBy = "customer", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
#PrimaryKeyJoinColumn
#JsonManagedReference
private List<Product> products = new ArrayList<>();
//getters and setters here
}
and the Product class holds OneToOne relation with other Classes and it is as follows:
#Entity
#Table(name = "product")
public class Product {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
#ManyToOne(targetEntity=Customer.class, fetch = FetchType.LAZY)
#JoinColumn(name = "customer_id")
#JsonBackReference
private Customer customer;
#OneToOne(mappedBy = "product", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
#PrimaryKeyJoinColumn
#JsonManagedReference
private SomeType1 someType1;
#OneToOne(mappedBy = "product", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
#PrimaryKeyJoinColumn
#JsonManagedReference
private SomeType2 someType2;
#OneToOne(mappedBy = "product", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
#PrimaryKeyJoinColumn
#JsonManagedReference
private SomeType3 someType3;
#OneToOne(mappedBy = "product", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
#PrimaryKeyJoinColumn
#JsonManagedReference
private SomeType4 someType4;
//getters and setters here
}
I am trying to achieve following functionality with this:
Given Customer ID and Product ID, update the values in SomeType1, SomeType2, SomeType3 classes. I am getting the updated SomeType1, SomeType2, SomeType3 objects from UI and I want to update the values in DB. I already have PUT method in place for this.
Here's the PUT method:
#PutMapping(value = "customer/{id}/product/{product_id}")
#ResponseBody
public ResponseEntity<Product> updateProduct(#PathVariable final String id,
#PathVariable final String product_id, #RequestBody final Product product) {
Optional<Customer> customerInDb = customerService.getCustomerById(id);
if (!customerInDb.isPresent()) {
throw new ResponseStatusException(HttpStatus.NOT_FOUND,
MessageFormat.format("Customer with id {0} does not exist.", id));
} else {
product.setId(Long.valueOf(product_id));
product.setCustomer(customerInDb.get());
Product savedProduct = customerService.createProduct(product);
return ResponseEntity.ok(savedProduct);
}
}
I am getting following error for this REST call:
javax.persistence.EntityExistsException: A different object with the same identifier value was already associated with the session : [com.myapp.arg.entities.SomeType2#12]
What could be the reason for this?
createProduct method:
#Override
public Product createProduct(Product product) {
Product savedProduct = productRepository.save(product);
return savedProduct;
}
JSON input to the PUT method:
{
"id":9,
"someType1":{
"id":9,
"avg":20,
"total":20
},
"someType2":{
"id":9,
"circum":45.0,
"strength":45.0,
"totalNav":0.0
},
"someType3":{
"id":9,
"tensile":87,
"pull":128,
"push":56,
"upward":28.0
},
"measuredBy":"SJ",
"addedDate":"2021-05-23",
"type":"Prime"
}
you are using the same id for all of your entities. ID must be unique

Spring data JPA populate data of 2 One-To-Many relationship

I have a ManyToMany relationship that is broken down into 2 OneToMany relation. A Book can belong to multiple Categories and a Category can have many Books.
When I query for Book, the categories list just get empty. How can I get a list of all Categories that a Book belong to ? Am I missing something ?
#Entity
public class Book {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Integer id;
#NotBlank(message = "Please input book title")
private String title;
private Integer publishYear;
private String publisher;
private String language;
private Integer numberOfPages;
private String avatarUrl;
#OneToMany(targetEntity = BookCategory.class, cascade = CascadeType.ALL)
#JoinColumn(name = "category", nullable = false, insertable = false, updatable = false)
private Set<BookCategory> categories = new LinkedHashSet<>();
}
#Entity
public class Category {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Integer id;
#Column(nullable = false)
#NotBlank(message = "Please input category name")
private String name;
}
#Entity
public class BookCategory {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Integer id;
#ManyToOne
#JoinColumn(name = "book", nullable = false)
private Book book;
#ManyToOne
#JoinColumn(name = "category", nullable = false)
private Category category;
}
Try using mappedBy attribute with #OneTOMany annotation on the 'One' side of the OneToMany relation.
Or you can also try using the following:
#ManyToMany
#JoinTable(
name = “book”_category,
joinColumns = #JoinColumn(name = “book_id”),
inverseJoinColumns = #JoinColumn(name = “category_id))
Read more:
https://vladmihalcea.com/the-best-way-to-use-the-manytomany-annotation-with-jpa-and-hibernate/

SQL error or missing database / OneToMany SQLIte-Spring Boot

I have a problem with the relationship oneToMany. I created tables in SQLite DB, this is my tables:
My CategoryModel:
#Entity
#Table(name = "Category")
#JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
public class CategoryModel {
#Id
#Column(name = "id")
#GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String category_name;
private String category_description;
private String image_path;
#JsonIgnore
#OneToMany( mappedBy = "category")
private Set<ProductModel> category;
My ProducCategory:
#Entity
#Table(name = "Product_Category")
#JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
public class ProductModel {
#Id
#Column(name = "id")
#GeneratedValue(strategy = GenerationType.AUTO)
private Long product_id;
private Long category_id;
private String name;
private String description;
private int numberOfProduct;
private String image;
private int price;
#ManyToOne
#JoinColumn(name = "country_id", nullable = false)
private CategoryModel category;
I can get data from the Category table well but when I call data from the Product_Category table I have the error:
SQL error or missing database (no such column: productmod0_.country_id)
country_id does not exist anywhere in your tables.
What you want is : #JoinColumn(name = "category_id", nullable = false)

Resources