问题描述
我正在编写一个访问数据库 (MariaDB) 的简单 Java 程序。
运行时,我总是遇到一个错误,说Table ...不存在。
之所以如此,是因为当 JPA 调用 CREATE TABLE 语句时,它使用 NUMBER(n)
作为我类中声明为 int 的字段的类型。这会导致语法错误并且不会创建表。因此,在尝试将新用户插入数据库时会发生错误。用 NUMBER
或 INT
替换 DECIMAL
工作正常。
我认为 MariaDB 驱动程序会处理它。
错误:
Exception in thread "AWT-EventQueue-0" jakarta.persistence.RollbackException: Exception [EclipseLink-4002] (Eclipse Persistence Services - 3.0.0.v202012081010): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: java.sql.sqlSyntaxErrorException: (conn=68) Table 'dbtest.user' doesn't exist
Error Code: 1146
Call: INSERT INTO User (ID,eMail,username,password) VALUES (?,?,?)
完整的堆栈跟踪:
Exception in thread "AWT-EventQueue-0" jakarta.persistence.RollbackException: Exception [EclipseLink-4002] (Eclipse Persistence Services - 3.0.0.v202012081010): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: java.sql.sqlSyntaxErrorException: (conn=68) Table 'dbtest.user' doesn't exist
Error Code: 1146
Call: INSERT INTO User (ID,?)
bind => [4 parameters bound]
Query: InsertObjectQuery(db.models.User@1b9b0b25)
at org.eclipse.persistence.internal.jpa.transaction.EntityTransactionImpl.commit(EntityTransactionImpl.java:163)
at db.Connector.registerUser(Connector.java:15)
at UI.Register_User$1.actionPerformed(Register_User.java:40)
at java.desktop/javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:1967)
at java.desktop/javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2308)
at java.desktop/javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:405)
at java.desktop/javax.swing.DefaultButtonModel.setpressed(DefaultButtonModel.java:262)
at java.desktop/javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:279)
at java.desktop/java.awt.Component.processMouseEvent(Component.java:6614)
at java.desktop/javax.swing.JComponent.processMouseEvent(JComponent.java:3342)
at java.desktop/java.awt.Component.processEvent(Component.java:6379)
at java.desktop/java.awt.Container.processEvent(Container.java:2263)
at java.desktop/java.awt.Component.dispatchEventImpl(Component.java:4990)
at java.desktop/java.awt.Container.dispatchEventImpl(Container.java:2321)
at java.desktop/java.awt.Component.dispatchEvent(Component.java:4822)
at java.desktop/java.awt.Lightweightdispatcher.retargetMouseEvent(Container.java:4919)
at java.desktop/java.awt.Lightweightdispatcher.processMouseEvent(Container.java:4548)
at java.desktop/java.awt.Lightweightdispatcher.dispatchEvent(Container.java:4489)
at java.desktop/java.awt.Container.dispatchEventImpl(Container.java:2307)
at java.desktop/java.awt.Window.dispatchEventImpl(Window.java:2769)
at java.desktop/java.awt.Component.dispatchEvent(Component.java:4822)
at java.desktop/java.awt.EventQueue.dispatchEventImpl(EventQueue.java:772)
at java.desktop/java.awt.EventQueue$4.run(EventQueue.java:721)
at java.desktop/java.awt.EventQueue$4.run(EventQueue.java:715)
at java.base/java.security.AccessController.doPrivileged(AccessController.java:391)
at java.base/java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:85)
at java.base/java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:95)
at java.desktop/java.awt.EventQueue$5.run(EventQueue.java:745)
at java.desktop/java.awt.EventQueue$5.run(EventQueue.java:743)
at java.base/java.security.AccessController.doPrivileged(AccessController.java:391)
at java.base/java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:85)
at java.desktop/java.awt.EventQueue.dispatchEvent(EventQueue.java:742)
at java.desktop/java.awt.EventdispatchThread.pumpOneEventForFilters(EventdispatchThread.java:203)
at java.desktop/java.awt.EventdispatchThread.pumpEventsForFilter(EventdispatchThread.java:124)
at java.desktop/java.awt.EventdispatchThread.pumpEventsForHierarchy(EventdispatchThread.java:113)
at java.desktop/java.awt.EventdispatchThread.pumpEvents(EventdispatchThread.java:109)
at java.desktop/java.awt.EventdispatchThread.pumpEvents(EventdispatchThread.java:101)
at java.desktop/java.awt.EventdispatchThread.run(EventdispatchThread.java:90)
Caused by: Exception [EclipseLink-4002] (Eclipse Persistence Services - 3.0.0.v202012081010): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: java.sql.sqlSyntaxErrorException: (conn=68) Table 'dbtest.user' doesn't exist
Error Code: 1146
Call: INSERT INTO User (ID,?)
bind => [4 parameters bound]
Query: InsertObjectQuery(db.models.User@1b9b0b25)
at org.eclipse.persistence.exceptions.DatabaseException.sqlException(DatabaseException.java:334)
at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeDirectNoSelect(DatabaseAccessor.java:908)
at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeNoSelect(DatabaseAccessor.java:970)
at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.basicExecuteCall(DatabaseAccessor.java:640)
at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeCall(DatabaseAccessor.java:567)
at org.eclipse.persistence.internal.sessions.AbstractSession.basicExecuteCall(AbstractSession.java:2045)
at org.eclipse.persistence.sessions.server.ClientSession.executeCall(ClientSession.java:312)
at org.eclipse.persistence.internal.queries.DatasourceCallQueryMechanism.executeCall(DatasourceCallQueryMechanism.java:282)
at org.eclipse.persistence.internal.queries.DatasourceCallQueryMechanism.executeCall(DatasourceCallQueryMechanism.java:268)
at org.eclipse.persistence.internal.queries.DatasourceCallQueryMechanism.insertObject(DatasourceCallQueryMechanism.java:421)
at org.eclipse.persistence.internal.queries.StatementQueryMechanism.insertObject(StatementQueryMechanism.java:175)
at org.eclipse.persistence.internal.queries.StatementQueryMechanism.insertObject(StatementQueryMechanism.java:191)
at org.eclipse.persistence.internal.queries.DatabaseQueryMechanism.insertObjectForWrite(DatabaseQueryMechanism.java:507)
at org.eclipse.persistence.queries.InsertObjectQuery.executeCommit(InsertObjectQuery.java:83)
at org.eclipse.persistence.queries.InsertObjectQuery.executeCommitWithChangeSet(InsertObjectQuery.java:94)
at org.eclipse.persistence.internal.queries.DatabaseQueryMechanism.executeWriteWithChangeSet(DatabaseQueryMechanism.java:319)
at org.eclipse.persistence.queries.WriteObjectQuery.executeDatabaseQuery(WriteObjectQuery.java:61)
at org.eclipse.persistence.queries.DatabaseQuery.execute(DatabaseQuery.java:912)
at org.eclipse.persistence.queries.DatabaseQuery.executeInUnitOfWork(DatabaseQuery.java:811)
at org.eclipse.persistence.queries.ObjectLevelModifyQuery.executeInUnitOfWorkObjectLevelModifyQuery(ObjectLevelModifyQuery.java:112)
at org.eclipse.persistence.queries.ObjectLevelModifyQuery.executeInUnitOfWork(ObjectLevelModifyQuery.java:89)
at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.internalExecuteQuery(UnitOfWorkImpl.java:2984)
at org.eclipse.persistence.internal.sessions.AbstractSession.executeQuery(AbstractSession.java:1844)
at org.eclipse.persistence.internal.sessions.AbstractSession.executeQuery(AbstractSession.java:1826)
at org.eclipse.persistence.internal.sessions.AbstractSession.executeQuery(AbstractSession.java:1776)
at org.eclipse.persistence.internal.sessions.CommitManager.commitNewObjectsForClassWithChangeSet(CommitManager.java:248)
at org.eclipse.persistence.internal.sessions.CommitManager.commitAllObjectsWithChangeSet(CommitManager.java:147)
at org.eclipse.persistence.internal.sessions.AbstractSession.writeallObjectsWithChangeSet(AbstractSession.java:4329)
at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.commitToDatabase(UnitOfWorkImpl.java:1496)
at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.commitToDatabaseWithChangeSet(UnitOfWorkImpl.java:1586)
at org.eclipse.persistence.internal.sessions.RepeatableWriteUnitOfWork.commitRootUnitOfWork(RepeatableWriteUnitOfWork.java:288)
at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.commitAndResume(UnitOfWorkImpl.java:1223)
at org.eclipse.persistence.internal.jpa.transaction.EntityTransactionImpl.commit(EntityTransactionImpl.java:138)
... 37 more
Caused by: java.sql.sqlSyntaxErrorException: (conn=68) Table 'dbtest.user' doesn't exist
at org.mariadb.jdbc.internal.util.exceptions.ExceptionFactory.createException(ExceptionFactory.java:62)
at org.mariadb.jdbc.internal.util.exceptions.ExceptionFactory.create(ExceptionFactory.java:153)
at org.mariadb.jdbc.MariaDbStatement.executeExceptionEpilogue(MariaDbStatement.java:274)
at org.mariadb.jdbc.ClientSidePreparedStatement.executeInternal(ClientSidePreparedStatement.java:229)
at org.mariadb.jdbc.ClientSidePreparedStatement.execute(ClientSidePreparedStatement.java:149)
at org.mariadb.jdbc.ClientSidePreparedStatement.executeUpdate(ClientSidePreparedStatement.java:181)
at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeDirectNoSelect(DatabaseAccessor.java:898)
... 68 more
Caused by: org.mariadb.jdbc.internal.util.exceptions.MariaDbsqlException: Table 'dbtest.user' doesn't exist
at org.mariadb.jdbc.internal.util.exceptions.MariaDbsqlException.of(MariaDbsqlException.java:34)
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.exceptionWithQuery(AbstractQueryProtocol.java:194)
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.exceptionWithQuery(AbstractQueryProtocol.java:177)
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.executeQuery(AbstractQueryProtocol.java:321)
at org.mariadb.jdbc.ClientSidePreparedStatement.executeInternal(ClientSidePreparedStatement.java:220)
... 71 more
Caused by: java.sql.sqlException: Table 'dbtest.user' doesn't exist
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.readErrorPacket(AbstractQueryProtocol.java:1683)
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.readPacket(AbstractQueryProtocol.java:1545)
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.getResult(AbstractQueryProtocol.java:1508)
at org.mariadb.jdbc.internal.protocol.AbstractQueryProtocol.executeQuery(AbstractQueryProtocol.java:318)
... 72 more
创建语句:
Call: CREATE TABLE User (ID NUMBER(10) NOT NULL,eMail VARCHAR NOT NULL UNIQUE,username VARCHAR(60) NOT NULL UNIQUE,password NUMBER(10) NOT NULL,PRIMARY KEY (ID))
Query: DataModifyQuery(sql="CREATE TABLE User (ID NUMBER(10) NOT NULL,PRIMARY KEY (ID))")
用户类:
package db.models;
import jakarta.persistence.*;
@Entity
@Table(name = "User")
public class User {
@Id @GeneratedValue(strategy = GenerationType.IDENTITY)
private int id;
@Column(nullable = false,unique = true,length = 60,name = "username")
private String name;
@Column(nullable = false,name = "password")
private int pass;
@Column(nullable = false,name = "eMail")
private String email;
public User() {
}
public User(String name,int pass,String email) {
this.name = name;
this.pass = pass;
this.email = email;
}
}
public boolean registerUser(User u) {
if(em.contains(u))
return false;
em.getTransaction().begin();
em.persist(u);
em.getTransaction().commit();
em.close();
return true;
}
回答马克的评论,这是我的persistence.xml:
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="1.0"
xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd">
<persistence-unit name="mariadb-localhost">
<provider>org.eclipse.persistence.jpa.PersistenceProvider</provider>
<class>db.models.User</class>
<exclude-unlisted-classes>false</exclude-unlisted-classes>
<properties>
<property name="jakarta.persistence.jdbc.driver" value="org.mariadb.jdbc.Driver"/>
<property name="jakarta.persistence.jdbc.url" value="jdbc:mariadb://localhost:3306/dbtest"/>
<property name="jakarta.persistence.jdbc.user" value="root"/>
<property name="jakarta.persistence.jdbc.password" value="password"/>
<property name="jakarta.persistence.schema-generation.database.action" value="drop-and-create"/>
<property name="eclipselink.logging.level.sql" value="FINE"/>
<property name="eclipselink.ddl-generation" value="create-tables"/>
<!-- or just value="create-tables" -->
</properties>
</persistence-unit>
</persistence>
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)