I have two table Movie and Actor
#Entity
#Table(name="movie")
#Data
public class Movie {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(nullable = false, unique = true)
private Integer MovieId;
......
#ManyToOne(fetch = FetchType.LAZY, cascade = CascadeType.ALL)
#JoinColumn(name = "actorId", referencedColumnName = "actorId")
private Actor actor;
}
#Entity
#Table(name = "actor")
#Data
public class Actor {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(nullable = false, unique = true)
private Integer actorId;
private String firstName;
private String lastName;
#OneToMany(mappedBy = "actor", cascade = CascadeType.ALL, fetch = FetchType.LAZY)
private List<Movie> actorMovies = new ArrayList<>();
}
Now in MySql database i have two table but I need transiet table movie_actor. Now I have Movie table and column actorId and insert only one id. I want to have relation that One Movie have many Actors.
Related
I have 3 tables as #Entity, and 2 join tables in my spring + hibernate app.
In one of join table i have extra column. I want to take info from this info column when i take info from my main table.
Main table code:
#Entity
#Table(name = "items")
public class Items {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "name")
private String name;
#ManyToMany(fetch = FetchType.EAGER)
#JoinTable(name = "crafts"
,joinColumns = #JoinColumn(name = "item_id")
,inverseJoinColumns = #JoinColumn(name = "plot_id"))
private Set<Plots> plotInfo = new HashSet<>();
#ManyToMany(fetch = FetchType.EAGER)
#JoinTable(name = "item_materials"
,joinColumns = #JoinColumn(name = "item_id")
,inverseJoinColumns = #JoinColumn(name = "material_id"))
private Set<Materials> materialsInfo = new HashSet<>();
Table item_materials have this columns "id, item_id(fkey), material_id(fkey), expense" and one of this which names as "expense" i need to have in my final result.
How can i code my class to have "expense" in my result?
I read about #embeddable but still dont understand how to use in my project.
Don't use a #ManyToMany association. Map the join table as entity and model it similar to this:
#Entity
#Table(name = "items")
public class Items {
#OneToMany(mappedBy = "item")
private Set<Crafts> plotInfo = new HashSet<>();
}
#Entity
#Table(name = "plots")
public class Plots {
#OneToMany(mappedBy = "plot")
private Set<Crafts> items = new HashSet<>();
}
#Entity
#Table(name = "crafts")
public class Crafts {
#EmbeddedId
private CraftsId id;
#ManyToOne
#JoinColumn(name = "item_id", insertable = false, updatable = false)
private Items item;
#ManyToOne
#JoinColumn(name = "plot_id", insertable = false, updatable = false)
private Plots plot;
}
#Embeddable
public class CraftsId {
#Column(name = "item_id")
private Integer itemId;
#Column(name = "plot_id")
private Integer plotId;
// equals + hashCode
}
I have two table in relation many to many
public class Repertoire {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(nullable = false, unique = true)
private Integer id;
private String name;
private Integer dayWeek;
#ManyToMany(cascade = CascadeType.REMOVE)
#JoinTable(
name = "repertoire_seance",
joinColumns = { #JoinColumn(name = "repertoire_id")},
inverseJoinColumns = {#JoinColumn(name = "seance_id")}
)
List<Seance> seances = new ArrayList<>();
}
and
public class Seance {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(nullable = false, unique = true)
private Integer id;
private java.time.LocalTime displayTime;
#ManyToOne
private Film film;
#Column(length=127)
private String kind;
#ManyToOne(fetch = FetchType.LAZY, cascade = CascadeType.MERGE)
private Hall hall;
#OneToMany(mappedBy = "reservationSeance")
#JsonIgnore
private List<Reservation> reservations = new ArrayList<>();
}
Hibernate create linked tabel repertoire_seance is posible get seances by seancesId and repertoire.dayWeek using spring data (JpaRepository) something like that findBySeanceIdAndRepertoireDayWeek()?
You could achieve this by writing an HQL.
It would look something like this:
select s from Repertoire r inner join r.seances s where r.dayWeek ="Your Value" and s.id = "Your Id Value"
I have 2 tables called Product and Category with many-to-many relationship. And Product has a one-to-many relationship with Images table. I created a table Product_Category to link 2 table Product and Category together. My problem is when 1 product belongs to 1 category, it's just fine with 4 images of that product. But if 1 product belongs to 2 categories, i get 8 images instead of 4
This is image of problem
As you can see is's supposed to be _1 _2 _3 _4 instead _1 _1 _2 _2 ...
This is my entities class
ProductEntity
#Entity
#Table(name = "product")
public class ProductEntity {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "name")
private String name;
#Column(name = "description")
private String description;
#Column(name = "price")
private double price;
#Column(name = "material")
private String material;
#ManyToOne
#JoinColumn(name="careId")
private ProductCareEntity productCare;
#OneToMany(mappedBy = "product", fetch = FetchType.EAGER)
private List<ImageEntity> images;
#OneToMany(mappedBy = "product", fetch = FetchType.EAGER)
private List<ProductCategoryEntity> productCategoryEntities;
#OneToMany(mappedBy = "product", fetch = FetchType.EAGER)
private List<OrderDetailEntity> orderDetailEntityList;
#OneToMany(mappedBy = "product", fetch = FetchType.EAGER,cascade=CascadeType.ALL)
private List<ProductSizeQuantityEntity> productSizeQuantities;
CategoryEntity
#Entity
#Table(name = "category")
public class CategoryEntity {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "name")
private String name;
#OneToMany(mappedBy = "category", fetch = FetchType.EAGER)
private List<ProductCategoryEntity> productCategories;
ProductCategoryEntity
#Entity
#Table(name = "product_category")
public class ProductCategoryEntity {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#ManyToOne
#JoinColumn(name = "categoryId")
private CategoryEntity category;
#ManyToOne
#JoinColumn(name = "productId")
private ProductEntity product;
How can i solve this problem?
I don't think you need ProductCategoryEntity at all. All you need to do is to make a List of Category type in product and List of Product type in Category. like this:
#Entity
#Table(name = "product")
public class ProductEntity {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "name")
private String name;
#Column(name = "description")
private String description;
#Column(name = "price")
private double price;
#Column(name = "material")
private String material;
#ManyToOne
#JoinColumn(name="careId")
private ProductCareEntity productCare;
#OneToMany(mappedBy = "product", fetch = FetchType.EAGER)
private List<ImageEntity> images;
#ManyToMany(cascade = { CascadeType.ALL })
#JoinTable(name = "ProductCategory",
joinColumns = { #JoinColumn(name = "category_id") },
inverseJoinColumns = { #JoinColumn(name = "product_id"))
private List<Category> categories;
#OneToMany(mappedBy = "product", fetch = FetchType.EAGER)
private List<OrderDetailEntity> orderDetailEntityList;
#OneToMany(mappedBy = "product", fetch =
FetchType.EAGER,cascade=CascadeType.ALL)
private List<ProductSizeQuantityEntity> productSizeQuantities;
and
#Entity
#Table(name = "category")
public class CategoryEntity {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column(name = "id")
private int id;
#Column(name = "name")
private String name;
#ManyToMany(mappedBy = "projects")
#JoinTable(name = "ProductCategory")
private List<Product> products;
I am facing a hibernate problem in updainting the join table in one to many mapping with hibernate. Below are my two entity class and join table entity class.
ArticleCategoryMap.java
#Entity
#Table(name = "ARTICLECATEGORYMAP")
public class ArticleCategoryMap {
private static final long serialVersionUID = -5653708523600543988L;
#Id
#GeneratedValue(strategy = GenerationType.SEQUENCE)
#Column ( name = "id")
Long id;
#ManyToOne(targetEntity = Article.class, fetch = FetchType.EAGER, optional = true, cascade = CascadeType.PERSIST)
#JoinColumn(name = "ARTICLE_ID", nullable = true, insertable = true, updatable = true)
private Article article;
#ManyToOne(targetEntity = Category.class, fetch = FetchType.EAGER, optional = true, cascade = CascadeType.PERSIST)
#JoinColumn(name = "CATEGORY_ID", nullable = true, insertable = true, updatable = true)
private Category category;
//setter and getter
}
Article.java
#Entity
#Table(name = "ARTICLE")
public class Article {
private long id;
private String title;
private String description;
private String keywords;
private String content;
#Id
#GeneratedValue
#Column(name = "ARTICLE_ID")
public long getId() {
return id;
}
//setter and getter
}
Category.java
#Entity
#Table(name = "CATEGORY")
public class Category {
private long id;
private String name;
#OneToMany(cascade = CascadeType.ALL, fetch=FetchType.EAGER)
#JoinTable(
name = "ARTICLECATEGORYMAP",
joinColumns = #JoinColumn(name = "CATEGORY_ID"),
inverseJoinColumns = #JoinColumn(name = "ARTICLE_ID")
)
#CollectionId(
columns = #Column(name="id"),
type=#Type(type="long"),
generator = "sequence"
)
private Collection<Article> articles;
#Id
#GeneratedValue
#Column(name = "CATEGORY_ID")
public long getId() {
return id;
}
#OneToMany(cascade = CascadeType.ALL, fetch=FetchType.EAGER)
#JoinTable(
name = "ARTICLECATEGORYMAP",
joinColumns = #JoinColumn(name = "CATEGORY_ID"),
inverseJoinColumns = #JoinColumn(name = "ARTICLE_ID")
)
#CollectionId(
columns = #Column(name="id"),
type=#Type(type="long"),
generator = "sequence"
)
// setter an getter
}
Now suppose first time I have 2 elements in article table which is mapping to one entry of the category table. so the join table will look something like
Now due to some reason, I want to update the entry where the article entry will map to a new category ID. So the final DB should look like
So My problem Is how can I update this join table.
If you want one to many relationship (1 category have many articles and 1 article to 1 category) you dont need a join table.
The entity classes should look like that:
Category Entity:
Contains a Set of articles:
#Entity
#Table(name = "CATEGORY")
public class Category {
private long id;
private String name;
#OneToMany(mappedBy="category")
private Set<Article> articles;
......
}
Article Entity:
#Entity
#Table(name = "ARTICLE")
public class Article {
#ManyToOne
#JoinColumn(name="id", nullable=false)
private Category category;
private long id;
private String title;
private String description;
private String keywords;
private String content;
.......
}
For more details take a look at hibernate-one-to-many. Hope this helps.
Also move annotation from methods to fields. This:
private long id;
#Id
#GeneratedValue
#Column(name = "CATEGORY_ID")
public long getId() {
return id;
}
Should be:
#Id
#GeneratedValue
#Column(name = "CATEGORY_ID")
private long id;
public long getId() {
return id;
}
Many to many relationship:
At your database you have 3 tables:
CATEGORY
ARTICLE
ARTICLECATEGORYMAP (join table)
For many to many relationship entities would be:
Category Entity:
#Entity
#Table(name = "CATEGORY")
public class Category {
#Id
#GeneratedValue
#Column(name = "CATEGORY_ID")
private long id;
private String name;
#ManyToMany(cascade = { CascadeType.ALL })
#JoinTable(
name = "ARTICLECATEGORYMAP",
joinColumns = { #JoinColumn(name = "CATEGORY_ID") },
inverseJoinColumns = { #JoinColumn(name = "ARTICLE_ID") }
)
Set<Article > articles = new HashSet<>();
.....
}
Article Entity:
#Entity
#Table(name = "ARTICLE")
public class Article {
#Id
#GeneratedValue
#Column(name = "ARTICLE_ID")
private long id;
private String title;
private String description;
private String keywords;
private String content;
#ManyToMany(mappedBy = "articles")
private Set<Category> categories = new HashSet<>();
.......
}
For more info take a look at many-to-many ralationship
I use hibernate and spring-data. There are two tables with many-to-many relationship.
#Entity
#Table(name = "FirstEntity")
public class FirstEntity {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(name = "first_entity_id")
private Long id;
#Column(name = "first_entiry_name")
private String name;
/* getters and setters are below*/
}
#Entity
#Table(name = "SecondEntity")
public class SecondEntity {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(name = "second_entity_id")
private Long id;
#Column(name = "second_entiry_name")
private String name;
#Column(name = "second_entiry_desc")
private String description;
/* getters and setters are below*/
}
And entity for cross-reference table.
#Entity
#Table(name = "FirstSecondEntity")
public class FirstSecondEntity {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(name = "first_second_entity_id")
private Long id;
#Column(name = "first_entity_id")
private Long firstEntityId;
#Column(name = "second_entity_id")
private Long secondEntityId;
/* getters and setters are below*/
}
I need SELECT like this
SELECT FirstEntity.name, SecondEntity.name, SecondEntity.description FROM SecondEntity INNER JOIN FirstSecondEntity ON SecondEntity.id = FirstSecondEntity.secondEntityId INNER JOIN User ON FirstEntity.id = FirstSecondEntity.firstEntityId
i.e. I need all records from cross-reference table where instead of ids there is actual info from entities.
Inserting this query into #Query annotation in my CrudRepository-extended class doesn't work because of
ERROR [main][org.hibernate.hql.internal.ast.ErrorCounter] Path expected for join!
So I need your help.
Your join table is all screwed up. In this case, you actually don't even need the join table as a hibernate mapping:
In Second Entity add the following list:
#ManyToMany(fetch = FetchType.LAZY)
#JoinTable(name = "FirstSecondEntity",
joinColumns = {
#JoinColumn(name = "first_entity_id",
nullable = false,
updatable = false) },
inverseJoinColumns = {
#JoinColumn(name = "second_entity_id",
nullable = false,
updatable = false) },
)
private List<FirstEntity> firstEntities;
In FirstEntity add the following list:
#ManyToMany(fetch = FetchType.LAZY,
mappedBy = "firstEntities")
private List<SecondEntity> secondEntities;