Google App Engine GAE上的问题:无法锁定表schema_version

时间:2013-05-08 16:27:32

标签: google-app-engine flyway google-cloud-sql

我们使用Cloud SQL进行GAE。一切都在本地开发服务器上运行良好。我们正在使用带有静态连接字符串的AppEngineDriver。由于Flyway能够创建schema_version表,因此连接在生产环境中很好。

但是我们得到一个错误,它无法锁定所述表。桌子是空的。我们有3次迁移,但没有一次迁移。

我们在Spring创建DataSource bean时以Java配置样式启动迁移。

这是堆栈跟踪。

非常感谢!

更新1:我在第一个结束时添加了相关的辅助堆栈跟踪。

com.googlecode.flyway.core.api.FlywayException:无法锁定表ourschemaschema_version: java.sql.SQLException:尚未在准备好的语句协议中支持此命令     在com.google.cloud.sql.jdbc.internal.Exceptions.newSqlException(Exceptions.java:219)     在com.google.cloud.sql.jdbc.internal.SqlProtoClient.check(SqlProtoClient.java:198)     在com.google.cloud.sql.jdbc.internal.SqlProtoClient.executeSql(SqlProtoClient.java:87)     在com.google.cloud.sql.jdbc.internal.SqlProtoClient.executeSql(SqlProtoClient.java:76)     在com.google.cloud.sql.jdbc.Connection.executeSql(Connection.java:528)     在com.google.cloud.sql.jdbc.PreparedStatement.executeSqlImpl(PreparedStatement.java:141)     在com.google.cloud.sql.jdbc.Statement.executeImpl(Statement.java:154)     在com.google.cloud.sql.jdbc.PreparedStatement.execute(PreparedStatement.java:122)     在com.googlecode.flyway.core.dbsupport.JdbcTemplate.execute(JdbcTemplate.java:214)     在com.googlecode.flyway.core.dbsupport.mysql.MySQLTable.doLock(MySQLTable.java:58)     在com.googlecode.flyway.core.dbsupport.Table.lock(Table.java:254)     在com.googlecode.flyway.core.metadatatable.MetaDataTableImpl.lock(MetaDataTableImpl.java:121)     在com.googlecode.flyway.core.command.DbMigrate $ 1.doInTransaction(DbMigrate.java:140)     在com.googlecode.flyway.core.command.DbMigrate $ 1.doInTransaction(DbMigrate.java:138)     在com.googlecode.flyway.core.util.jdbc.TransactionTemplate.execute(TransactionTemplate.java:54)     在com.googlecode.flyway.core.command.DbMigrate.migrate(DbMigrate.java:137)     在com.googlecode.flyway.core.Flyway $ 1.execute(Flyway.java:862)     在com.googlecode.flyway.core.Flyway $ 1.execute(Flyway.java:815)     在com.googlecode.flyway.core.Flyway.execute(Flyway.java:1177)     在com.googlecode.flyway.core.Flyway.migrate(Flyway.java:815)     at com.ourapplication.pilote.persistence.FlywayMigrationDataSourceInitializer.postInitialize(FlywayMigrationDataSourceInitializer.java:23)     at com.ourapplication.pilote.persistence.PersistenceConfiguration.initializeDataSource(PersistenceConfiguration.java:188)     在com.ourapplication.pilote.persistence.PersistenceConfiguration.dataSource(PersistenceConfiguration.java:175)

引起:java.sql.SQLException:尚未在准备好的语句协议中支持此命令     在com.google.cloud.sql.jdbc.internal.Exceptions.newSqlException(Exceptions.java:219)     在com.google.cloud.sql.jdbc.internal.SqlProtoClient.check(SqlProtoClient.java:198)     在com.google.cloud.sql.jdbc.internal.SqlProtoClient.executeSql(SqlProtoClient.java:87)     在com.google.cloud.sql.jdbc.internal.SqlProtoClient.executeSql(SqlProtoClient.java:76)     在com.google.cloud.sql.jdbc.Connection.executeSql(Connection.java:528)     在com.google.cloud.sql.jdbc.PreparedStatement.executeSqlImpl(PreparedStatement.java:141)     在com.google.cloud.sql.jdbc.Statement.executeImpl(Statement.java:154)     在com.google.cloud.sql.jdbc.PreparedStatement.execute(PreparedStatement.java:122)     在com.googlecode.flyway.core.dbsupport.JdbcTemplate.execute(JdbcTemplate.java:214)     在com.googlecode.flyway.core.dbsupport.mysql.MySQLTable.doLock(MySQLTable.java:58)     在com.googlecode.flyway.core.dbsupport.Table.lock(Table.java:254)

1 个答案:

答案 0 :(得分:1)

我有点困惑,因为Flyway文档说一切都适用于使用Cloud SQL和AppEngineDriver的GAE。也许这是最近对Flyway或GAE的改变。

但这是我的修复。

在使用JAD查看GAE的类并跟踪Flyway之后,我认为用于在App Engine服务器实例和MySQL集群之间发送查询的RPC协议不支持某些SQL语句(如LOCK)。

所以一时兴起,我在Flyway中覆盖了MySQLTable.java,使用一个简单的Statement而不是PreparedStatement。没有语句缓存,但它有效。

我刚刚将MySQLTable.java复制到我的项目中,保留了相同的包装并替换了以下内容:

@Override
protected void doLock() throws SQLException
{
    jdbcTemplate.executeStatement("LOCK TABLES " + this + " WRITE");
}

@Override
protected void doUnlock() throws SQLException
{
    jdbcTemplate.executeStatement("UNLOCK TABLES");
}

executeStatement而不是execute。

我们将等待正式修复。

此致

雷米