JosephLenton opened a new issue, #654:
URL: https://github.com/apache/avro-rs/issues/654

   Hey, in version 0.22.0 the attribute `logicalType` was dropped entirely. I 
believe this is a regression, and is incorrect behaviour. I am pretty new to 
Avro, so I'm looking for some help on asserting if this is right. I have 
replicated the behaviour in both the Java and Rust Avro projects, and the 
results are different. 
   
   # Steps to reproduce
   
    * You create a valid Json schema which contains a `logicalType` attribute.
    * You parse the Json into an Avro type.
    * You then serialise the schema back to Json.
   
   ## What do I expect?
   
    * The `logicalType` should still be present.
    * The behaviour should match the Java implementation.
   
   ## What happened?
   
    * The `logicalType` is missing.
    * The behaviour does not match the Java implementation.
    * The `logicalType` is entirely dropped, making it impossible to correctly 
identify `map` types for Iceberg.
   
   # Context
   
   I am trying to upgrade the Iceberg repo from Avro 0.21.0 to 0.22.0. One test 
there is failing, which is for map types. There is no Avro equivalent, so the 
Iceberg spec asks for an array of key/value pairs + adding `logicalType: map` 
to the schema. As Avro 0.22.0 drops `logicalType`, this makes it impossible to 
identify the map type.
   
    1. I am trying to upgrade the Iceberg project to use Avro 0.22.0, and find 
that the map tests now fail. Looking at the Iceberg spec, the maps are arrays 
with a `logicalType: map` added. The tests break because the parser drops the 
`logicalType`, making it impossible to know for certainty it is meant to be a 
map.
    2. I believe the Java version preserved the `logicalType`. The Java version 
has tests which perform a round trip and asserts what they started and ended 
with are the same. This implies the `logicalType` is preserved. See: 
https://github.com/apache/avro/blob/main/lang/java/avro/src/test/java/org/apache/avro/TestLogicalType.java#L190-L195
    3. The original PR is about fixing **duplicate** outputs of `logicalType`, 
not removing all of them. It seems odd to remove them all.
   
   # Tests to reproduce
   
   ## For Java
   
   Here is a *passing* test for the Java Apache Avro repo at 
(https://github.com/apache/avro). It's a bit noisy. The key part is 
`logicalType` is at the end of the Json schema, and turning it from the schema 
to string yields the original schema.,
   ```java
   @Test
   void logicalTypeTestReplication() {
     String rawSchema = "{\n" + "  \"type\" : \"array\",\n" + "  \"items\" : 
{\n" + "    \"type\" : \"record\",\n"
         + "    \"name\" : \"k12_v13\",\n" + "    \"fields\" : [ {\n" + "      
\"name\" : \"key\",\n"
         + "      \"type\" : \"int\",\n" + "      \"field-id\" : 12\n" + "    
}, {\n" + "      \"name\" : \"value\",\n"
         + "      \"type\" : \"string\",\n" + "      \"field-id\" : 13\n" + "   
 } ]\n" + "  },\n"
         + "  \"logicalType\" : \"map\"\n" + "}";
   
     Schema schema = SchemaParser.parseSingle(rawSchema);
     String output = schema.toString(true);
   
     assertEquals(rawSchema, output, "logicalType and custom properties should 
survive parsing");
   }
   ```
   
   ## For Rust
   
   Here is the same test for your repo:
   ```rust
   #[test]
   fn it_should_preserve_map_logical_type_on_outer_item() -> TestResult {
       let raw_schema = r#"{
           "type": "array",
           "logicalType": "map",
           "items": {
               "type": "record",
               "name": "k12_v13",
               "fields": [
                   {
                       "name": "key",
                       "type": "int",
                       "field-id": 12
                   },
                   {
                       "name": "value",
                       "type": "string",
                       "field-id": 13
                   }
               ]
           }
       }"#;
   
       let schema = Schema::parse_str(raw_schema)?;
       let output = serde_json::to_string_pretty(&schema).unwrap();
       pretty_assertions::assert_eq!(r#"{
     "type": "array",
     "logicalType": "map", // <-- this is missing!
     "items": {
       "type": "record",
       "name": "k12_v13",
       "fields": [
         {
           "name": "key",
           "type": "int",
           "field-id": 12
         },
         {
           "name": "value",
           "type": "string",
           "field-id": 13
         }
       ]
     }
   }"#, output);
   
       let logical_type = schema
           .custom_attributes()
           .unwrap()
           .get("logicalType");
   
       // !!! This fails !!!
       assert!(logical_type.is_some());
   
       Ok(())
   }
   ```


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to