Getting started

The basic stuff:

To use the library you need to:

Note:

Examples:

POJO class

import dk.vajhoej.record.FieldType;
import dk.vajhoej.record.Struct;
import dk.vajhoej.record.StructField;

@Struct
public class Data {
    @StructField(n=0,type=FieldType.INT4)
    private int iv;
    @StructField(n=1,type=FieldType.FP8)
    private double xv;
    @StructField(n=2,type=FieldType.FIXSTR,length=8,encoding="ISO-8859-1")
    private String sv;
	public int getIv() {
        return iv;
    }
    public void setIv(int iv) {
        this.iv = iv;
    }
    public double getXv() {
        return xv;
    }
    public void setXv(double xv) {
        this.xv = xv;
    }
    public String getSv() {
        return sv;
    }
    public void setSv(String sv) {
        this.sv = sv;
    }
}

The class got a @Struct annotation. Each field in the class got a @StructField annotation with an element n that determines the order of the fields and an element type that describes the datatype in the native struct plus some optional elements that are needed for some field types.

Code fragments

// read
StructReader sr = new StructReader(somebytearray);
Data obj = sr.read(Data.class);
// write
Data obj = new Data();
...
StructWriter sw = new StructWriter();
sw.write(obj);
byte[] ba = sw.GetBytes();

The advanced stuff:

Arrays:

To specify a field as an array put an @Array annotation on the field and make the Java type an array.

Sub structs:

To specify a field as a sub struct just specify type=FieldType.STRUCT in the @StructField annotation.

Polymorphism:

The Record library supports polymorphism in records.

You must use the @Selector annotation on the last field in the super class.

import dk.vajhoej.record.Alignment;
import dk.vajhoej.record.FieldType;
import dk.vajhoej.record.Struct;
import dk.vajhoej.record.StructField;
import dk.vajhoej.record.Selector;
import dk.vajhoej.record.SubType;

@Struct
public class Data {
    @StructField(n=0,type=FieldType.INT4)
    protected int id;
    @StructField(n=1,type=FieldType.INT4)
    @Selector(subtypes={@SubType(value=1,type=DataX.class),
                        @SubType(value=3,type=DataY.class)})
    protected int typ;
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public int getTyp() {
        return typ;
    }
    public void setTyp(int typ) {
        this.typ = typ;
    }
}

Usage is as simple as:

Data obj = sr.read(Data.class);

This will actually read DataX or DataY instances depending on the value of the typ field.

Note that the numbering of the struct fields continue in the sub class - it does not reset to zero.

More info about defining structs:

Struct
documentation
StructField
documentation
FieldType
documentation
ArrayField
documentation
Selector
documentation
SubType
documentation

The fast stuff:

Concept:

The API described above read/write by runtime analyzing the class and interpreting the output from the analysis.

The fast API analyze the class once and generate Java code dynamically to read/write using the Javassist library.

The annotation son the POJO classes are the same.

Note that not all features are supported in fast API - anything dynamic with length providers etc. does not work.

Simple example:

// read
FastStructReader<Data> fsr = CodeGen.genReader(Data.class);
fsr.init(somebytearray);
Data obj = fsr.read(Data.class);
// write
Data obj = new Data();
...
FastStructWriter fsw = CodGen.genWriter(Data.class);
fsw.write(obj);
byte[] ba = sw.GetBytes();

Sub class example:

// read
Map<Class<? extends Data>, FastStructReader<? extends Data>> map = new HashMap<Class<? extends Data>, FastStructReader<? extends Data>>();
map.put(DataX.class, CodeGen.genReader(DataX.class));
map.put(DataY.class, CodeGen.genReader(DataY.class));
FastStructReader<Data> fsr = new CompositFastStructReader<Data>(Data.class, map);
fsr.init(somebytearray);
Data obj = fsr.read(Data.class);
// write
Data obj = new Data();
...
Map<Class<? extends Data>, FastStructReader<? extends Data>> map = new HashMap<Class<? extends Data>, FastStructReader<? extends Data>>();
map.put(DataX.class, CodeGen.genReader(DataX.class));
map.put(DataY.class, CodeGen.genReader(DataY.class));
FastStructWriter<Object> fsw = new CompositFastStructWriter(map);
fsw.write(obj);
byte[] ba = sw.GetBytes();