From e7e3263cf875b6db653320d6250f3890be86b041 Mon Sep 17 00:00:00 2001 From: maxlastglance <e52004266@student.tuwien.ac.at> Date: Mon, 10 Mar 2025 12:30:55 +0100 Subject: [PATCH] update timestamp table on delete --- .../java/at/tuwien/mapper/MariaDbMapper.java | 4 +- .../service/impl/TableServiceMariaDbImpl.java | 75 ++++++++++++++----- 2 files changed, 61 insertions(+), 18 deletions(-) diff --git a/dbrepo-data-service/services/src/main/java/at/tuwien/mapper/MariaDbMapper.java b/dbrepo-data-service/services/src/main/java/at/tuwien/mapper/MariaDbMapper.java index 9f2e89c32f..c870c0bc04 100644 --- a/dbrepo-data-service/services/src/main/java/at/tuwien/mapper/MariaDbMapper.java +++ b/dbrepo-data-service/services/src/main/java/at/tuwien/mapper/MariaDbMapper.java @@ -797,7 +797,9 @@ public interface MariaDbMapper { } statement.append("`").append(pkColumn).append("` = ").append(valueStr); } - statement.append(";"); + + // Append ORDER BY clause to sort by ROW_START descending and limit the result to the most recent row. + statement.append(" ORDER BY `ROW_START` DESC LIMIT 1;"); log.trace("mapped select system timestamps query: {}", statement); return statement.toString(); diff --git a/dbrepo-data-service/services/src/main/java/at/tuwien/service/impl/TableServiceMariaDbImpl.java b/dbrepo-data-service/services/src/main/java/at/tuwien/service/impl/TableServiceMariaDbImpl.java index aaaf84003c..ab31033524 100644 --- a/dbrepo-data-service/services/src/main/java/at/tuwien/service/impl/TableServiceMariaDbImpl.java +++ b/dbrepo-data-service/services/src/main/java/at/tuwien/service/impl/TableServiceMariaDbImpl.java @@ -253,14 +253,69 @@ public class TableServiceMariaDbImpl extends DataConnector implements TableServi final int[] idx = new int[]{1}; final PreparedStatement statement = connection.prepareStatement(mariaDbMapper.tupleToRawDeleteQuery(table, data)); for (String column : data.getKeys().keySet()) { - mariaDbMapper.prepareStatementWithColumnTypeObject(statement, - getColumnType(table.getColumns(), column), idx[0], column, data.getKeys().get(column)); + mariaDbMapper.prepareStatementWithColumnTypeObject( + statement, + getColumnType(table.getColumns(), column), + idx[0], + column, + data.getKeys().get(column)); idx[0]++; } final long start = System.currentTimeMillis(); statement.executeUpdate(); log.trace("executed statement in {} ms", System.currentTimeMillis() - start); connection.commit(); + + String selectQuery = mariaDbMapper.tupleToRawSelectSystemTimestampsQuery( + table, TupleDto.builder().data(data.getKeys()).build()); + try (PreparedStatement selectStmt = connection.prepareStatement(selectQuery); + ResultSet rs = selectStmt.executeQuery()) { + if (rs.next()) { + // Retrieve the new primary key values from the updated row (if needed). + Map<String, Object> pkData = new HashMap<>(); + for (PrimaryKeyDto pk : table.getConstraints().getPrimaryKey()) { + pkData.put(pk.getColumn().getInternalName(), + rs.getObject(pk.getColumn().getInternalName())); + } + Timestamp tsAdd = rs.getTimestamp("ROW_START"); + Timestamp tsDelete = rs.getTimestamp("ROW_END"); + + // Build the update query for the _timestamps table. + String updateTsQuery = mariaDbMapper.tupleToRawUpdateTimestampQuery( + table, TupleUpdateDto.builder().data(data.getKeys()).build(), tsAdd, tsDelete); + try (PreparedStatement ps = connection.prepareStatement(updateTsQuery)) { + int parameterIndex = 1; + + // SET clause: new timestamp values. + ps.setTimestamp(parameterIndex++, tsAdd); + ps.setTimestamp(parameterIndex++, tsDelete); + + // SET clause: new primary key values (assumed to be provided in data.getKeys()) + for (PrimaryKeyDto pk : table.getConstraints().getPrimaryKey()) { + Object newPkValue = data.getKeys().get(pk.getColumn().getInternalName()); + ps.setObject(parameterIndex++, newPkValue); + } + + // WHERE clause: bind the database id. + String databaseId = table.getDatabase().getInternalName(); + ps.setString(parameterIndex++, databaseId); + + // WHERE clause: bind the old primary key values. + for (PrimaryKeyDto pk : table.getConstraints().getPrimaryKey()) { + log.info("Setting new primary key value: {}", pk.getColumn().getInternalName()); + Object oldPkValue = data.getKeys().get(pk.getColumn().getInternalName()); + log.info("Old primary key value: {}", oldPkValue); + ps.setObject(parameterIndex++, oldPkValue); + } + int rowsUpdated = ps.executeUpdate(); + } catch (SQLException e) { + log.error("Error updating timestamp table", e); + throw new RuntimeException("Error updating timestamp table", e); + } + } else { + log.warn("No row found for updated PK; timestamps not updated."); + } + } // End of try-with-resources for selectStmt and rs. } catch (SQLException e) { connection.rollback(); log.error("Failed to delete tuple: {}", e.getMessage()); @@ -271,6 +326,7 @@ public class TableServiceMariaDbImpl extends DataConnector implements TableServi log.info("Deleted tuple(s) from table: {}.{}", table.getDatabase(), table.getInternalName()); } + @Override public void createTuple(TableDto table, TupleDto data) throws SQLException, QueryMalformedException, TableMalformedException, StorageUnavailableException, StorageNotFoundException { @@ -426,9 +482,7 @@ public class TableServiceMariaDbImpl extends DataConnector implements TableServi // SET clause: new primary key values (assumed to be provided in data.getData()) for (PrimaryKeyDto pk : table.getConstraints().getPrimaryKey()) { - log.info("Setting new primary key value: {}", pk.getColumn().getInternalName()); Object newPkValue = data.getData().get(pk.getColumn().getInternalName()); - log.info("New primary key value: {}", newPkValue); ps.setObject(parameterIndex++, newPkValue); } @@ -443,20 +497,7 @@ public class TableServiceMariaDbImpl extends DataConnector implements TableServi log.info("Old primary key value: {}", oldPkValue); ps.setObject(parameterIndex++, oldPkValue); } - - log.info("SQL Query: " + updateTsQuery); - log.info("Bound parameters: tsAdd={}, tsDelete={}, newPKValues={}, databaseId={}, oldPKValues={}", - tsAdd, tsDelete, - table.getConstraints().getPrimaryKey().stream() - .map(pk -> data.getData().get(pk.getColumn().getInternalName())) - .collect(Collectors.toList()), - databaseId, - table.getConstraints().getPrimaryKey().stream() - .map(pk -> data.getKeys().get(pk.getColumn().getInternalName())) - .collect(Collectors.toList())); - int rowsUpdated = ps.executeUpdate(); - log.info("Updated {} row(s) in {}_timestamps table.", rowsUpdated, table.getInternalName()); } } else { log.warn("No row found for updated PK; timestamps not updated."); -- GitLab