@Test
  public void testUpdateColumnTypeInIcebergTable() throws IOException, TException, InterruptedException {
    // Create an Iceberg table with int, float and decimal(2,1) types with some initial records
    Schema schema = new Schema(optional(1, "id", Types.LongType.get()),
        optional(2, "int_col", Types.IntegerType.get(), "This is an integer type"),
        optional(3, "float_col", Types.FloatType.get(), "This is a float type"),
        optional(4, "decimal_col", Types.DecimalType.of(2, 1), "This is a decimal type"));

    List<Record> records = TestHelper.RecordsBuilder.newInstance(schema).add(0L, 35, 22F, BigDecimal.valueOf(13L, 1))
        .add(1L, 223344, 555.22F, BigDecimal.valueOf(22L, 1)).add(2L, -234, -342F, BigDecimal.valueOf(-12L, 1)).build();

    Table icebergTable = testTables.createTable(shell, "types_table", schema, fileFormat, records);

    // In the result set a float column is returned as double and a decimal is returned as string,
    // even though Hive has the columns with the right types.
    // Probably this conversation happens when fetching the result set after calling the select through the shell.
    // Because of this, a separate schema and record list has to be used when validating the returned values.
    Schema schemaForResultSet =
        new Schema(optional(1, "id", Types.LongType.get()), optional(2, "int_col", Types.IntegerType.get()),
            optional(3, "float_col", Types.DoubleType.get()), optional(4, "decimal_col", Types.StringType.get()));

    List<Record> expectedResults = TestHelper.RecordsBuilder.newInstance(schema).add(0L, 35, 22d, "1.3")
        .add(1L, 223344, 555.22d, "2.2").add(2L, -234, -342d, "-1.2").build();

    // Check the select result and the column types of the table.
    List<Object[]> rows = shell.executeStatement("SELECT * FROM types_table");
    HiveIcebergTestUtils.validateData(expectedResults, HiveIcebergTestUtils.valueForRow(schemaForResultSet, rows), 0);

    org.apache.hadoop.hive.metastore.api.Table table = shell.metastore().getTable("default", "types_table");
    Assert.assertNotNull(table);
    Assert.assertNotNull(table.getSd());
    List<FieldSchema> columns = table.getSd().getCols();
    Assert.assertEquals("id", columns.get(0).getName());
    Assert.assertEquals("bigint", columns.get(0).getType());
    Assert.assertEquals("int_col", columns.get(1).getName());
    Assert.assertEquals("int", columns.get(1).getType());
    Assert.assertEquals("float_col", columns.get(2).getName());
    Assert.assertEquals("float", columns.get(2).getType());
    Assert.assertEquals("decimal_col", columns.get(3).getName());
    Assert.assertEquals("decimal(2,1)", columns.get(3).getType());

    // Change the column types on the table to long, double and decimal(6,1)
    icebergTable.updateSchema().updateColumn("int_col", Types.LongType.get())
        .updateColumn("float_col", Types.DoubleType.get()).updateColumn("decimal_col", Types.DecimalType.of(6, 1))
        .commit();

    schemaForResultSet =
        new Schema(optional(1, "id", Types.LongType.get()), optional(2, "int_col", Types.LongType.get()),
            optional(3, "float_col", Types.DoubleType.get()), optional(4, "decimal_col", Types.StringType.get()));

    expectedResults = TestHelper.RecordsBuilder.newInstance(schema).add(0L, 35L, 22d, "1.3")
        .add(1L, 223344L, 555.219970703125d, "2.2").add(2L, -234L, -342d, "-1.2").build();

    rows = shell.executeStatement("SELECT * FROM types_table");
    HiveIcebergTestUtils.validateData(expectedResults, HiveIcebergTestUtils.valueForRow(schemaForResultSet, rows), 0);

    // Check if the column types in Hive have also changed to big_int, double an decimal(6,1)
    // Do this check only for Hive catalog, as this is the only case when the column types are updated
    // in the metastore. In case of other catalog types, the table is not updated in the metastore,
    // so no point in checking the column types.
    if (TestTables.TestTableType.HIVE_CATALOG.equals(this.testTableType)) {
      table = shell.metastore().getTable("default", "types_table");
      Assert.assertNotNull(table);
      Assert.assertNotNull(table.getSd());
      columns = table.getSd().getCols();
      Assert.assertEquals("id", columns.get(0).getName());
      Assert.assertEquals("bigint", columns.get(0).getType());
      Assert.assertEquals("int_col", columns.get(1).getName());
      Assert.assertEquals("bigint", columns.get(1).getType());
      Assert.assertEquals("float_col", columns.get(2).getName());
      Assert.assertEquals("double", columns.get(2).getType());
      Assert.assertEquals("decimal_col", columns.get(3).getName());
      Assert.assertEquals("decimal(6,1)", columns.get(3).getType());
    }

    // Insert some data which fit to the new column types and check if they are saved and can be queried correctly.
    // This should work for all catalog types.
    shell.executeStatement(
        "INSERT INTO types_table values (3, 3147483647, 111.333, 12345.5), (4, -3147483648, 55, -2234.5)");
    expectedResults = TestHelper.RecordsBuilder.newInstance(schema).add(3L, 3147483647L, 111.333d, "12345.5")
        .add(4L, -3147483648L, 55d, "-2234.5").build();
    rows = shell.executeStatement("SELECT * FROM types_table where id in(3, 4)");
    HiveIcebergTestUtils.validateData(expectedResults, HiveIcebergTestUtils.valueForRow(schemaForResultSet, rows), 0);
  }
Tests that schema changes of Iceberg backed Hive tables are correctly reflected in subsequent select statements.
Verification is done from both ends:
 - when ALTER TABLE statements were initiated from Hive
 - when schema changes were originally done on the Iceberg table
iceberg/iceberg-handler/src/test/java/org/apache/iceberg/mr/hive/TestHiveIcebergSchemaEvolution.java