codelipenghui edited a comment on issue #5503: [Schema]GenericData$Record cannot be cast URL: https://github.com/apache/pulsar/issues/5503#issuecomment-590084502 The problem is we should specify the correct namespace and name in the JSON definition. I have written a demo in java: ```java package org.apache.pulsar.client.impl; import org.apache.pulsar.client.api.schema.SchemaDefinition; import org.apache.pulsar.client.impl.schema.AvroSchema; import org.testng.Assert; import org.testng.annotations.Test; import java.util.Objects; public class SchemaTest { @Test public void test() { SchemaDefinition<User> sd = SchemaDefinition.<User>builder().withJsonDef("{\n" + " \"type\": \"record\",\n" + " \"name\": \"User\",\n" + " \"namespace\": \"org.apache.pulsar.client.impl.SchemaTest\",\n" + " \"fields\": [\n" + " {\n" + " \"name\": \"id\",\n" + " \"type\": [\n" + " \"null\",\n" + " \"int\"\n" + " ]\n" + " },\n" + " {\n" + " \"name\": \"name\",\n" + " \"type\": [\n" + " \"null\",\n" + " \"string\"\n" + " ]\n" + " }\n" + " ]\n" + " }").build(); AvroSchema<User> schema = AvroSchema.of(sd); User user = new User(); user.setId(1); user.setName("penghui"); byte[] encoded = schema.encode(user); User decoded = schema.decode(encoded); Assert.assertEquals(user, decoded); } private static class User { private Integer id; private String name; public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } @Override public boolean equals(Object o) { if (this == o) return true; if (o == null || getClass() != o.getClass()) return false; User user = (User) o; return Objects.equals(id, user.id) && Objects.equals(name, user.name); } @Override public int hashCode() { return Objects.hash(id, name); } } } ``` Avro use full name(`namespace` + "." + `name`) to get Class for decoding data. GenericData uses If class not found. Here is source code of `SpecificData` in avro, and `SpecificData` is `GenericData`'s subclass, if the class not found, will call `supper.newRecord`, this will introduce `GenericRecord`. ```java public Object newRecord(Object old, Schema schema) { Class c = getClass(schema); if (c == null) return super.newRecord(old, schema); // punt to generic return (c.isInstance(old) ? old : newInstance(c, schema)); } ```
---------------------------------------------------------------- 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. For queries about this service, please contact Infrastructure at: [email protected] With regards, Apache Git Services
