我想在Spring中使用JPA。我试图实现这一点:
主表商家:
@Entity
@Table
public class Merchants {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Column(name = "merchantId", updatable = false, nullable = false)
private int merchantId;
@Column
private String name;
@OneToMany(mappedBy="merchants")
private List<Terminals> terminals;
@Column
private String login;
}
包含商家ID的第二张表:
@Entity
@Table
public class Terminals {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Column(name = "id", updatable = false, nullable = false)
private int id;
@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="merchantId")
private Merchants merchants;
@Column
private String mode;
}
但是当我部署代码时,我得到了异常:
Caused by: java.sql.SQLException: Table 'production.terminals' doesn't exist
Query is: alter table terminals drop foreign key FKbemlf2t70j5blgdda69vyl032
当我删除表关系代码时,表的创建没有错误。 有什么解决办法吗?
编辑:
MariaDB [production]> show tables;
+------------------------------+
| Tables_in_production |
+------------------------------+
| hibernate_sequence |
| merchants |
| terminals |
+------------------------------+
3 rows in set (0.00 sec)
MariaDB [production]>
application.properties
spring.jmx.enabled=false
spring.datasource.jndi-name=java:/global/production
spring.datasource.driver-class-name=org.mariadb.jdbc.Driver
spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.MariaDBDialect
spring.jpa.show-sql = true
spring.jpa.hibernate.ddl-auto = create-drop
request.limit=300000
答案 0 :(得分:1)
您在这里看到的问题与您在application.properties
文件中定义的DDL策略有关。
似乎您使用create-drop
来告诉Hibernate在会话结束后使用它创建然后销毁数据库模式。 Hibernate通常支持以下DDL指令:
无论如何,我已经看到使用create-drop
DDL策略和H2数据库进行集成测试时会发生这种情况。我从没有花更多的时间对此进行研究,但是它可能归因于您使用的方言,对于标准MySQL而言,这种情况不会发生。
尽管如此,我还是倾向于避免使用Hibernate的DDL函数来创建或更改数据库模式-尤其是在生产部署中。尽管它在大多数情况下都能正常工作,但使用自动DDL功能可能会导致许多讨厌的副作用。
因此,我倾向于将Hibernate的DDL函数设置为validate
,并使用Flyway https://flywaydb.org/处理从创建到数据更改的所有所需的模式更改。
这样,我可以运行自己的sql脚本来执行所需的任何更改。我认为使用flyway是一种更好的选择,因为它允许以下操作:
验证模式更改。
一种更安全的方式来处理任何数据库更改。
允许使用VCS控制架构更改(实际脚本)。
通常它集成得很好,并且设置非常容易,所以我建议您看看它。
答案 1 :(得分:0)
在sqlyog或mysql工作台或任何编辑器中运行此“更改表终端删除外键FKbemlf2t70j5blgdda69vyl032”查询,然后启动应用程序,否则删除表并启动应用程序,因为已经映射了错误的外键。所以我们必须手动输入错误的foregin键