This is an automated email from the ASF dual-hosted git repository.

blue pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/iceberg.git


The following commit(s) were added to refs/heads/master by this push:
     new eaf7c4f2e2 Core: Fix view version ID reassigment and deduplication, 
start schema ID at 0 (#8664)
eaf7c4f2e2 is described below

commit eaf7c4f2e2adc952b5a150cf0b854adebfb9fdf0
Author: Eduard Tudenhoefner <[email protected]>
AuthorDate: Thu Sep 28 18:49:10 2023 +0200

    Core: Fix view version ID reassigment and deduplication, start schema ID at 
0 (#8664)
---
 .../java/org/apache/iceberg/view/ViewMetadata.java |  23 +-
 .../org/apache/iceberg/view/TestViewMetadata.java  | 345 +++++++++++++++------
 .../iceberg/view/TestViewMetadataParser.java       |   9 +-
 .../org/apache/iceberg/view/ValidViewMetadata.json |   8 +-
 4 files changed, 284 insertions(+), 101 deletions(-)

diff --git a/core/src/main/java/org/apache/iceberg/view/ViewMetadata.java 
b/core/src/main/java/org/apache/iceberg/view/ViewMetadata.java
index cb905bce09..43dba2f6b2 100644
--- a/core/src/main/java/org/apache/iceberg/view/ViewMetadata.java
+++ b/core/src/main/java/org/apache/iceberg/view/ViewMetadata.java
@@ -22,6 +22,7 @@ import java.io.Serializable;
 import java.util.Comparator;
 import java.util.List;
 import java.util.Map;
+import java.util.Objects;
 import java.util.Set;
 import java.util.UUID;
 import java.util.stream.Collectors;
@@ -139,6 +140,7 @@ public interface ViewMetadata extends Serializable {
   }
 
   class Builder {
+    private static final int INITIAL_SCHEMA_ID = 0;
     private static final int LAST_ADDED = -1;
     private final List<ViewVersion> versions;
     private final List<Schema> schemas;
@@ -295,16 +297,31 @@ public interface ViewMetadata extends Serializable {
       // if the view version already exists, use its id; otherwise use the 
highest id + 1
       int newVersionId = viewVersion.versionId();
       for (ViewVersion version : versions) {
-        if (version.equals(viewVersion)) {
+        if (sameViewVersion(version, viewVersion)) {
           return version.versionId();
         } else if (version.versionId() >= newVersionId) {
-          newVersionId = viewVersion.versionId() + 1;
+          newVersionId = version.versionId() + 1;
         }
       }
 
       return newVersionId;
     }
 
+    /**
+     * Checks whether the given view versions would behave the same while 
ignoring the view version
+     * id, the creation timestamp, and the summary.
+     *
+     * @param one the view version to compare
+     * @param two the view version to compare
+     * @return true if the given view versions would behave the same
+     */
+    private boolean sameViewVersion(ViewVersion one, ViewVersion two) {
+      return Objects.equals(one.representations(), two.representations())
+          && Objects.equals(one.defaultCatalog(), two.defaultCatalog())
+          && Objects.equals(one.defaultNamespace(), two.defaultNamespace())
+          && one.schemaId() == two.schemaId();
+    }
+
     public Builder addSchema(Schema schema) {
       addSchemaInternal(schema);
       return this;
@@ -338,7 +355,7 @@ public interface ViewMetadata extends Serializable {
 
     private int reuseOrCreateNewSchemaId(Schema newSchema) {
       // if the schema already exists, use its id; otherwise use the highest 
id + 1
-      int newSchemaId = newSchema.schemaId();
+      int newSchemaId = INITIAL_SCHEMA_ID;
       for (Schema schema : schemas) {
         if (schema.sameSchema(newSchema)) {
           return schema.schemaId();
diff --git a/core/src/test/java/org/apache/iceberg/view/TestViewMetadata.java 
b/core/src/test/java/org/apache/iceberg/view/TestViewMetadata.java
index b525068cdf..4706640f53 100644
--- a/core/src/test/java/org/apache/iceberg/view/TestViewMetadata.java
+++ b/core/src/test/java/org/apache/iceberg/view/TestViewMetadata.java
@@ -38,6 +38,10 @@ import org.junit.jupiter.api.Test;
 public class TestViewMetadata {
 
   private ViewVersion newViewVersion(int id, String sql) {
+    return newViewVersion(id, 0, sql);
+  }
+
+  private ViewVersion newViewVersion(int id, int schemaId, String sql) {
     return ImmutableViewVersion.builder()
         .versionId(id)
         .timestampMillis(System.currentTimeMillis())
@@ -46,7 +50,7 @@ public class TestViewMetadata {
         .summary(ImmutableMap.of("operation", "create"))
         .addRepresentations(
             
ImmutableSQLViewRepresentation.builder().dialect("spark").sql(sql).build())
-        .schemaId(1)
+        .schemaId(schemaId)
         .build();
   }
 
@@ -117,11 +121,10 @@ public class TestViewMetadata {
                 ViewMetadata.builder()
                     .upgradeFormatVersion(23)
                     .setLocation("location")
-                    .addSchema(
-                        new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get())))
+                    .addSchema(new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get())))
                     .addVersion(
                         ImmutableViewVersion.builder()
-                            .schemaId(1)
+                            .schemaId(0)
                             .versionId(1)
                             .timestampMillis(23L)
                             .putSummary("operation", "op")
@@ -177,11 +180,10 @@ public class TestViewMetadata {
             () ->
                 ViewMetadata.builder()
                     .setLocation("location")
-                    .addSchema(
-                        new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get())))
+                    .addSchema(new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get())))
                     .addVersion(
                         ImmutableViewVersion.builder()
-                            .schemaId(1)
+                            .schemaId(0)
                             .versionId(1)
                             .timestampMillis(23L)
                             .putSummary("operation", "op")
@@ -224,30 +226,9 @@ public class TestViewMetadata {
                     .setLocation("location")
                     .addSchema(
                         new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get())))
-                    .addVersion(
-                        ImmutableViewVersion.builder()
-                            .schemaId(1)
-                            .versionId(1)
-                            .timestampMillis(23L)
-                            .putSummary("operation", "a")
-                            .defaultNamespace(Namespace.of("ns"))
-                            .build())
-                    .addVersion(
-                        ImmutableViewVersion.builder()
-                            .schemaId(1)
-                            .versionId(2)
-                            .timestampMillis(24L)
-                            .putSummary("operation", "b")
-                            .defaultNamespace(Namespace.of("ns"))
-                            .build())
-                    .addVersion(
-                        ImmutableViewVersion.builder()
-                            .schemaId(1)
-                            .versionId(3)
-                            .timestampMillis(25L)
-                            .putSummary("operation", "c")
-                            .defaultNamespace(Namespace.of("ns"))
-                            .build())
+                    .addVersion(newViewVersion(1, "select * from ns.tbl"))
+                    .addVersion(newViewVersion(2, "select count(*) from 
ns.tbl"))
+                    .addVersion(newViewVersion(3, "select count(*) as count 
from ns.tbl"))
                     .setCurrentVersionId(3)
                     .build())
         .isInstanceOf(IllegalArgumentException.class)
@@ -257,36 +238,15 @@ public class TestViewMetadata {
   @Test
   public void viewHistoryNormalization() {
     Map<String, String> properties = 
ImmutableMap.of(ViewProperties.VERSION_HISTORY_SIZE, "2");
-    ViewVersion viewVersionOne =
-        ImmutableViewVersion.builder()
-            .schemaId(1)
-            .versionId(1)
-            .timestampMillis(23L)
-            .putSummary("operation", "a")
-            .defaultNamespace(Namespace.of("ns"))
-            .build();
-    ViewVersion viewVersionTwo =
-        ImmutableViewVersion.builder()
-            .schemaId(1)
-            .versionId(2)
-            .timestampMillis(24L)
-            .putSummary("operation", "b")
-            .defaultNamespace(Namespace.of("ns"))
-            .build();
-    ViewVersion viewVersionThree =
-        ImmutableViewVersion.builder()
-            .schemaId(1)
-            .versionId(3)
-            .timestampMillis(25L)
-            .putSummary("operation", "c")
-            .defaultNamespace(Namespace.of("ns"))
-            .build();
+    ViewVersion viewVersionOne = newViewVersion(1, "select * from ns.tbl");
+    ViewVersion viewVersionTwo = newViewVersion(2, "select count(*) from 
ns.tbl");
+    ViewVersion viewVersionThree = newViewVersion(3, "select count(*) as count 
from ns.tbl");
 
     ViewMetadata originalViewMetadata =
         ViewMetadata.builder()
             .setProperties(properties)
             .setLocation("location")
-            .addSchema(new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get())))
+            .addSchema(new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get())))
             .addVersion(viewVersionOne)
             .addVersion(viewVersionTwo)
             .addVersion(viewVersionThree)
@@ -326,7 +286,7 @@ public class TestViewMetadata {
         
.asInstanceOf(InstanceOfAssertFactories.type(MetadataUpdate.AddSchema.class))
         .extracting(MetadataUpdate.AddSchema::schema)
         .extracting(Schema::schemaId)
-        .isEqualTo(1);
+        .isEqualTo(0);
 
     assertThat(changes)
         .element(3)
@@ -360,32 +320,11 @@ public class TestViewMetadata {
   @Test
   public void viewMetadataAndMetadataChanges() {
     Map<String, String> properties = ImmutableMap.of("key1", "prop1", "key2", 
"prop2");
-    Schema schemaOne = new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get()));
-    Schema schemaTwo = new Schema(2, Types.NestedField.required(1, "y", 
Types.LongType.get()));
-    ViewVersion viewVersionOne =
-        ImmutableViewVersion.builder()
-            .schemaId(schemaOne.schemaId())
-            .versionId(1)
-            .timestampMillis(23L)
-            .putSummary("operation", "a")
-            .defaultNamespace(Namespace.of("ns"))
-            .build();
-    ViewVersion viewVersionTwo =
-        ImmutableViewVersion.builder()
-            .schemaId(schemaOne.schemaId())
-            .versionId(2)
-            .timestampMillis(24L)
-            .putSummary("operation", "b")
-            .defaultNamespace(Namespace.of("ns"))
-            .build();
-    ViewVersion viewVersionThree =
-        ImmutableViewVersion.builder()
-            .schemaId(schemaTwo.schemaId())
-            .versionId(3)
-            .timestampMillis(25L)
-            .putSummary("operation", "c")
-            .defaultNamespace(Namespace.of("ns"))
-            .build();
+    Schema schemaOne = new Schema(0, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schemaTwo = new Schema(1, Types.NestedField.required(1, "y", 
Types.LongType.get()));
+    ViewVersion viewVersionOne = newViewVersion(1, 0, "select * from ns.tbl");
+    ViewVersion viewVersionTwo = newViewVersion(2, 0, "select count(*) from 
ns.tbl");
+    ViewVersion viewVersionThree = newViewVersion(3, 1, "select count(*) as 
count from ns.tbl");
 
     String uuid = "fa6506c3-7681-40c8-86dc-e36561f83385";
     ViewMetadata viewMetadata =
@@ -408,7 +347,9 @@ public class TestViewMetadata {
     assertThat(viewMetadata.currentVersionId()).isEqualTo(3);
     assertThat(viewMetadata.currentVersion()).isEqualTo(viewVersionThree);
     
assertThat(viewMetadata.formatVersion()).isEqualTo(ViewMetadata.DEFAULT_VIEW_FORMAT_VERSION);
-    assertThat(viewMetadata.schemas()).hasSize(2).containsExactly(schemaOne, 
schemaTwo);
+    assertThat(viewMetadata.schemas().stream().map(Schema::asStruct))
+        .hasSize(2)
+        .containsExactly(schemaOne.asStruct(), schemaTwo.asStruct());
     
assertThat(viewMetadata.schema().asStruct()).isEqualTo(schemaTwo.asStruct());
     assertThat(viewMetadata.currentSchemaId()).isEqualTo(schemaTwo.schemaId());
     assertThat(viewMetadata.location()).isEqualTo("custom-location");
@@ -443,7 +384,7 @@ public class TestViewMetadata {
         
.asInstanceOf(InstanceOfAssertFactories.type(MetadataUpdate.AddSchema.class))
         .extracting(MetadataUpdate.AddSchema::schema)
         .extracting(Schema::schemaId)
-        .isEqualTo(1);
+        .isEqualTo(0);
 
     assertThat(changes)
         .element(4)
@@ -451,7 +392,7 @@ public class TestViewMetadata {
         
.asInstanceOf(InstanceOfAssertFactories.type(MetadataUpdate.AddSchema.class))
         .extracting(MetadataUpdate.AddSchema::schema)
         .extracting(Schema::schemaId)
-        .isEqualTo(2);
+        .isEqualTo(1);
 
     assertThat(changes)
         .element(5)
@@ -489,10 +430,10 @@ public class TestViewMetadata {
         ViewMetadata.builder()
             .assignUUID(uuid)
             .setLocation("custom-location")
-            .addSchema(new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get())))
+            .addSchema(new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get())))
             .addVersion(
                 ImmutableViewVersion.builder()
-                    .schemaId(1)
+                    .schemaId(0)
                     .versionId(1)
                     .timestampMillis(23L)
                     .putSummary("operation", "create")
@@ -525,7 +466,7 @@ public class TestViewMetadata {
 
   @Test
   public void viewMetadataWithMetadataLocation() {
-    Schema schema = new Schema(1, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schema = new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get()));
     ViewVersion viewVersion =
         ImmutableViewVersion.builder()
             .schemaId(schema.schemaId())
@@ -560,4 +501,230 @@ public class TestViewMetadata {
             .build();
     
assertThat(viewMetadata.metadataFileLocation()).isEqualTo("metadata-location");
   }
+
+  @Test
+  public void viewVersionIDReassignment() {
+    // all view versions have the same ID
+    ViewVersion viewVersionOne = newViewVersion(1, "select * from ns.tbl");
+    ViewVersion viewVersionTwo = newViewVersion(1, "select count(*) from 
ns.tbl");
+    ViewVersion viewVersionThree = newViewVersion(1, "select count(*) as count 
from ns.tbl");
+
+    ViewMetadata viewMetadata =
+        ViewMetadata.builder()
+            .setLocation("custom-location")
+            .addSchema(new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get())))
+            .addVersion(viewVersionOne)
+            .addVersion(viewVersionTwo)
+            .addVersion(viewVersionThree)
+            .setCurrentVersionId(3)
+            .build();
+
+    assertThat(viewMetadata.currentVersion())
+        
.isEqualTo(ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).build());
+
+    // IDs of the view versions should be re-assigned
+    assertThat(viewMetadata.versions())
+        .hasSize(3)
+        .containsExactly(
+            viewVersionOne,
+            
ImmutableViewVersion.builder().from(viewVersionTwo).versionId(2).build(),
+            
ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).build());
+  }
+
+  @Test
+  public void viewVersionDeduplication() {
+    // all view versions have the same ID
+    // additionally, there are duplicate view versions that only differ in 
their creation timestamp
+    // and/or the summary
+    ViewVersion viewVersionOne = newViewVersion(1, "select * from ns.tbl");
+    ViewVersion viewVersionTwo = newViewVersion(1, "select count(*) from 
ns.tbl");
+    ViewVersion viewVersionThree = newViewVersion(1, "select count(*) as count 
from ns.tbl");
+    ViewVersion viewVersionOneUpdated =
+        
ImmutableViewVersion.builder().from(viewVersionOne).timestampMillis(1000).build();
+    ViewVersion viewVersionTwoUpdated =
+        ImmutableViewVersion.builder()
+            .from(viewVersionTwo)
+            .summary(ImmutableMap.of("operation", "replace"))
+            .build();
+    ViewVersion viewVersionThreeUpdated =
+        ImmutableViewVersion.builder()
+            .from(viewVersionThree)
+            .timestampMillis(1000)
+            .summary(ImmutableMap.of("operation", "replace"))
+            .build();
+
+    ViewMetadata viewMetadata =
+        ViewMetadata.builder()
+            .setLocation("custom-location")
+            .addSchema(new Schema(Types.NestedField.required(1, "x", 
Types.LongType.get())))
+            .addVersion(viewVersionOne)
+            .addVersion(viewVersionTwo)
+            .addVersion(viewVersionThree)
+            .addVersion(viewVersionOneUpdated)
+            .addVersion(viewVersionTwoUpdated)
+            .addVersion(viewVersionThreeUpdated)
+            .setCurrentVersionId(3)
+            .build();
+
+    assertThat(viewMetadata.currentVersion())
+        
.isEqualTo(ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).build());
+
+    // IDs of the view versions should be re-assigned and view versions should 
be de-duplicated
+    assertThat(viewMetadata.versions())
+        .hasSize(3)
+        .containsExactly(
+            viewVersionOne,
+            
ImmutableViewVersion.builder().from(viewVersionTwo).versionId(2).build(),
+            
ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).build());
+  }
+
+  @Test
+  public void schemaIDReassignment() {
+    Schema schemaOne = new Schema(5, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schemaTwo = new Schema(7, Types.NestedField.required(1, "y", 
Types.LongType.get()));
+    Schema schemaThree = new Schema(9, Types.NestedField.required(1, "z", 
Types.LongType.get()));
+
+    ViewVersion viewVersion = newViewVersion(1, "select * from ns.tbl");
+    ViewMetadata viewMetadata =
+        ViewMetadata.builder()
+            .setLocation("custom-location")
+            .addSchema(schemaOne)
+            .addSchema(schemaTwo)
+            .addSchema(schemaThree)
+            .setCurrentVersion(viewVersion, schemaThree)
+            .build();
+
+    // schema ID should be re-assigned
+    assertThat(viewMetadata.versions())
+        .hasSize(1)
+        
.containsExactly(ImmutableViewVersion.builder().from(viewVersion).schemaId(2).build());
+
+    // all schema IDs should be re-assigned and start at 0
+    assertThat(viewMetadata.schemas().stream().map(Schema::asStruct))
+        .hasSize(3)
+        .containsExactly(schemaOne.asStruct(), schemaTwo.asStruct(), 
schemaThree.asStruct());
+    assertThat(viewMetadata.schemasById().keySet()).containsExactly(0, 1, 2);
+  }
+
+  @Test
+  public void schemaDeduplication() {
+    Schema schemaOne = new Schema(5, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schemaTwo = new Schema(7, Types.NestedField.required(1, "y", 
Types.LongType.get()));
+    Schema schemaThree = new Schema(9, Types.NestedField.required(1, "z", 
Types.LongType.get()));
+    Schema schemaOneUpdated =
+        new Schema(6, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schemaTwoUpdated =
+        new Schema(8, Types.NestedField.required(1, "y", 
Types.LongType.get()));
+    Schema schemaThreeUpdated =
+        new Schema(10, Types.NestedField.required(1, "z", 
Types.LongType.get()));
+
+    ViewVersion viewVersion = newViewVersion(1, "select * from ns.tbl");
+    ViewMetadata viewMetadata =
+        ViewMetadata.builder()
+            .setLocation("custom-location")
+            .addSchema(schemaOne)
+            .addSchema(schemaTwo)
+            .addSchema(schemaThree)
+            .addSchema(schemaOneUpdated)
+            .addSchema(schemaTwoUpdated)
+            .addSchema(schemaThreeUpdated)
+            .setCurrentVersion(viewVersion, schemaThree)
+            .build();
+
+    // schema ID should be re-assigned
+    assertThat(viewMetadata.versions())
+        .hasSize(1)
+        
.containsExactly(ImmutableViewVersion.builder().from(viewVersion).schemaId(2).build());
+
+    // all schema IDs should be re-assigned and start at 0 and be de-duplicated
+    assertThat(viewMetadata.schemas().stream().map(Schema::asStruct))
+        .hasSize(3)
+        .containsExactly(schemaOne.asStruct(), schemaTwo.asStruct(), 
schemaThree.asStruct());
+    assertThat(viewMetadata.schemasById().keySet()).containsExactly(0, 1, 2);
+  }
+
+  @Test
+  public void viewVersionAndSchemaIDReassignment() {
+    Schema schemaOne = new Schema(5, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schemaTwo = new Schema(7, Types.NestedField.required(1, "y", 
Types.LongType.get()));
+    Schema schemaThree = new Schema(9, Types.NestedField.required(1, "z", 
Types.LongType.get()));
+
+    // all view versions have the same ID
+    ViewVersion viewVersionOne = newViewVersion(1, 5, "select * from ns.tbl");
+    ViewVersion viewVersionTwo = newViewVersion(1, 7, "select count(*) from 
ns.tbl");
+    ViewVersion viewVersionThree = newViewVersion(1, 9, "select count(*) as 
count from ns.tbl");
+
+    ViewMetadata viewMetadata =
+        ViewMetadata.builder()
+            .setLocation("custom-location")
+            .addSchema(schemaOne)
+            .addSchema(schemaTwo)
+            .addSchema(schemaThree)
+            .setCurrentVersion(viewVersionOne, schemaOne)
+            .setCurrentVersion(viewVersionTwo, schemaTwo)
+            .setCurrentVersion(viewVersionThree, schemaThree)
+            .build();
+
+    assertThat(viewMetadata.currentVersion())
+        .isEqualTo(
+            
ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).schemaId(2).build());
+
+    // IDs of the schemas and view versions should be re-assigned
+    assertThat(viewMetadata.versions())
+        .hasSize(3)
+        .containsExactly(
+            
ImmutableViewVersion.builder().from(viewVersionOne).versionId(1).schemaId(0).build(),
+            
ImmutableViewVersion.builder().from(viewVersionTwo).versionId(2).schemaId(1).build(),
+            
ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).schemaId(2).build());
+
+    assertThat(viewMetadata.schemas().stream().map(Schema::asStruct))
+        .hasSize(3)
+        .containsExactly(schemaOne.asStruct(), schemaTwo.asStruct(), 
schemaThree.asStruct());
+    assertThat(viewMetadata.schemasById().keySet()).containsExactly(0, 1, 2);
+  }
+
+  @Test
+  public void viewVersionAndSchemaDeduplication() {
+    Schema schemaOne = new Schema(5, Types.NestedField.required(1, "x", 
Types.LongType.get()));
+    Schema schemaTwo = new Schema(7, Types.NestedField.required(1, "y", 
Types.LongType.get()));
+    Schema schemaThree = new Schema(9, Types.NestedField.required(1, "z", 
Types.LongType.get()));
+
+    // all view versions have the same ID
+    // additionally, there are duplicate view versions and schemas
+    ViewVersion viewVersionOne = newViewVersion(1, 5, "select * from ns.tbl");
+    ViewVersion viewVersionTwo = newViewVersion(1, 7, "select count(*) from 
ns.tbl");
+    ViewVersion viewVersionThree = newViewVersion(1, 9, "select count(*) as 
count from ns.tbl");
+
+    // all view versions have the same ID
+    ViewMetadata viewMetadata =
+        ViewMetadata.builder()
+            .setLocation("custom-location")
+            .addSchema(schemaOne)
+            .addSchema(schemaTwo)
+            .addSchema(schemaThree)
+            .setCurrentVersion(viewVersionOne, schemaOne)
+            .setCurrentVersion(viewVersionTwo, schemaTwo)
+            .setCurrentVersion(viewVersionThree, schemaThree)
+            .setCurrentVersion(viewVersionThree, schemaThree)
+            .setCurrentVersion(viewVersionTwo, schemaTwo)
+            .setCurrentVersion(viewVersionOne, schemaOne)
+            .build();
+
+    assertThat(viewMetadata.currentVersion())
+        .isEqualTo(
+            
ImmutableViewVersion.builder().from(viewVersionOne).versionId(1).schemaId(0).build());
+
+    // IDs of schemas and view versions should be re-assigned and both should 
be de-duplicated
+    assertThat(viewMetadata.versions())
+        .hasSize(3)
+        .containsExactly(
+            
ImmutableViewVersion.builder().from(viewVersionOne).versionId(1).schemaId(0).build(),
+            
ImmutableViewVersion.builder().from(viewVersionTwo).versionId(2).schemaId(1).build(),
+            
ImmutableViewVersion.builder().from(viewVersionThree).versionId(3).schemaId(2).build());
+
+    assertThat(viewMetadata.schemas().stream().map(Schema::asStruct))
+        .hasSize(3)
+        .containsExactly(schemaOne.asStruct(), schemaTwo.asStruct(), 
schemaThree.asStruct());
+    assertThat(viewMetadata.schemasById().keySet()).containsExactly(0, 1, 2);
+  }
 }
diff --git 
a/core/src/test/java/org/apache/iceberg/view/TestViewMetadataParser.java 
b/core/src/test/java/org/apache/iceberg/view/TestViewMetadataParser.java
index 076626d9fa..5fb9589522 100644
--- a/core/src/test/java/org/apache/iceberg/view/TestViewMetadataParser.java
+++ b/core/src/test/java/org/apache/iceberg/view/TestViewMetadataParser.java
@@ -34,7 +34,6 @@ public class TestViewMetadataParser {
 
   private static final Schema TEST_SCHEMA =
       new Schema(
-          1,
           Types.NestedField.required(1, "x", Types.LongType.get()),
           Types.NestedField.required(2, "y", Types.LongType.get(), "comment"),
           Types.NestedField.required(3, "z", Types.LongType.get()));
@@ -61,7 +60,7 @@ public class TestViewMetadataParser {
             .versionId(1)
             .timestampMillis(4353L)
             .summary(ImmutableMap.of("operation", "create"))
-            .schemaId(1)
+            .schemaId(0)
             .defaultCatalog("some-catalog")
             .defaultNamespace(Namespace.empty())
             .addRepresentations(
@@ -74,7 +73,7 @@ public class TestViewMetadataParser {
     ViewVersion version2 =
         ImmutableViewVersion.builder()
             .versionId(2)
-            .schemaId(1)
+            .schemaId(0)
             .timestampMillis(5555L)
             .summary(ImmutableMap.of("operation", "replace"))
             .defaultCatalog("some-catalog")
@@ -170,7 +169,7 @@ public class TestViewMetadataParser {
             .versionId(1)
             .timestampMillis(4353L)
             .summary(ImmutableMap.of("operation", "create"))
-            .schemaId(1)
+            .schemaId(0)
             .defaultCatalog("some-catalog")
             .defaultNamespace(Namespace.empty())
             .addRepresentations(
@@ -183,7 +182,7 @@ public class TestViewMetadataParser {
     ViewVersion version2 =
         ImmutableViewVersion.builder()
             .versionId(2)
-            .schemaId(1)
+            .schemaId(0)
             .timestampMillis(5555L)
             .summary(ImmutableMap.of("operation", "replace"))
             .defaultCatalog("some-catalog")
diff --git 
a/core/src/test/resources/org/apache/iceberg/view/ValidViewMetadata.json 
b/core/src/test/resources/org/apache/iceberg/view/ValidViewMetadata.json
index 4e29ed8702..3183945024 100644
--- a/core/src/test/resources/org/apache/iceberg/view/ValidViewMetadata.json
+++ b/core/src/test/resources/org/apache/iceberg/view/ValidViewMetadata.json
@@ -3,11 +3,11 @@
   "format-version": 1,
   "location": "s3://bucket/test/location",
   "properties": {"some-key": "some-value"},
-  "current-schema-id": 1,
+  "current-schema-id": 0,
   "schemas": [
     {
       "type": "struct",
-      "schema-id": 1,
+      "schema-id": 0,
       "fields": [
         {
           "id": 1,
@@ -37,7 +37,7 @@
       "version-id": 1,
       "timestamp-ms": 4353,
       "summary": {"operation":"create"},
-      "schema-id": 1,
+      "schema-id": 0,
       "default-catalog": "some-catalog",
       "default-namespace": [],
       "representations": [
@@ -52,7 +52,7 @@
       "version-id": 2,
       "timestamp-ms": 5555,
       "summary": {"operation": "replace"},
-      "schema-id": 1,
+      "schema-id": 0,
       "default-catalog": "some-catalog",
       "default-namespace": [],
       "representations": [

Reply via email to