Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,6 @@
import com.expediagroup.apiary.extensions.gluesync.listener.service.GlueDatabaseService;
import com.expediagroup.apiary.extensions.gluesync.listener.service.GluePartitionService;
import com.expediagroup.apiary.extensions.gluesync.listener.service.GlueTableService;
import com.expediagroup.apiary.extensions.gluesync.listener.service.IsIcebergTablePredicate;

public class ApiaryGlueSync extends MetaStoreEventListener {

Expand All @@ -68,7 +67,6 @@ public class ApiaryGlueSync extends MetaStoreEventListener {
private final GlueDatabaseService glueDatabaseService;
private final GlueTableService glueTableService;
private final GluePartitionService gluePartitionService;
private final IsIcebergTablePredicate isIcebergPredicate;
private final MetricService metricService;
private final boolean throwExceptions;

Expand All @@ -83,7 +81,6 @@ public ApiaryGlueSync(Configuration config, boolean throwExceptions) {
this.glueDatabaseService = new GlueDatabaseService(glueClient, gluePrefix);
this.gluePartitionService = new GluePartitionService(glueClient, gluePrefix);
this.glueTableService = new GlueTableService(glueClient, gluePartitionService, gluePrefix);
this.isIcebergPredicate = new IsIcebergTablePredicate();
this.metricService = new MetricService();
this.throwExceptions = throwExceptions;
log.debug("ApiaryGlueSync created");
Expand All @@ -109,7 +106,6 @@ public ApiaryGlueSync(Configuration config, AWSGlue glueClient, String gluePrefi
this.glueDatabaseService = new GlueDatabaseService(glueClient, gluePrefix);
this.gluePartitionService = new GluePartitionService(glueClient, gluePrefix, defaultSkipArchive);
this.glueTableService = new GlueTableService(glueClient, gluePartitionService, gluePrefix);
this.isIcebergPredicate = new IsIcebergTablePredicate();
this.metricService = metricService;
this.throwExceptions = throwExceptions;
log.debug("ApiaryGlueSync created");
Expand Down Expand Up @@ -214,9 +210,7 @@ public void onAlterTable(AlterTableEvent event) throws MetaException {
Table oldTable = event.getOldTable();
Table newTable = event.getNewTable();
try {
// Only Iceberg rename is supported by Glue, for Hive tables we need to delete
// table and create again
if (isTableRename(oldTable, newTable) && !isIcebergPredicate.test(oldTable.getParameters())) {
if (isTableRename(oldTable, newTable)) {
doRenameOperation(oldTable, newTable);
return;
}
Expand Down Expand Up @@ -291,7 +285,7 @@ private String updateOrCreatePartition(Table table, Partition partition) {
private void doRenameOperation(Table oldTable, Table newTable) {
log.info("{} glue table rename detected to {}", oldTable.getTableName(), newTable.getTableName());
long startTime = System.currentTimeMillis();
glueTableService.create(newTable);
createOrUpdateTable(newTable);
gluePartitionService.copyPartitions(newTable, gluePartitionService.getPartitions(oldTable));
glueTableService.deleteIfUnchanged(oldTable);
metricService.incrementCounter(MetricConstants.LISTENER_TABLE_SUCCESS);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -870,23 +870,47 @@ public void onCreateTable_exceptionRethrownWhenThrowExceptionsEnabled() throws M
}

@Test
public void onAlterIcebergTable_RenameTableSkipsRenameOperation() throws MetaException {
public void onAlterIcebergTable_RenameTable() throws MetaException {
AlterTableEvent event = mock(AlterTableEvent.class);
when(event.getStatus()).thenReturn(true);
Table oldTable = simpleIcebergTable(dbName, tableName, simpleIcebergSchema(), simpleIcebergPartitionSpec(), null);
Table newTable = simpleIcebergTable(dbName, "table_renamed", simpleIcebergSchema(), simpleIcebergPartitionSpec(), null);
when(event.getOldTable()).thenReturn(oldTable);
when(event.getNewTable()).thenReturn(newTable);
when(glueClient.getPartitions(any())).thenReturn(new GetPartitionsResult().withPartitions());
when(glueClient.getTable(any())).thenReturn(new GetTableResult().withTable(new com.amazonaws.services.glue.model.Table()));

glueSync.onAlterTable(event);

verify(glueClient).updateTable(updateTableRequestCaptor.capture());
verify(glueClient).createTable(createTableRequestCaptor.capture());
assertThat(createTableRequestCaptor.getValue().getTableInput().getName(), is("table_renamed"));
verify(glueClient).deleteTable(deleteTableRequestCaptor.capture());
assertThat(deleteTableRequestCaptor.getValue().getName(), is(tableName));
verify(glueClient, never()).updateTable(any());
verify(metricService).incrementCounter(MetricConstants.LISTENER_TABLE_SUCCESS);
verify(metricService).recordEvent(MetricConstants.ALTER_TABLE, MetricConstants.RESULT_SUCCESS, MetricConstants.OUTCOME_UPDATED);
verify(metricService).recordEvent(MetricConstants.ALTER_TABLE, MetricConstants.RESULT_SUCCESS, "renamed");
}

@Test
public void onAlterIcebergTable_RenameTable_idempotentWhenNewTableAlreadyExists() throws MetaException {
AlterTableEvent event = mock(AlterTableEvent.class);
when(event.getStatus()).thenReturn(true);
Table oldTable = simpleIcebergTable(dbName, tableName, simpleIcebergSchema(), simpleIcebergPartitionSpec(), null);
Table newTable = simpleIcebergTable(dbName, "table_renamed", simpleIcebergSchema(), simpleIcebergPartitionSpec(), null);
when(event.getOldTable()).thenReturn(oldTable);
when(event.getNewTable()).thenReturn(newTable);
when(glueClient.getPartitions(any())).thenReturn(new GetPartitionsResult().withPartitions());
when(glueClient.getTable(any())).thenReturn(new GetTableResult().withTable(new com.amazonaws.services.glue.model.Table()));
when(glueClient.createTable(any())).thenThrow(new AlreadyExistsException("already exists"));

glueSync.onAlterTable(event);

verify(glueClient).updateTable(updateTableRequestCaptor.capture());
assertThat(updateTableRequestCaptor.getValue().getTableInput().getName(), is("table_renamed"));
// rename operation (copy+delete) must not be triggered for Iceberg tables
verify(glueClient, times(0)).deleteTable(any());
verify(glueClient, times(0)).batchCreatePartition(any());
verify(glueClient).deleteTable(deleteTableRequestCaptor.capture());
assertThat(deleteTableRequestCaptor.getValue().getName(), is(tableName));
verify(metricService).incrementCounter(MetricConstants.LISTENER_TABLE_SUCCESS);
verify(metricService).recordEvent(MetricConstants.ALTER_TABLE, MetricConstants.RESULT_SUCCESS, "renamed");
}

@Test
Expand Down
Loading