func testSerializeEmbMap(t *testing.T, off int, mp interface{}, origBase64 string) {
	buf := bytes.NewBuffer(nil)
	for i := 0; i < off; i++ {
		buf.WriteByte(0)
	}
	if err := (binaryRecordFormatV0{}).writeEmbeddedMap(rw.NewWriter(buf), off, mp); err != nil {
		t.Fatal(err)
	}
	testBase64Compare(t, buf.Bytes(), origBase64)
	r := rw.NewReadSeeker(bytes.NewReader(buf.Bytes()))
	out, err := (binaryRecordFormatV0{}).readEmbeddedMap(r, nil)
	if err != nil {
		t.Fatal(err)
	}
	if reflect.TypeOf(out) != reflect.TypeOf(mp) {
		t.Logf("types are not the same: %T -> %T", mp, out)
	}
}
func TestSerializeDecimalV0(t *testing.T) {
	buf := bytes.NewBuffer(nil)
	val := big.NewInt(123456789)
	if err := (binaryRecordFormatV0{}).writeSingleValue(rw.NewWriter(buf), 0, val, orient.DECIMAL, orient.UNKNOWN); err != nil {
		t.Fatal(err)
	}
	testBase64Compare(t, buf.Bytes(), "AAAAAAAAAAQHW80V")

	r := rw.NewReadSeeker(bytes.NewReader(buf.Bytes()))
	out, err := (binaryRecordFormatV0{}).readSingleValue(r, orient.DECIMAL, nil)
	if err != nil {
		t.Fatal(err)
	}
	if val2, ok := out.(orient.Decimal); !ok {
		t.Fatalf("expected Decimal, got: %T", out)
	} else if val.Cmp(val2.Value) != 0 {
		t.Fatalf("values differs: %v != %v", val, val2)
	}
}
func TestSerializeDatetimeV0(t *testing.T) {
	buf := bytes.NewBuffer(nil)
	val := time.Now()
	val = time.Unix(val.Unix(), int64(val.Nanosecond()/1e6)*1e6) // precise to milliseconds
	if err := (binaryRecordFormatV0{}).writeSingleValue(rw.NewWriter(buf), 0, val, orient.DATETIME, orient.UNKNOWN); err != nil {
		t.Fatal(err)
	}

	r := rw.NewReadSeeker(bytes.NewReader(buf.Bytes()))
	out, err := (binaryRecordFormatV0{}).readSingleValue(r, orient.DATETIME, nil)
	if err != nil {
		t.Fatal(err)
	}
	if val2, ok := out.(time.Time); !ok {
		t.Fatalf("expected Time, got: %T", out)
	} else if !val.Equal(val2) {
		t.Fatalf("values differs: %v != %v", val, val2)
	}
}
func (f BinaryRecordFormat) FromStream(data []byte) (out orient.ORecord, err error) {
	if len(data) < 1 {
		err = io.ErrUnexpectedEOF
		return
	}

	r := bytes.NewReader(data)
	br := rw.NewReadSeeker(r)
	vers := br.ReadByte()
	if err = br.Err(); err != nil {
		return
	}

	// TODO: support partial deserialization (only certain fields)

	ser := binaryFormatVerions[vers]()
	ser.SetGlobalPropertyFunc(f.fnc)
	doc := orient.NewEmptyDocument()
	if err = ser.Deserialize(doc, br); err != nil {
		return
	}
	return doc, nil
}