Я новичок в Hibernate. Я пытаюсь реализовать сопоставление OneToMany и ManyToOne , при этом я застрял и SQLGrammarException.

Это класс Category (pojo).

package com.app.pojos;

import java.util.ArrayList;
import java.util.List;

import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

import org.hibernate.validator.constraints.NotBlank;

//Category class will have all master categories like Adventurous, tourist destinations etc.
@Entity
@Table(name="category")
public class Category {
    private Integer cid;
    private String name,image,desc;
    private List<SubCategory> subcategories = new ArrayList<>();

    public Category() {

    }

    public Category(String name, String image, String desc, List<SubCategory> subcategories) {
        super();
        this.name = name;
        this.image = image;
        this.desc = desc;
        this.subcategories = subcategories;
    }

    public Category(Integer cid, String name, String image, String desc, List<SubCategory> subcategories) {
        super();
        this.cid = cid;
        this.name = name;
        this.image = image;
        this.desc = desc;
        this.subcategories = subcategories;
    }

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    public Integer getCid() {
        return cid;
    }

    public void setCid(Integer cid) {
        this.cid = cid;
    }

    //This is category name
    @NotBlank(message="Name is REQUIRED....")
    public String getName() {
        return name;
    }


    public void setName(String name) {
        this.name = name;
    }

    //This is category image to be displayed
    @NotBlank(message="Please select an image....")
    public String getImage() {
        return image;
    }

    public void setImage(String image) {
        this.image = image;
    }


    @NotBlank(message="desc is REQUIRED....")
    public String getDesc() {
        return desc;
    }

    public void setDesc(String desc) {
        this.desc = desc;
    }

    //This is an INVERSE SIDE because it is not having foreign key......
    @OneToMany(targetEntity=SubCategory.class,mappedBy="category",
            cascade=CascadeType.ALL,fetch=FetchType.LAZY)
    public List<SubCategory> getSubcategories() {
        return subcategories;
    }


    public void setSubcategories(List<SubCategory> subcategories) {
        this.subcategories = subcategories;
    }

    //Convenience method sub-category into  category
    public void addSubCategory(SubCategory sub) {
        subcategories.add(sub);
        sub.setCategory(this);
    }
}

Это мой класс подкатегории (класс Pojo).

package com.app.pojos;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

import org.hibernate.validator.constraints.NotBlank;

@Entity
@Table(name="subcategory")
public class SubCategory {
    private Integer scid;
    private String name,image,desc;
    private Category category;

    public SubCategory() {

    }

    public SubCategory(String name, String image, String desc, Category category) {
        super();
        this.name = name;
        this.image = image;
        this.desc = desc;
        this.category = category;
    }

    public SubCategory(Integer scid, String name, String image, String desc, Category category) {
        super();
        this.scid = scid;
        this.name = name;
        this.image = image;
        this.desc = desc;
        this.category = category;
    }

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY)
    public Integer getScid() {
        return scid;
    }

    public void setScid(Integer scid) {
        this.scid = scid;
    }

    @NotBlank(message="Name is REQUIRED")
    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @NotBlank(message="Please select an image")
    public String getImage() {
        return image;
    }

    public void setImage(String image) {
        this.image = image;
    }

    @NotBlank(message="Desc is REQUIRED")
    public String getDesc() {
        return desc;
    }

    public void setDesc(String desc) {
        this.desc = desc;
    }


    //This is the OWNING SIDE because it is having foreign key.....
    @ManyToOne
    @JoinColumn(name="cat_id")
    public Category getCategory() {
        return category;
    }

    public void setCategory(Category category) {
        this.category = category;
    }


}

Это мой основной метод.

package com.app.test;

import java.util.Scanner;

import com.app.dao.CategoryDao;
import com.app.pojos.Category;
import com.app.pojos.SubCategory;

import static utils.HibernateUtils.*;

public class Tester {
    public static void main(String[] args) {
        try(Scanner sc = new Scanner(System.in)) {
            getSf();
            System.out.println("Enter Category details.....Name,image,desc");
            Category category  = new Category();
            category.setName(sc.nextLine());
            category.setImage(sc.nextLine());
            category.setDesc(sc.nextLine());
            System.out.println("Enter sub category....Name,Image,desc");
            SubCategory sub = new SubCategory();
            sub.setName(sc.nextLine());
            sub.setImage(sc.nextLine());
            sub.setDesc(sc.nextLine());
            category.addSubCategory(sub);
            System.out.println("ID  : "+ new CategoryDao().saveCatgory(category));
        } catch (Exception e) {
            e.printStackTrace();
        }
        finally {
            getSf().close();
        }
    }
}

Это класс CategoryDao.

package com.app.dao;

import org.hibernate.*;

import com.app.pojos.Category;
import static utils.HibernateUtils.*;

public class CategoryDao {
    public String saveCatgory(Category c) {
        Session hs = getSf().getCurrentSession();
        Transaction tx = hs.beginTransaction();
        try {
            hs.save(c);
            tx.commit();
        } catch (HibernateException e) {
            if (tx != null)
                tx.rollback();
            throw e;
        }
        return "Course added with ID=" + c.getCid();
    }
}

Это мой файл hibernate.cfg.xml.

<?xml version="1.0" encoding="UTF-8"?>

  <!DOCTYPE hibernate-configuration PUBLIC
    "-//Hibernate/Hibernate Configuration DTD//EN"
    "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">

<hibernate-configuration>

    <session-factory>

        <property name="hibernate.connection.autocommit">false</property>
        <property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
        <property name="hibernate.connection.password"></property>
        <property name="hibernate.connection.url">jdbc:mysql://localhost:3306/vov</property>
        <property name="hibernate.connection.username">root</property>
        <property name="hibernate.current_session_context_class">thread</property>
        <property name="hibernate.connection.pool_size">2</property>
        <property name="hibernate.dialect">org.hibernate.dialect.MySQL5Dialect</property>
        <property name="hibernate.show_sql">true</property>
        <property name="hibernate.format_sql">true</property>
        <property name="hibernate.hbm2ddl.auto">update</property>
        <mapping class="com.app.pojos.Category"/>
        <mapping class="com.app.pojos.SubCategory"/>

    </session-factory>
</hibernate-configuration>

Я получаю исключения. Это полноценная консоль

log4j:WARN No appenders could be found for logger (org.jboss.logging).
log4j:WARN Please initialize the log4j system properly.
Hibernate: 

    create table category (
       cid integer not null auto_increment,
        desc varchar(255) not null,
        image varchar(255) not null,
        name varchar(255) not null,
        primary key (cid)
    )
Hibernate: 

    create table subcategory (
       scid integer not null auto_increment,
        desc varchar(255) not null,
        image varchar(255) not null,
        name varchar(255) not null,
        cat_id integer,
        primary key (scid)
    )
Hibernate: 

    alter table subcategory 
       add constraint FK2umvqgly5rb2aqk8v273tk4o5 
       foreign key (cat_id) 
       references category (cid)
sf created!!!!!
Enter Category details.....Name,image,desc
hlkj
khjlgfh
hgvnb
Enter sub category....Name,Image,desc
hjgctg
gcnb
hcgv
Hibernate: 
    insert 
    into
        category
        (desc, image, name) 
    values
        (?, ?, ?)
org.hibernate.exception.SQLGrammarException: could not execute statement
    at org.hibernate.exception.internal.SQLExceptionTypeDelegate.convert(SQLExceptionTypeDelegate.java:63)
    at org.hibernate.exception.internal.StandardSQLExceptionConverter.convert(StandardSQLExceptionConverter.java:42)
    at org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:111)
    at org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:97)
    at org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.executeUpdate(ResultSetReturnImpl.java:207)
    at org.hibernate.dialect.identity.GetGeneratedKeysDelegate.executeAndExtract(GetGeneratedKeysDelegate.java:57)
    at org.hibernate.id.insert.AbstractReturningDelegate.performInsert(AbstractReturningDelegate.java:42)
    at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2907)
    at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:3478)
    at org.hibernate.action.internal.EntityIdentityInsertAction.execute(EntityIdentityInsertAction.java:81)
    at org.hibernate.engine.spi.ActionQueue.execute(ActionQueue.java:623)
    at org.hibernate.engine.spi.ActionQueue.addResolvedEntityInsertAction(ActionQueue.java:277)
    at org.hibernate.engine.spi.ActionQueue.addInsertAction(ActionQueue.java:258)
    at org.hibernate.engine.spi.ActionQueue.addAction(ActionQueue.java:303)
    at org.hibernate.event.internal.AbstractSaveEventListener.addInsertAction(AbstractSaveEventListener.java:318)
    at org.hibernate.event.internal.AbstractSaveEventListener.performSaveOrReplicate(AbstractSaveEventListener.java:275)
    at org.hibernate.event.internal.AbstractSaveEventListener.performSave(AbstractSaveEventListener.java:182)
    at org.hibernate.event.internal.AbstractSaveEventListener.saveWithGeneratedId(AbstractSaveEventListener.java:113)
    at org.hibernate.event.internal.DefaultSaveOrUpdateEventListener.saveWithGeneratedOrRequestedId(DefaultSaveOrUpdateEventListener.java:192)
    at org.hibernate.event.internal.DefaultSaveEventListener.saveWithGeneratedOrRequestedId(DefaultSaveEventListener.java:38)
    at org.hibernate.event.internal.DefaultSaveOrUpdateEventListener.entityIsTransient(DefaultSaveOrUpdateEventListener.java:177)
    at org.hibernate.event.internal.DefaultSaveEventListener.performSaveOrUpdate(DefaultSaveEventListener.java:32)
    at org.hibernate.event.internal.DefaultSaveOrUpdateEventListener.onSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:73)
    at org.hibernate.internal.SessionImpl.fireSave(SessionImpl.java:682)
    at org.hibernate.internal.SessionImpl.save(SessionImpl.java:674)
    at org.hibernate.internal.SessionImpl.save(SessionImpl.java:669)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.hibernate.context.internal.ThreadLocalSessionContext$TransactionProtectionWrapper.invoke(ThreadLocalSessionContext.java:355)
    at com.sun.proxy.$Proxy32.save(Unknown Source)
    at com.app.dao.CategoryDao.saveCatgory(CategoryDao.java:13)
    at com.app.test.Tester.main(Tester.java:26)
Caused by: com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'desc, image, name) values ('hgvnb', 'khjlgfh', 'hlkj')' at line 1
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at com.mysql.jdbc.Util.handleNewInstance(Util.java:404)
    at com.mysql.jdbc.Util.getInstance(Util.java:387)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:942)
    at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3966)
    at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3902)
    at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:2526)
    at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2673)
    at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2549)
    at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1861)
    at com.mysql.jdbc.PreparedStatement.executeUpdateInternal(PreparedStatement.java:2073)
    at com.mysql.jdbc.PreparedStatement.executeUpdateInternal(PreparedStatement.java:2009)
    at com.mysql.jdbc.PreparedStatement.executeLargeUpdate(PreparedStatement.java:5098)
    at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:1994)
    at org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.executeUpdate(ResultSetReturnImpl.java:204)
    ... 29 more
0
user9095617 15 Янв 2018 в 23:09

1 ответ

Лучший ответ

desc - ключевое слово SQL. Не используйте это как имя столбца. В любом случае description намного яснее.

1
JB Nizet 15 Янв 2018 в 20:16