use of net.morimekta.providence.descriptor.PMap in project providence by morimekta.
the class TProtocolSerializer method readTypedValue.
private Object readTypedValue(byte tType, PDescriptor type, TProtocol protocol, boolean allowNull) throws TException, SerializerException {
if (tType != forType(type.getType())) {
throw new SerializerException("Expected type " + asString(forType(type.getType())) + " but found " + asString(tType));
}
switch(tType) {
case BinaryType.BOOL:
return protocol.readBool();
case BinaryType.BYTE:
return protocol.readByte();
case BinaryType.I16:
return protocol.readI16();
case BinaryType.I32:
if (PType.ENUM == type.getType()) {
PEnumDescriptor<?> et = (PEnumDescriptor<?>) type;
PEnumBuilder<?> eb = et.builder();
int value = protocol.readI32();
eb.setById(value);
if (!eb.valid() && !allowNull) {
throw new SerializerException("Invalid enum value " + value + " for " + et.getQualifiedName());
}
return eb.build();
} else {
return protocol.readI32();
}
case BinaryType.I64:
return protocol.readI64();
case BinaryType.DOUBLE:
return protocol.readDouble();
case BinaryType.STRING:
if (type == PPrimitive.BINARY) {
ByteBuffer buffer = protocol.readBinary();
return Binary.wrap(buffer.array());
}
return protocol.readString();
case BinaryType.STRUCT:
return readMessage(protocol, (PMessageDescriptor<?, ?>) type);
case BinaryType.LIST:
TList listInfo = protocol.readListBegin();
PList<Object> lDesc = (PList<Object>) type;
PDescriptor liDesc = lDesc.itemDescriptor();
PList.Builder<Object> list = lDesc.builder();
for (int i = 0; i < listInfo.size; ++i) {
list.add(readTypedValue(listInfo.elemType, liDesc, protocol, false));
}
protocol.readListEnd();
return list.build();
case BinaryType.SET:
TSet setInfo = protocol.readSetBegin();
PSet<Object> sDesc = (PSet<Object>) type;
PDescriptor siDesc = sDesc.itemDescriptor();
PSet.Builder<Object> set = sDesc.builder();
for (int i = 0; i < setInfo.size; ++i) {
set.add(readTypedValue(setInfo.elemType, siDesc, protocol, false));
}
protocol.readSetEnd();
return set.build();
case BinaryType.MAP:
TMap mapInfo = protocol.readMapBegin();
PMap<Object, Object> mDesc = (PMap<Object, Object>) type;
PDescriptor mkDesc = mDesc.keyDescriptor();
PDescriptor miDesc = mDesc.itemDescriptor();
PMap.Builder<Object, Object> map = mDesc.builder();
for (int i = 0; i < mapInfo.size; ++i) {
Object key = readTypedValue(mapInfo.keyType, mkDesc, protocol, false);
Object val = readTypedValue(mapInfo.valueType, miDesc, protocol, false);
map.put(key, val);
}
protocol.readMapEnd();
return map.build();
default:
throw new SerializerException("Unsupported protocol field type: " + tType);
}
}
use of net.morimekta.providence.descriptor.PMap in project providence by morimekta.
the class TProtocolSerializer method writeTypedValue.
private void writeTypedValue(Object item, PDescriptor type, TProtocol protocol) throws TException, SerializerException {
switch(type.getType()) {
case BOOL:
protocol.writeBool((Boolean) item);
break;
case BYTE:
protocol.writeByte((Byte) item);
break;
case I16:
protocol.writeI16((Short) item);
break;
case I32:
protocol.writeI32((Integer) item);
break;
case I64:
protocol.writeI64((Long) item);
break;
case DOUBLE:
protocol.writeDouble((Double) item);
break;
case STRING:
protocol.writeString((String) item);
break;
case BINARY:
protocol.writeBinary(((Binary) item).getByteBuffer());
break;
case ENUM:
PEnumValue<?> value = (PEnumValue<?>) item;
protocol.writeI32(value.asInteger());
break;
case MESSAGE:
writeMessage((PMessage<?, ?>) item, protocol);
break;
case LIST:
PList<?> lType = (PList<?>) type;
List<?> list = (List<?>) item;
TList listInfo = new TList(forType(lType.itemDescriptor().getType()), list.size());
protocol.writeListBegin(listInfo);
for (Object i : list) {
writeTypedValue(i, lType.itemDescriptor(), protocol);
}
protocol.writeListEnd();
break;
case SET:
PSet<?> sType = (PSet<?>) type;
Set<?> set = (Set<?>) item;
TSet setInfo = new TSet(forType(sType.itemDescriptor().getType()), set.size());
protocol.writeSetBegin(setInfo);
for (Object i : set) {
writeTypedValue(i, sType.itemDescriptor(), protocol);
}
protocol.writeSetEnd();
break;
case MAP:
PMap<?, ?> mType = (PMap<?, ?>) type;
Map<?, ?> map = (Map<?, ?>) item;
protocol.writeMapBegin(new TMap(forType(mType.keyDescriptor().getType()), forType(mType.itemDescriptor().getType()), map.size()));
for (Map.Entry<?, ?> entry : map.entrySet()) {
writeTypedValue(entry.getKey(), mType.keyDescriptor(), protocol);
writeTypedValue(entry.getValue(), mType.itemDescriptor(), protocol);
}
protocol.writeMapEnd();
break;
default:
break;
}
}
use of net.morimekta.providence.descriptor.PMap in project providence by morimekta.
the class FastBinarySerializer method readFieldValue.
@SuppressWarnings("unchecked")
private Object readFieldValue(@Nonnull LittleEndianBinaryReader in, int type, @Nullable PDescriptor descriptor) throws IOException {
switch(type) {
case NONE:
return Boolean.FALSE;
case TRUE:
return Boolean.TRUE;
case VARINT:
{
if (descriptor == null) {
in.readLongVarint();
return null;
}
switch(descriptor.getType()) {
case BOOL:
return in.readIntVarint() != 0;
case BYTE:
return (byte) in.readIntZigzag();
case I16:
return (short) in.readIntZigzag();
case I32:
return in.readIntZigzag();
case I64:
return in.readLongZigzag();
case ENUM:
{
PEnumBuilder<?> builder = ((PEnumDescriptor<?>) descriptor).builder();
builder.setById(in.readIntZigzag());
return builder.build();
}
default:
{
throw new SerializerException("");
}
}
}
case FIXED_64:
return in.expectDouble();
case BINARY:
{
int len = in.readIntVarint();
byte[] data = in.expectBytes(len);
if (descriptor != null) {
switch(descriptor.getType()) {
case STRING:
return new String(data, StandardCharsets.UTF_8);
case BINARY:
return Binary.wrap(data);
default:
throw new SerializerException("");
}
} else {
return null;
}
}
case MESSAGE:
if (descriptor == null) {
consumeMessage(in);
return null;
}
return readMessage(in, (PMessageDescriptor<?, ?>) descriptor);
case COLLECTION:
if (descriptor == null) {
final int len = in.readIntVarint();
final int tag = in.readIntVarint();
final int vtype = tag & 0x07;
final int ktype = tag > 0x07 ? tag >>> 3 : vtype;
for (int i = 0; i < len; ++i) {
if (i % 2 == 0) {
readFieldValue(in, ktype, null);
} else {
readFieldValue(in, vtype, null);
}
}
return null;
} else if (descriptor.getType() == PType.MAP) {
PMap<Object, Object> ct = (PMap<Object, Object>) descriptor;
PDescriptor kt = ct.keyDescriptor();
PDescriptor vt = ct.itemDescriptor();
PMap.Builder<Object, Object> out = ct.builder();
final int len = in.readIntVarint();
final int tag = in.readIntVarint();
final int vtype = tag & 0x07;
final int ktype = tag > 0x07 ? tag >>> 3 : vtype;
for (int i = 0; i < len; ++i, ++i) {
Object key = readFieldValue(in, ktype, kt);
Object value = readFieldValue(in, vtype, vt);
if (key != null && value != null) {
out.put(key, value);
} else if (readStrict) {
if (key == null) {
throw new SerializerException("Unknown enum key in map");
}
throw new SerializerException("Null value in map");
}
}
return out.build();
} else if (descriptor.getType() == PType.LIST) {
PList<Object> ct = (PList<Object>) descriptor;
PDescriptor it = ct.itemDescriptor();
PList.Builder<Object> out = ct.builder();
final int len = in.readIntVarint();
final int vtype = in.readIntVarint() & 0x07;
for (int i = 0; i < len; ++i) {
Object item = readFieldValue(in, vtype, it);
if (item != null) {
out.add(item);
} else if (readStrict) {
throw new SerializerException("Null value in list");
}
}
return out.build();
} else if (descriptor.getType() == PType.SET) {
PSet<Object> ct = (PSet<Object>) descriptor;
PDescriptor it = ct.itemDescriptor();
PSet.Builder<Object> out = ct.builder();
final int len = in.readIntVarint();
final int vtype = in.readIntVarint() & 0x07;
for (int i = 0; i < len; ++i) {
Object item = readFieldValue(in, vtype, it);
if (item != null) {
out.add(item);
} else if (readStrict) {
throw new SerializerException("Null value in set");
}
}
return out.build();
} else {
throw new SerializerException("Type " + descriptor.getType() + " not compatible with collection data");
}
default:
throw new Error("Unreachable code reached");
}
}
use of net.morimekta.providence.descriptor.PMap in project providence by morimekta.
the class BinaryFormatUtils method readFieldValue.
/**
* Read a field value from stream.
*
* @param in The stream to consume.
* @param fieldInfo The field info about the content.
* @param fieldType The type to generate content for.
* @param strict If the field should be read strictly.
* @return The field value, or null if no type.
* @throws IOException If unable to read from stream or invalid field type.
*/
public static Object readFieldValue(BigEndianBinaryReader in, FieldInfo fieldInfo, PDescriptor fieldType, boolean strict) throws IOException {
if (fieldType != null && forType(fieldType.getType()) != fieldInfo.type) {
throw new SerializerException("Wrong field type for id=%d: expected %s, got %s", fieldInfo.id, asString(forType(fieldType.getType())), asString(fieldInfo.getType()));
}
switch(fieldInfo.type) {
case BinaryType.VOID:
return Boolean.TRUE;
case BinaryType.BOOL:
return in.expectByte() != 0;
case BinaryType.BYTE:
return in.expectByte();
case BinaryType.I16:
return in.expectShort();
case BinaryType.I32:
int val = in.expectInt();
if (fieldType != null && fieldType instanceof PEnumDescriptor) {
@SuppressWarnings("unchecked") PEnumBuilder builder = ((PEnumDescriptor<?>) fieldType).builder();
builder.setById(val);
return builder.build();
} else {
return val;
}
case BinaryType.I64:
return in.expectLong();
case BinaryType.DOUBLE:
return in.expectDouble();
case BinaryType.STRING:
int len = in.expectUInt32();
byte[] data = in.expectBytes(len);
if (fieldType != null && fieldType.getType() == PType.STRING) {
return new String(data, StandardCharsets.UTF_8);
} else {
return Binary.wrap(data);
}
case BinaryType.STRUCT:
{
if (fieldType == null) {
consumeMessage(in);
return null;
}
return readMessage(in, (PMessageDescriptor<?, ?>) fieldType, strict);
}
case BinaryType.MAP:
{
final byte keyT = in.expectByte();
final byte itemT = in.expectByte();
final int size = in.expectUInt32();
PDescriptor keyType = null;
PDescriptor valueType = null;
PMap.Builder<Object, Object> out;
if (fieldType != null) {
@SuppressWarnings("unchecked") PMap<Object, Object> mapType = (PMap<Object, Object>) fieldType;
keyType = mapType.keyDescriptor();
valueType = mapType.itemDescriptor();
out = mapType.builder();
} else {
out = new PMap.DefaultBuilder<>();
}
FieldInfo keyInfo = new FieldInfo(1, keyT);
FieldInfo itemInfo = new FieldInfo(2, itemT);
for (int i = 0; i < size; ++i) {
Object key = readFieldValue(in, keyInfo, keyType, strict);
Object value = readFieldValue(in, itemInfo, valueType, strict);
if (key != null && value != null) {
out.put(key, value);
} else if (strict) {
if (key == null) {
throw new SerializerException("Null key in map");
} else {
throw new SerializerException("Null value in map");
}
}
}
return out.build();
}
case BinaryType.SET:
{
final byte itemT = in.expectByte();
final int size = in.expectUInt32();
PDescriptor entryType = null;
PSet.Builder<Object> out;
if (fieldType != null) {
@SuppressWarnings("unchecked") PSet<Object> setType = (PSet<Object>) fieldType;
entryType = setType.itemDescriptor();
out = setType.builder();
} else {
out = new PSet.DefaultBuilder<>();
}
FieldInfo itemInfo = new FieldInfo(0, itemT);
for (int i = 0; i < size; ++i) {
Object value = readFieldValue(in, itemInfo, entryType, strict);
if (value != null) {
out.add(value);
} else if (strict) {
throw new SerializerException("Null value in set");
}
}
return out.build();
}
case BinaryType.LIST:
{
final byte itemT = in.expectByte();
final int size = in.expectUInt32();
PDescriptor entryType = null;
PList.Builder<Object> out;
if (fieldType != null) {
@SuppressWarnings("unchecked") PList<Object> listType = (PList<Object>) fieldType;
entryType = listType.itemDescriptor();
out = listType.builder();
} else {
out = new PList.DefaultBuilder<>();
}
FieldInfo itemInfo = new FieldInfo(0, itemT);
for (int i = 0; i < size; ++i) {
Object value = readFieldValue(in, itemInfo, entryType, strict);
if (value != null) {
out.add(value);
} else if (strict) {
throw new SerializerException("Null value in list");
}
}
return out.build();
}
default:
throw new SerializerException("unknown data type: " + fieldInfo.getType());
}
}
use of net.morimekta.providence.descriptor.PMap in project providence by morimekta.
the class BuilderCommonMemberFormatter method appendAdder.
private void appendAdder(JMessage message, JField field) throws GeneratorException {
BlockCommentBuilder comment = new BlockCommentBuilder(writer);
if (field.hasComment()) {
comment.comment(field.comment());
} else if (field.type() == PType.MAP) {
comment.comment("Adds a mapping to " + field.name() + ".");
} else {
comment.comment("Adds entries to " + field.name() + ".");
}
comment.newline();
if (field.type() == PType.MAP) {
comment.param_("key", "The inserted key").param_("value", "The inserted value");
} else {
comment.param_("values", "The added value");
}
comment.return_("The builder");
if (JAnnotation.isDeprecated(field)) {
String reason = field.field().getAnnotationValue(ThriftAnnotation.DEPRECATED);
if (reason != null && reason.trim().length() > 0) {
comment.deprecated_(reason);
}
}
comment.finish();
if (JAnnotation.isDeprecated(field)) {
writer.appendln(JAnnotation.DEPRECATED);
}
writer.appendln(JAnnotation.NON_NULL);
switch(field.type()) {
case MAP:
{
PMap<?, ?> mType = (PMap<?, ?>) field.field().getDescriptor();
String mkType = helper.getValueType(mType.keyDescriptor());
String miType = helper.getValueType(mType.itemDescriptor());
writer.formatln("public _Builder %s(%s key, %s value) {", field.adder(), mkType, miType).begin();
if (message.isUnion()) {
writer.formatln("%s = _Field.%s;", UNION_FIELD, field.fieldEnum());
writer.appendln("modified = true;");
} else {
writer.formatln("optionals.set(%d);", field.index());
writer.formatln("modified.set(%d);", field.index());
}
writer.formatln("%s().put(key, value);", field.mutable()).appendln("return this;").end().appendln('}').newline();
break;
}
case SET:
case LIST:
{
PContainer<?> lType = (PContainer<?>) field.field().getDescriptor();
String liType = helper.getValueType(lType.itemDescriptor());
writer.formatln("public _Builder %s(%s... values) {", field.adder(), liType).begin();
if (message.isUnion()) {
writer.formatln("%s = _Field.%s;", UNION_FIELD, field.fieldEnum());
writer.appendln("modified = true;");
} else {
writer.formatln("optionals.set(%d);", field.index());
writer.formatln("modified.set(%d);", field.index());
}
writer.formatln("%s _container = %s();", field.fieldType(), field.mutable()).formatln("for (%s item : values) {", liType).begin().appendln("_container.add(item);").end().appendln('}').appendln("return this;").end().appendln('}').newline();
break;
}
}
}
Aggregations