diff --git a/src/main/java/org/qortal/repository/hsqldb/HSQLDBDatabaseUpdates.java b/src/main/java/org/qortal/repository/hsqldb/HSQLDBDatabaseUpdates.java index e29d6b44..a0cc4b85 100644 --- a/src/main/java/org/qortal/repository/hsqldb/HSQLDBDatabaseUpdates.java +++ b/src/main/java/org/qortal/repository/hsqldb/HSQLDBDatabaseUpdates.java @@ -695,7 +695,7 @@ public class HSQLDBDatabaseUpdates { stmt.execute("CHECKPOINT"); break; - case 30: + case 30: { // Split AT state data off to new table for better performance/management. if (!wasPristine && !"mem".equals(HSQLDBRepository.getDbPathname(connection.getMetaData().getURL()))) { @@ -770,12 +770,42 @@ public class HSQLDBDatabaseUpdates { stmt.execute("ALTER TABLE ATStatesNew RENAME TO ATStates"); stmt.execute("CHECKPOINT"); break; + } - case 31: + case 31: { // AT sleep-until-message support + LOGGER.info("Altering AT table in repository - this might take a while... (approx. 20 seconds on high-spec)"); stmt.execute("ALTER TABLE ATs ADD sleep_until_message_timestamp BIGINT"); - stmt.execute("ALTER TABLE ATStates ADD sleep_until_message_timestamp BIGINT"); + + // Create new AT-states table with new column + stmt.execute("CREATE TABLE ATStatesNew (" + + "AT_address QortalAddress, height INTEGER NOT NULL, state_hash ATStateHash NOT NULL, " + + "fees QortalAmount NOT NULL, is_initial BOOLEAN NOT NULL, sleep_until_message_timestamp BIGINT, " + + "PRIMARY KEY (AT_address, height), " + + "FOREIGN KEY (AT_address) REFERENCES ATs (AT_address) ON DELETE CASCADE)"); + stmt.execute("SET TABLE ATStatesNew NEW SPACE"); + stmt.execute("CHECKPOINT"); + + ResultSet resultSet = stmt.executeQuery("SELECT height FROM Blocks ORDER BY height DESC LIMIT 1"); + final int blockchainHeight = resultSet.next() ? resultSet.getInt(1) : 0; + final int heightStep = 100; + + LOGGER.info("Altering AT states table in repository - this might take a while... (approx. 3 mins on high-spec)"); + for (int minHeight = 1; minHeight < blockchainHeight; minHeight += heightStep) { + stmt.execute("INSERT INTO ATStatesNew (" + + "SELECT AT_address, height, state_hash, fees, is_initial, NULL " + + "FROM ATStates " + + "WHERE height BETWEEN " + minHeight + " AND " + (minHeight + heightStep - 1) + + ")"); + stmt.execute("COMMIT"); + } + stmt.execute("CHECKPOINT"); + + stmt.execute("DROP TABLE ATStates"); + stmt.execute("ALTER TABLE ATStatesNew RENAME TO ATStates"); + stmt.execute("CHECKPOINT"); break; + } default: // nothing to do