Question

I am trying to learn Apache Avro and I have started with simple tutorial for Avro. I am trying to use a JSON Schema to load the data. Below is my Simple example-

public class AvroExample {

    public static Schema SCHEMA; // writer's schema
    public static Schema SCHEMA2; // reader's schema

    private String name;
    private int age;
    private String[] mails;
    private AvroExample boss;

    static {
        try {

            SCHEMA = Schema.parse(AvroExample.class.getResourceAsStream("Employee.avsc"));
            SCHEMA2 = Schema.parse(AvroExample.class.getResourceAsStream("Employee2.avsc"));
        } catch (Exception e) {
            System.out.println("Couldn't load a schema: " + e.getMessage());
        }
    }

    // some more code

}

But somehow this line, always give me exception-

SCHEMA = Schema.parse(AvroExample.class.getResourceAsStream("Employee.avsc"));

as- Couldn't load a schema: java.lang.NullPointerException

I believe somehow, it is not able to load the file properly or I am loading the file in a wrong way.

This is the file content-

{
  "type": "record", 
  "name": "Employee", 
  "fields": [
      {"name": "name", "type": "string"},
      {"name": "age", "type": "int"},
      {"name": "emails", "type": {"type": "array", "items": "string"}},
      {"name": "boss", "type": ["Employee","null"]}
  ]
}

Below is the picture of my workspace which shows where I have put those two avsc files-

enter image description here

Can anybody help me with this?

Was it helpful?

Solution

With the project setup you've shown us, your classpath will likely look like

/root
    /Employee.avsc
    /Employee2.avsc
    /com
        /rjamal
            /avro
                /test
                    /AvroExperiment
                        /...

In other words, the two avsc files will be at the root of the classpath. The method call

AvroExample.class.getResourceAsStream("Employee.avsc")

looks for the resource in the package the AvroExample class is in.

To make it relative to the root of the classpath, prefix your path with a /.

AvroExample.class.getResourceAsStream("/Employee.avsc")

Check the javadoc

Before delegation, an absolute resource name is constructed from the given resource name using this algorithm:

  • If the name begins with a '/' ('\u002f'), then the absolute name of the resource is the portion of the name following the '/'.
  • Otherwise, the absolute name is of the following form: modified_package_name/name

    Where the modified_package_name is the package name of this object with '/' substituted for '.' ('\u002e').

Emphasis mine.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top