deployed 2.0.0.RELEASE,升级相关依赖
使用RuntimeSchema 使用反射(Field)取代内省(PropertyDescriptor),以兼容android平台master
parent
a6e0e7c819
commit
c305df04b9
6
pom.xml
6
pom.xml
|
@ -3,7 +3,7 @@
|
|||
<modelVersion>4.0.0</modelVersion>
|
||||
<groupId>io.github.yezhihao</groupId>
|
||||
<artifactId>protostar</artifactId>
|
||||
<version>1.0.5.RELEASE</version>
|
||||
<version>2.0.0.RELEASE</version>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<name>Protostar</name>
|
||||
|
@ -50,13 +50,13 @@
|
|||
<dependency>
|
||||
<groupId>org.slf4j</groupId>
|
||||
<artifactId>slf4j-simple</artifactId>
|
||||
<version>1.7.30</version>
|
||||
<version>1.7.31</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.slf4j</groupId>
|
||||
<artifactId>slf4j-api</artifactId>
|
||||
<version>1.7.30</version>
|
||||
<version>1.7.31</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
package io.github.yezhihao.protostar;
|
||||
|
||||
import io.github.yezhihao.protostar.annotation.Message;
|
||||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
import io.github.yezhihao.protostar.util.ClassUtils;
|
||||
|
||||
import java.beans.Introspector;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
@ -14,7 +14,7 @@ import java.util.Map;
|
|||
*/
|
||||
public class DefaultLoadStrategy extends LoadStrategy {
|
||||
|
||||
private Map<String, Map<Integer, Schema<?>>> typeClassMapping = new HashMap(140);
|
||||
private Map<String, Map<Integer, RuntimeSchema<?>>> typeClassMapping = new HashMap(140);
|
||||
|
||||
public DefaultLoadStrategy() {
|
||||
}
|
||||
|
@ -26,33 +26,32 @@ public class DefaultLoadStrategy extends LoadStrategy {
|
|||
if (message != null) {
|
||||
int[] values = message.value();
|
||||
for (int typeId : values)
|
||||
loadSchema(typeClassMapping, typeId, type);
|
||||
loadRuntimeSchema(typeClassMapping, typeId, type);
|
||||
}
|
||||
}
|
||||
Introspector.flushCaches();
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> Schema<T> getSchema(Class<T> typeClass, Integer version) {
|
||||
Map<Integer, Schema<?>> schemas = typeClassMapping.get(typeClass.getName());
|
||||
public <T> RuntimeSchema<T> getRuntimeSchema(Class<T> typeClass, Integer version) {
|
||||
Map<Integer, RuntimeSchema<?>> schemas = typeClassMapping.get(typeClass.getName());
|
||||
if (schemas == null) {
|
||||
schemas = loadSchema(typeClassMapping, typeClass);
|
||||
schemas = loadRuntimeSchema(typeClassMapping, typeClass);
|
||||
}
|
||||
if (schemas == null) return null;
|
||||
return (Schema<T>) schemas.get(version);
|
||||
return (RuntimeSchema<T>) schemas.get(version);
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> Map<Integer, Schema<T>> getSchema(Class<T> typeClass) {
|
||||
Map<Integer, Schema<?>> schemas = typeClassMapping.get(typeClass.getName());
|
||||
public <T> Map<Integer, RuntimeSchema<T>> getRuntimeSchema(Class<T> typeClass) {
|
||||
Map<Integer, RuntimeSchema<?>> schemas = typeClassMapping.get(typeClass.getName());
|
||||
if (schemas == null) {
|
||||
schemas = loadSchema(typeClassMapping, typeClass);
|
||||
schemas = loadRuntimeSchema(typeClassMapping, typeClass);
|
||||
}
|
||||
if (schemas == null) return null;
|
||||
|
||||
HashMap<Integer, Schema<T>> result = new HashMap<>(schemas.size());
|
||||
for (Map.Entry<Integer, Schema<?>> entry : schemas.entrySet()) {
|
||||
result.put(entry.getKey(), (Schema<T>) entry.getValue());
|
||||
HashMap<Integer, RuntimeSchema<T>> result = new HashMap<>(schemas.size());
|
||||
for (Map.Entry<Integer, RuntimeSchema<?>> entry : schemas.entrySet()) {
|
||||
result.put(entry.getKey(), (RuntimeSchema<T>) entry.getValue());
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -10,7 +10,6 @@ import io.github.yezhihao.protostar.schema.*;
|
|||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.beans.PropertyDescriptor;
|
||||
import java.nio.ByteBuffer;
|
||||
import java.time.LocalDateTime;
|
||||
|
||||
|
@ -23,13 +22,13 @@ public abstract class FieldFactory {
|
|||
protected static Logger log = LoggerFactory.getLogger(FieldFactory.class.getSimpleName());
|
||||
public static boolean EXPLAIN = false;
|
||||
|
||||
public static BasicField create(Field field, PropertyDescriptor property) {
|
||||
return create(field, property, null);
|
||||
public static BasicField create(Field field, java.lang.reflect.Field f) {
|
||||
return create(field, f, null);
|
||||
}
|
||||
|
||||
public static BasicField create(Field field, PropertyDescriptor property, Schema schema) {
|
||||
public static BasicField create(Field field, java.lang.reflect.Field f, Schema schema) {
|
||||
DataType dataType = field.type();
|
||||
Class<?> typeClass = property.getPropertyType();
|
||||
Class<?> typeClass = f.getType();
|
||||
|
||||
Schema fieldSchema;
|
||||
switch (dataType) {
|
||||
|
@ -63,7 +62,7 @@ public abstract class FieldFactory {
|
|||
if (schema != null) {
|
||||
fieldSchema = ObjectSchema.getInstance(schema);
|
||||
} else {
|
||||
Convert convert = property.getReadMethod().getAnnotation(Convert.class);
|
||||
Convert convert = f.getAnnotation(Convert.class);
|
||||
fieldSchema = ConvertSchema.getInstance(convert.converter());
|
||||
}
|
||||
break;
|
||||
|
@ -71,7 +70,7 @@ public abstract class FieldFactory {
|
|||
fieldSchema = CollectionSchema.getInstance(schema);
|
||||
break;
|
||||
case MAP:
|
||||
Convert convert = property.getReadMethod().getAnnotation(Convert.class);
|
||||
Convert convert = f.getAnnotation(Convert.class);
|
||||
fieldSchema = ConvertSchema.getInstance(convert.converter());
|
||||
break;
|
||||
default:
|
||||
|
@ -82,19 +81,19 @@ public abstract class FieldFactory {
|
|||
BasicField result;
|
||||
if (EXPLAIN) {
|
||||
if (field.lengthSize() > 0) {
|
||||
result = new DynamicLengthField.Logger(field, property, fieldSchema);
|
||||
result = new DynamicLengthField.Logger(field, f, fieldSchema);
|
||||
} else if (field.length() > 0) {
|
||||
result = new FixedLengthField.Logger(field, property, fieldSchema);
|
||||
result = new FixedLengthField.Logger(field, f, fieldSchema);
|
||||
} else {
|
||||
result = new FixedField.Logger(field, property, fieldSchema);
|
||||
result = new FixedField.Logger(field, f, fieldSchema);
|
||||
}
|
||||
} else {
|
||||
if (field.lengthSize() > 0) {
|
||||
result = new DynamicLengthField(field, property, fieldSchema);
|
||||
result = new DynamicLengthField(field, f, fieldSchema);
|
||||
} else if (field.length() > 0) {
|
||||
result = new FixedLengthField(field, property, fieldSchema);
|
||||
result = new FixedLengthField(field, f, fieldSchema);
|
||||
} else {
|
||||
result = new FixedField(field, property, fieldSchema);
|
||||
result = new FixedField(field, f, fieldSchema);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
|
|
|
@ -5,11 +5,6 @@ import io.github.yezhihao.protostar.field.BasicField;
|
|||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
|
||||
import java.beans.BeanInfo;
|
||||
import java.beans.IntrospectionException;
|
||||
import java.beans.Introspector;
|
||||
import java.beans.PropertyDescriptor;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.ParameterizedType;
|
||||
import java.util.*;
|
||||
|
||||
|
@ -54,11 +49,11 @@ public abstract class IdStrategy {
|
|||
if (schema != null)
|
||||
return (Schema<T>) schema;
|
||||
|
||||
List<PropertyDescriptor> properties = findFieldProperties(typeClass);
|
||||
if (properties.isEmpty())
|
||||
List<java.lang.reflect.Field> fs = findFields(typeClass);
|
||||
if (fs.isEmpty())
|
||||
return null;
|
||||
|
||||
List<BasicField> fieldList = findFields(root, properties);
|
||||
List<BasicField> fieldList = findFields(root, fs);
|
||||
BasicField[] fields = fieldList.toArray(new BasicField[fieldList.size()]);
|
||||
Arrays.sort(fields);
|
||||
|
||||
|
@ -67,57 +62,44 @@ public abstract class IdStrategy {
|
|||
return (Schema<T>) schema;
|
||||
}
|
||||
|
||||
protected static List<PropertyDescriptor> findFieldProperties(Class typeClass) {
|
||||
BeanInfo beanInfo;
|
||||
try {
|
||||
beanInfo = Introspector.getBeanInfo(typeClass);
|
||||
} catch (IntrospectionException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
PropertyDescriptor[] properties = beanInfo.getPropertyDescriptors();
|
||||
List<PropertyDescriptor> result = new ArrayList<>(properties.length);
|
||||
protected static List<java.lang.reflect.Field> findFields(Class typeClass) {
|
||||
java.lang.reflect.Field[] fields = typeClass.getDeclaredFields();
|
||||
List<java.lang.reflect.Field> result = new ArrayList<>(fields.length);
|
||||
|
||||
for (PropertyDescriptor property : properties) {
|
||||
Method readMethod = property.getReadMethod();
|
||||
|
||||
if (readMethod != null) {
|
||||
if (readMethod.isAnnotationPresent(Field.class)) {
|
||||
result.add(property);
|
||||
}
|
||||
for (java.lang.reflect.Field f : fields) {
|
||||
if (f.isAnnotationPresent(Field.class)) {
|
||||
result.add(f);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
protected static List<BasicField> findFields(Map<Object, Schema> root, List<PropertyDescriptor> properties) {
|
||||
List<BasicField> fields = new ArrayList<>(properties.size());
|
||||
protected static List<BasicField> findFields(Map<Object, Schema> root, List<java.lang.reflect.Field> fs) {
|
||||
List<BasicField> fields = new ArrayList<>(fs.size());
|
||||
|
||||
for (PropertyDescriptor property : properties) {
|
||||
Method readMethod = property.getReadMethod();
|
||||
|
||||
Field field = readMethod.getDeclaredAnnotation(Field.class);
|
||||
for (java.lang.reflect.Field f : fs) {
|
||||
Field field = f.getDeclaredAnnotation(Field.class);
|
||||
if (field != null) {
|
||||
fillField(root, fields, property, field);
|
||||
fillField(root, fields, f, field);
|
||||
}
|
||||
}
|
||||
return fields;
|
||||
}
|
||||
|
||||
protected static void fillField(Map<Object, Schema> root, List<BasicField> fields, PropertyDescriptor propertyDescriptor, Field field) {
|
||||
Class typeClass = propertyDescriptor.getPropertyType();
|
||||
Method readMethod = propertyDescriptor.getReadMethod();
|
||||
protected static void fillField(Map<Object, Schema> root, List<BasicField> fields, java.lang.reflect.Field f, Field field) {
|
||||
Class typeClass = f.getType();
|
||||
|
||||
BasicField value;
|
||||
|
||||
if (field.type() == DataType.OBJ || field.type() == DataType.LIST) {
|
||||
if (Collection.class.isAssignableFrom(typeClass))
|
||||
typeClass = (Class) ((ParameterizedType) readMethod.getGenericReturnType()).getActualTypeArguments()[0];
|
||||
typeClass = (Class) ((ParameterizedType) f.getGenericType()).getActualTypeArguments()[0];
|
||||
loadSchema(root, typeClass);
|
||||
Schema schema = root.get(typeClass.getName());
|
||||
value = FieldFactory.create(field, propertyDescriptor, schema);
|
||||
value = FieldFactory.create(field, f, schema);
|
||||
fields.add(value);
|
||||
} else {
|
||||
value = FieldFactory.create(field, propertyDescriptor);
|
||||
value = FieldFactory.create(field, f);
|
||||
fields.add(value);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -5,55 +5,50 @@ import io.github.yezhihao.protostar.annotation.Fs;
|
|||
import io.github.yezhihao.protostar.field.BasicField;
|
||||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
|
||||
import java.beans.BeanInfo;
|
||||
import java.beans.IntrospectionException;
|
||||
import java.beans.Introspector;
|
||||
import java.beans.PropertyDescriptor;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.ParameterizedType;
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* Schema加载策略
|
||||
* RuntimeSchema加载策略
|
||||
* @author yezhihao
|
||||
* home https://gitee.com/yezhihao/jt808-server
|
||||
*/
|
||||
public abstract class LoadStrategy {
|
||||
|
||||
protected Map<Object, Map<Integer, Schema<?>>> typeIdMapping = new HashMap<>(64);
|
||||
protected Map<Object, Map<Integer, RuntimeSchema<?>>> typeIdMapping = new HashMap<>(64);
|
||||
|
||||
public abstract <T> Map<Integer, Schema<T>> getSchema(Class<T> typeClass);
|
||||
public abstract <T> Map<Integer, RuntimeSchema<T>> getRuntimeSchema(Class<T> typeClass);
|
||||
|
||||
public abstract <T> Schema<T> getSchema(Class<T> typeClass, Integer version);
|
||||
public abstract <T> RuntimeSchema<T> getRuntimeSchema(Class<T> typeClass, Integer version);
|
||||
|
||||
public Schema getSchema(Object typeId, Integer version) {
|
||||
Map<Integer, Schema<?>> schemaMap = typeIdMapping.get(typeId);
|
||||
public RuntimeSchema getRuntimeSchema(Object typeId, Integer version) {
|
||||
Map<Integer, RuntimeSchema<?>> schemaMap = typeIdMapping.get(typeId);
|
||||
if (schemaMap == null)
|
||||
return null;
|
||||
return schemaMap.get(version);
|
||||
}
|
||||
|
||||
protected void loadSchema(Map<String, Map<Integer, Schema<?>>> root, Object typeId, Class<?> typeClass) {
|
||||
Map<Integer, Schema<?>> schemas = typeIdMapping.get(typeId);
|
||||
protected void loadRuntimeSchema(Map<String, Map<Integer, RuntimeSchema<?>>> root, Object typeId, Class<?> typeClass) {
|
||||
Map<Integer, RuntimeSchema<?>> schemas = typeIdMapping.get(typeId);
|
||||
if (schemas == null) {
|
||||
schemas = loadSchema(root, typeClass);
|
||||
schemas = loadRuntimeSchema(root, typeClass);
|
||||
typeIdMapping.put(typeId, schemas);
|
||||
}
|
||||
}
|
||||
|
||||
protected Map<Integer, Schema<?>> loadSchema(Map<String, Map<Integer, Schema<?>>> root, Class<?> typeClass) {
|
||||
Map<Integer, Schema<?>> schemas = root.get(typeClass.getName());
|
||||
protected Map<Integer, RuntimeSchema<?>> loadRuntimeSchema(Map<String, Map<Integer, RuntimeSchema<?>>> root, Class<?> typeClass) {
|
||||
Map<Integer, RuntimeSchema<?>> schemas = root.get(typeClass.getName());
|
||||
//不支持循环引用
|
||||
if (schemas != null)
|
||||
return schemas;
|
||||
|
||||
List<PropertyDescriptor> properties = findFieldProperties(typeClass);
|
||||
if (properties.isEmpty())
|
||||
List<java.lang.reflect.Field> fs = findFields(typeClass);
|
||||
if (fs.isEmpty())
|
||||
return null;
|
||||
|
||||
root.put(typeClass.getName(), schemas = new HashMap(4));
|
||||
|
||||
Map<Integer, List<BasicField>> multiVersionFields = findMultiVersionFields(root, properties);
|
||||
Map<Integer, List<BasicField>> multiVersionFields = findMultiVersionFields(root, fs);
|
||||
for (Map.Entry<Integer, List<BasicField>> entry : multiVersionFields.entrySet()) {
|
||||
|
||||
Integer version = entry.getKey();
|
||||
|
@ -62,79 +57,68 @@ public abstract class LoadStrategy {
|
|||
BasicField[] fields = fieldList.toArray(new BasicField[fieldList.size()]);
|
||||
Arrays.sort(fields);
|
||||
|
||||
Schema schema = new RuntimeSchema(typeClass, version, fields);
|
||||
RuntimeSchema schema = new RuntimeSchema(typeClass, version, fields);
|
||||
schemas.put(version, schema);
|
||||
}
|
||||
return schemas;
|
||||
}
|
||||
|
||||
protected List<PropertyDescriptor> findFieldProperties(Class<?> typeClass) {
|
||||
BeanInfo beanInfo;
|
||||
try {
|
||||
beanInfo = Introspector.getBeanInfo(typeClass);
|
||||
} catch (IntrospectionException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
PropertyDescriptor[] properties = beanInfo.getPropertyDescriptors();
|
||||
List<PropertyDescriptor> result = new ArrayList<>(properties.length);
|
||||
protected List<java.lang.reflect.Field> findFields(Class<?> typeClass) {
|
||||
java.lang.reflect.Field[] fs = typeClass.getDeclaredFields();
|
||||
|
||||
for (PropertyDescriptor property : properties) {
|
||||
Method readMethod = property.getReadMethod();
|
||||
List<java.lang.reflect.Field> result = new ArrayList<>(fs.length);
|
||||
|
||||
if (readMethod != null) {
|
||||
if (readMethod.isAnnotationPresent(Fs.class) || readMethod.isAnnotationPresent(Field.class)) {
|
||||
result.add(property);
|
||||
}
|
||||
for (java.lang.reflect.Field f : fs) {
|
||||
if (f.isAnnotationPresent(Fs.class) || f.isAnnotationPresent(Field.class)) {
|
||||
result.add(f);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
protected Map<Integer, List<BasicField>> findMultiVersionFields(Map<String, Map<Integer, Schema<?>>> root, List<PropertyDescriptor> properties) {
|
||||
protected Map<Integer, List<BasicField>> findMultiVersionFields(Map<String, Map<Integer, RuntimeSchema<?>>> root, List<java.lang.reflect.Field> fs) {
|
||||
Map<Integer, List<BasicField>> multiVersionFields = new TreeMap<Integer, List<BasicField>>() {
|
||||
@Override
|
||||
public List<BasicField> get(Object key) {
|
||||
List result = super.get(key);
|
||||
if (result == null)
|
||||
super.put((Integer) key, result = new ArrayList<>(properties.size()));
|
||||
super.put((Integer) key, result = new ArrayList<>(fs.size()));
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
for (PropertyDescriptor property : properties) {
|
||||
Method readMethod = property.getReadMethod();
|
||||
for (java.lang.reflect.Field f : fs) {
|
||||
|
||||
Field field = readMethod.getDeclaredAnnotation(Field.class);
|
||||
Field field = f.getDeclaredAnnotation(Field.class);
|
||||
if (field != null) {
|
||||
fillField(root, multiVersionFields, property, field);
|
||||
fillField(root, multiVersionFields, f, field);
|
||||
} else {
|
||||
Field[] fields = readMethod.getDeclaredAnnotation(Fs.class).value();
|
||||
Field[] fields = f.getDeclaredAnnotation(Fs.class).value();
|
||||
for (int i = 0; i < fields.length; i++)
|
||||
fillField(root, multiVersionFields, property, fields[i]);
|
||||
fillField(root, multiVersionFields, f, fields[i]);
|
||||
}
|
||||
}
|
||||
return multiVersionFields;
|
||||
}
|
||||
|
||||
protected void fillField(Map<String, Map<Integer, Schema<?>>> root, Map<Integer, List<BasicField>> multiVersionFields, PropertyDescriptor propertyDescriptor, Field field) {
|
||||
Class<?> typeClass = propertyDescriptor.getPropertyType();
|
||||
Method readMethod = propertyDescriptor.getReadMethod();
|
||||
protected void fillField(Map<String, Map<Integer, RuntimeSchema<?>>> root, Map<Integer, List<BasicField>> multiVersionFields, java.lang.reflect.Field f, Field field) {
|
||||
Class<?> typeClass = f.getType();
|
||||
|
||||
BasicField value;
|
||||
int[] versions = field.version();
|
||||
|
||||
if (field.type() == DataType.OBJ || field.type() == DataType.LIST) {
|
||||
if (Collection.class.isAssignableFrom(typeClass))
|
||||
typeClass = (Class<?>) ((ParameterizedType) readMethod.getGenericReturnType()).getActualTypeArguments()[0];
|
||||
loadSchema(root, typeClass);
|
||||
typeClass = (Class<?>) ((ParameterizedType) f.getGenericType()).getActualTypeArguments()[0];
|
||||
loadRuntimeSchema(root, typeClass);
|
||||
for (int ver : versions) {
|
||||
Map<Integer, Schema<?>> schemaMap = root.getOrDefault(typeClass.getName(), Collections.EMPTY_MAP);
|
||||
Schema schema = schemaMap.get(ver);
|
||||
value = FieldFactory.create(field, propertyDescriptor, schema);
|
||||
Map<Integer, RuntimeSchema<?>> schemaMap = root.getOrDefault(typeClass.getName(), Collections.EMPTY_MAP);
|
||||
RuntimeSchema schema = schemaMap.get(ver);
|
||||
value = FieldFactory.create(field, f, schema);
|
||||
multiVersionFields.get(ver).add(value);
|
||||
}
|
||||
} else {
|
||||
value = FieldFactory.create(field, propertyDescriptor);
|
||||
value = FieldFactory.create(field, f);
|
||||
for (int ver : versions) {
|
||||
multiVersionFields.get(ver).add(value);
|
||||
}
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
package io.github.yezhihao.protostar;
|
||||
|
||||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
|
@ -24,15 +26,15 @@ public class ProtostarUtil {
|
|||
}
|
||||
}
|
||||
|
||||
public static Schema getSchema(Object typeId, Integer version) {
|
||||
return LOAD_STRATEGY.getSchema(typeId, version);
|
||||
public static RuntimeSchema getRuntimeSchema(Object typeId, Integer version) {
|
||||
return LOAD_STRATEGY.getRuntimeSchema(typeId, version);
|
||||
}
|
||||
|
||||
public static Schema getSchema(Class<?> typeClass, Integer version) {
|
||||
return LOAD_STRATEGY.getSchema(typeClass, version);
|
||||
public static RuntimeSchema getRuntimeSchema(Class<?> typeClass, Integer version) {
|
||||
return LOAD_STRATEGY.getRuntimeSchema(typeClass, version);
|
||||
}
|
||||
|
||||
public static <T> Map<Integer, Schema<T>> getSchema(Class<T> typeClass) {
|
||||
return LOAD_STRATEGY.getSchema(typeClass);
|
||||
public static <T> Map<Integer, RuntimeSchema<T>> getRuntimeSchema(Class<T> typeClass) {
|
||||
return LOAD_STRATEGY.getRuntimeSchema(typeClass);
|
||||
}
|
||||
}
|
|
@ -12,7 +12,7 @@ import java.lang.annotation.Target;
|
|||
* @author yezhihao
|
||||
* home https://gitee.com/yezhihao/jt808-server
|
||||
*/
|
||||
@Target(ElementType.METHOD)
|
||||
@Target(ElementType.FIELD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface Convert {
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@ import java.lang.annotation.*;
|
|||
* home https://gitee.com/yezhihao/jt808-server
|
||||
*/
|
||||
@Repeatable(Fs.class)
|
||||
@Target(ElementType.METHOD)
|
||||
@Target(ElementType.FIELD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface Field {
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@ import java.lang.annotation.Target;
|
|||
* @author yezhihao
|
||||
* home https://gitee.com/yezhihao/jt808-server
|
||||
*/
|
||||
@Target(ElementType.METHOD)
|
||||
@Target(ElementType.FIELD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface Fs {
|
||||
|
||||
|
|
|
@ -6,9 +6,6 @@ import io.netty.buffer.ByteBuf;
|
|||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.beans.PropertyDescriptor;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
/**
|
||||
* 固定长度的字段
|
||||
* @author yezhihao
|
||||
|
@ -19,23 +16,21 @@ public abstract class BasicField<T> implements Comparable<BasicField<T>> {
|
|||
|
||||
protected final int index;
|
||||
protected final int length;
|
||||
protected final String desc;
|
||||
protected final Method readMethod;
|
||||
protected final Method writeMethod;
|
||||
protected final PropertyDescriptor property;
|
||||
protected final Field field;
|
||||
protected final java.lang.reflect.Field f;
|
||||
|
||||
public BasicField(Field field, PropertyDescriptor property) {
|
||||
public BasicField(Field field, java.lang.reflect.Field f) {
|
||||
this.index = field.index();
|
||||
int length = field.length();
|
||||
if (length < 0)
|
||||
length = field.type().length;
|
||||
this.length = length;
|
||||
this.desc = field.desc();
|
||||
this.readMethod = property.getReadMethod();
|
||||
this.writeMethod = property.getWriteMethod();
|
||||
this.field = field;
|
||||
this.property = property;
|
||||
this.f = f;
|
||||
try {
|
||||
f.setAccessible(true);
|
||||
} catch (Exception e) {
|
||||
}
|
||||
}
|
||||
|
||||
public abstract boolean readFrom(ByteBuf input, Object message) throws Exception;
|
||||
|
@ -62,13 +57,12 @@ public abstract class BasicField<T> implements Comparable<BasicField<T>> {
|
|||
|
||||
@Override
|
||||
public String toString() {
|
||||
final StringBuilder sb = new StringBuilder(60);
|
||||
final StringBuilder sb = new StringBuilder(50);
|
||||
sb.append('{');
|
||||
sb.append("index=").append(index);
|
||||
sb.append(", length=").append(length);
|
||||
sb.append(", desc").append(desc);
|
||||
sb.append(", readMethod=").append(readMethod.getName());
|
||||
sb.append(", writeMethod=").append(writeMethod.getName());
|
||||
sb.append(", desc").append(field.desc());
|
||||
sb.append(", field=").append(f.getName());
|
||||
sb.append('}');
|
||||
return sb.toString();
|
||||
}
|
||||
|
|
|
@ -1,12 +1,10 @@
|
|||
package io.github.yezhihao.protostar.field;
|
||||
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.annotation.Field;
|
||||
import io.github.yezhihao.protostar.util.ByteBufUtils;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.util.ByteBufUtils;
|
||||
|
||||
import java.beans.PropertyDescriptor;
|
||||
|
||||
/**
|
||||
* 动态长度的字段
|
||||
|
@ -19,8 +17,8 @@ public class DynamicLengthField<T> extends BasicField<T> {
|
|||
|
||||
protected final int lengthSize;
|
||||
|
||||
public DynamicLengthField(Field field, PropertyDescriptor property, Schema<T> schema) {
|
||||
super(field, property);
|
||||
public DynamicLengthField(Field field, java.lang.reflect.Field f, Schema<T> schema) {
|
||||
super(field, f);
|
||||
this.schema = schema;
|
||||
this.lengthSize = field.lengthSize();
|
||||
}
|
||||
|
@ -30,12 +28,12 @@ public class DynamicLengthField<T> extends BasicField<T> {
|
|||
if (!input.isReadable(length))
|
||||
return false;
|
||||
Object value = schema.readFrom(input, length);
|
||||
writeMethod.invoke(message, value);
|
||||
f.set(message, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void writeTo(ByteBuf output, Object message) throws Exception {
|
||||
Object value = readMethod.invoke(message);
|
||||
Object value = f.get(message);
|
||||
if (value != null) {
|
||||
int begin = output.writerIndex();
|
||||
output.writeBytes(ByteBufUtils.BLOCKS[lengthSize]);
|
||||
|
@ -55,8 +53,8 @@ public class DynamicLengthField<T> extends BasicField<T> {
|
|||
|
||||
public static class Logger<T> extends DynamicLengthField<T> {
|
||||
|
||||
public Logger(Field field, PropertyDescriptor property, Schema<T> schema) {
|
||||
super(field, property, schema);
|
||||
public Logger(Field field, java.lang.reflect.Field f, Schema<T> schema) {
|
||||
super(field, f, schema);
|
||||
}
|
||||
|
||||
public boolean readFrom(ByteBuf input, Object message) throws Exception {
|
||||
|
@ -66,18 +64,18 @@ public class DynamicLengthField<T> extends BasicField<T> {
|
|||
if (!input.isReadable(length))
|
||||
return false;
|
||||
Object value = schema.readFrom(input, length);
|
||||
writeMethod.invoke(message, value);
|
||||
f.set(message, value);
|
||||
|
||||
int after = input.readerIndex();
|
||||
String hex = ByteBufUtil.hexDump(input.slice(before, after - before));
|
||||
println(this.index, this.desc, hex, value);
|
||||
println(this.index, this.field.desc(), hex, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void writeTo(ByteBuf output, Object message) throws Exception {
|
||||
int before = output.writerIndex();
|
||||
|
||||
Object value = readMethod.invoke(message);
|
||||
Object value = f.get(message);
|
||||
if (value != null) {
|
||||
int begin = output.writerIndex();
|
||||
output.writeBytes(ByteBufUtils.BLOCKS[lengthSize]);
|
||||
|
@ -88,7 +86,7 @@ public class DynamicLengthField<T> extends BasicField<T> {
|
|||
|
||||
int after = output.writerIndex();
|
||||
String hex = ByteBufUtil.hexDump(output.slice(before, after - before));
|
||||
println(this.index, this.desc, hex, value);
|
||||
println(this.index, this.field.desc(), hex, value);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,11 +1,9 @@
|
|||
package io.github.yezhihao.protostar.field;
|
||||
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.annotation.Field;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
|
||||
import java.beans.PropertyDescriptor;
|
||||
|
||||
/**
|
||||
* 原子域
|
||||
|
@ -16,51 +14,51 @@ public class FixedField<T> extends BasicField<T> {
|
|||
|
||||
protected final Schema<T> schema;
|
||||
|
||||
public FixedField(Field field, PropertyDescriptor property, Schema<T> schema) {
|
||||
super(field, property);
|
||||
public FixedField(Field field, java.lang.reflect.Field f, Schema<T> schema) {
|
||||
super(field, f);
|
||||
this.schema = schema;
|
||||
}
|
||||
|
||||
public boolean readFrom(ByteBuf input, Object message) throws Exception {
|
||||
Object value = schema.readFrom(input);
|
||||
writeMethod.invoke(message, value);
|
||||
f.set(message, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void writeTo(ByteBuf output, Object message) throws Exception {
|
||||
Object value = readMethod.invoke(message);
|
||||
Object value = f.get(message);
|
||||
if (value != null)
|
||||
schema.writeTo(output, (T) value);
|
||||
}
|
||||
|
||||
public static class Logger<T> extends FixedField<T> {
|
||||
|
||||
public Logger(Field field, PropertyDescriptor property, Schema<T> schema) {
|
||||
super(field, property, schema);
|
||||
public Logger(Field field, java.lang.reflect.Field f, Schema<T> schema) {
|
||||
super(field, f, schema);
|
||||
}
|
||||
|
||||
public boolean readFrom(ByteBuf input, Object message) throws Exception {
|
||||
int before = input.readerIndex();
|
||||
|
||||
Object value = schema.readFrom(input);
|
||||
writeMethod.invoke(message, value);
|
||||
f.set(message, value);
|
||||
|
||||
int after = input.readerIndex();
|
||||
String hex = ByteBufUtil.hexDump(input.slice(before, after - before));
|
||||
println(this.index, this.desc, hex, value);
|
||||
println(this.index, this.field.desc(), hex, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void writeTo(ByteBuf output, Object message) throws Exception {
|
||||
int before = output.writerIndex();
|
||||
|
||||
Object value = readMethod.invoke(message);
|
||||
Object value = f.get(message);
|
||||
if (value != null)
|
||||
schema.writeTo(output, (T) value);
|
||||
|
||||
int after = output.writerIndex();
|
||||
String hex = ByteBufUtil.hexDump(output.slice(before, after - before));
|
||||
println(this.index, this.desc, hex, value);
|
||||
println(this.index, this.field.desc(), hex, value);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,11 +1,9 @@
|
|||
package io.github.yezhihao.protostar.field;
|
||||
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.annotation.Field;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
|
||||
import java.beans.PropertyDescriptor;
|
||||
|
||||
/**
|
||||
* 固定长度的字段
|
||||
|
@ -16,51 +14,51 @@ public class FixedLengthField<T> extends BasicField<T> {
|
|||
|
||||
protected final Schema<T> schema;
|
||||
|
||||
public FixedLengthField(Field field, PropertyDescriptor property, Schema<T> schema) {
|
||||
super(field, property);
|
||||
public FixedLengthField(Field field, java.lang.reflect.Field f, Schema<T> schema) {
|
||||
super(field, f);
|
||||
this.schema = schema;
|
||||
}
|
||||
|
||||
public boolean readFrom(ByteBuf input, Object message) throws Exception {
|
||||
Object value = schema.readFrom(input, length);
|
||||
writeMethod.invoke(message, value);
|
||||
f.set(message, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void writeTo(ByteBuf output, Object message) throws Exception {
|
||||
Object value = readMethod.invoke(message);
|
||||
Object value = f.get(message);
|
||||
if (value != null)
|
||||
schema.writeTo(output, length, (T) value);
|
||||
}
|
||||
|
||||
public static class Logger<T> extends FixedLengthField<T> {
|
||||
|
||||
public Logger(Field field, PropertyDescriptor property, Schema<T> schema) {
|
||||
super(field, property, schema);
|
||||
public Logger(Field field, java.lang.reflect.Field f, Schema<T> schema) {
|
||||
super(field, f, schema);
|
||||
}
|
||||
|
||||
public boolean readFrom(ByteBuf input, Object message) throws Exception {
|
||||
int before = input.readerIndex();
|
||||
|
||||
Object value = schema.readFrom(input, length);
|
||||
writeMethod.invoke(message, value);
|
||||
f.set(message, value);
|
||||
|
||||
int after = input.readerIndex();
|
||||
String hex = ByteBufUtil.hexDump(input.slice(before, after - before));
|
||||
println(this.index, this.desc, hex, value);
|
||||
println(this.index, this.field.desc(), hex, value);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void writeTo(ByteBuf output, Object message) throws Exception {
|
||||
int before = output.writerIndex();
|
||||
|
||||
Object value = readMethod.invoke(message);
|
||||
Object value = f.get(message);
|
||||
if (value != null)
|
||||
schema.writeTo(output, length, (T) value);
|
||||
|
||||
int after = output.writerIndex();
|
||||
String hex = ByteBufUtil.hexDump(output.slice(before, after - before));
|
||||
println(this.index, this.desc, hex, value);
|
||||
println(this.index, this.field.desc(), hex, value);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -34,6 +34,29 @@ public class RuntimeSchema<T> implements Schema<T> {
|
|||
}
|
||||
}
|
||||
|
||||
public T newInstance() {
|
||||
try {
|
||||
return constructor.newInstance((Object[]) null);
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("newInstance failed " + typeClass.getName(), e);
|
||||
}
|
||||
}
|
||||
|
||||
public T mergeFrom(ByteBuf input, T result) {
|
||||
BasicField field = null;
|
||||
try {
|
||||
for (int i = 0; i < fields.length; i++) {
|
||||
if (!input.isReadable())
|
||||
break;
|
||||
field = fields[i];
|
||||
field.readFrom(input, result);
|
||||
}
|
||||
return result;
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("Read failed " + typeClass.getName() + field, e);
|
||||
}
|
||||
}
|
||||
|
||||
public T readFrom(ByteBuf input) {
|
||||
BasicField field = null;
|
||||
try {
|
||||
|
|
|
@ -5,7 +5,9 @@ import io.github.yezhihao.protostar.annotation.Field;
|
|||
|
||||
public class Attr1 {
|
||||
|
||||
@Field(index = 0, type = DataType.STRING, lengthSize = 1, desc = "名称")
|
||||
private String name;
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID")
|
||||
private int id;
|
||||
|
||||
public Attr1() {
|
||||
|
@ -16,7 +18,6 @@ public class Attr1 {
|
|||
this.id = id;
|
||||
}
|
||||
|
||||
@Field(index = 0, type = DataType.STRING, lengthSize = 1, desc = "名称")
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
@ -25,7 +26,6 @@ public class Attr1 {
|
|||
this.name = name;
|
||||
}
|
||||
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID")
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
|
|
@ -2,10 +2,9 @@ package io.github.yezhihao.protostar.convert;
|
|||
|
||||
import io.github.yezhihao.protostar.DataType;
|
||||
import io.github.yezhihao.protostar.ProtostarUtil;
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.annotation.Convert;
|
||||
import io.github.yezhihao.protostar.annotation.Field;
|
||||
import io.github.yezhihao.protostar.annotation.Fs;
|
||||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import io.netty.buffer.Unpooled;
|
||||
|
@ -17,9 +16,9 @@ import java.util.TreeMap;
|
|||
public class Test {
|
||||
|
||||
public static void main(String[] args) {
|
||||
Map<Integer, Schema<Foo>> multiVersionSchema = ProtostarUtil.getSchema(Foo.class);
|
||||
Schema<Foo> schema_v0 = multiVersionSchema.get(0);
|
||||
Schema<Foo> schema_v1 = multiVersionSchema.get(1);
|
||||
Map<Integer, RuntimeSchema<Foo>> multiVersionSchema = ProtostarUtil.getRuntimeSchema(Foo.class);
|
||||
RuntimeSchema<Foo> schema_v0 = multiVersionSchema.get(0);
|
||||
RuntimeSchema<Foo> schema_v1 = multiVersionSchema.get(1);
|
||||
|
||||
ByteBuf buffer = Unpooled.buffer(32);
|
||||
schema_v0.writeTo(buffer, foo());
|
||||
|
@ -56,13 +55,18 @@ public class Test {
|
|||
|
||||
public static class Foo {
|
||||
|
||||
@Field(index = 0, type = DataType.STRING, lengthSize = 1, desc = "名称", version = 0)
|
||||
@Field(index = 0, type = DataType.STRING, length = 10, desc = "名称", version = 1)
|
||||
private String name;
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID", version = 0)
|
||||
@Field(index = 1, type = DataType.DWORD, desc = "ID", version = 1)
|
||||
private int id;
|
||||
@Field(index = 3, type = DataType.BCD8421, desc = "日期", version = {0, 1})
|
||||
private LocalDateTime dateTime;
|
||||
@Convert(converter = AttributeConverter.class)
|
||||
@Field(index = 4, type = DataType.MAP, desc = "属性", version = {0, 1})
|
||||
private Map<Integer, Object> attributes;
|
||||
|
||||
@Fs({@Field(index = 0, type = DataType.STRING, lengthSize = 1, desc = "名称", version = 0),
|
||||
@Field(index = 0, type = DataType.STRING, length = 10, desc = "名称", version = 1)})
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
@ -71,8 +75,6 @@ public class Test {
|
|||
this.name = name;
|
||||
}
|
||||
|
||||
@Fs({@Field(index = 1, type = DataType.WORD, desc = "ID", version = 0),
|
||||
@Field(index = 1, type = DataType.DWORD, desc = "ID", version = 1)})
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
@ -81,7 +83,6 @@ public class Test {
|
|||
this.id = id;
|
||||
}
|
||||
|
||||
@Field(index = 3, type = DataType.BCD8421, desc = "日期", version = {0, 1})
|
||||
public LocalDateTime getDateTime() {
|
||||
return dateTime;
|
||||
}
|
||||
|
@ -90,8 +91,6 @@ public class Test {
|
|||
this.dateTime = dateTime;
|
||||
}
|
||||
|
||||
@Convert(converter = AttributeConverter.class)
|
||||
@Field(index = 4, type = DataType.MAP, desc = "属性", version = {0, 1})
|
||||
public Map<Integer, Object> getAttributes() {
|
||||
return attributes;
|
||||
}
|
||||
|
|
|
@ -2,8 +2,8 @@ package io.github.yezhihao.protostar.multiversion;
|
|||
|
||||
import io.github.yezhihao.protostar.DataType;
|
||||
import io.github.yezhihao.protostar.ProtostarUtil;
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.annotation.Field;
|
||||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import io.netty.buffer.Unpooled;
|
||||
|
@ -14,9 +14,9 @@ import java.util.Map;
|
|||
public class Test {
|
||||
|
||||
public static void main(String[] args) {
|
||||
Map<Integer, Schema<Foo>> multiVersionSchema = ProtostarUtil.getSchema(Foo.class);
|
||||
Schema<Foo> schema_v0 = multiVersionSchema.get(0);
|
||||
Schema<Foo> schema_v1 = multiVersionSchema.get(1);
|
||||
Map<Integer, RuntimeSchema<Foo>> multiVersionSchema = ProtostarUtil.getRuntimeSchema(Foo.class);
|
||||
RuntimeSchema<Foo> schema_v0 = multiVersionSchema.get(0);
|
||||
RuntimeSchema<Foo> schema_v1 = multiVersionSchema.get(1);
|
||||
|
||||
ByteBuf buffer = Unpooled.buffer(32);
|
||||
Foo foo = foo();
|
||||
|
@ -48,12 +48,15 @@ public class Test {
|
|||
|
||||
public static class Foo {
|
||||
|
||||
private String name;
|
||||
private int id;
|
||||
private LocalDateTime dateTime;
|
||||
|
||||
@Field(index = 0, type = DataType.STRING, lengthSize = 1, desc = "名称", version = 0)
|
||||
@Field(index = 0, type = DataType.STRING, length = 10, desc = "名称", version = 1)
|
||||
private String name;
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID", version = 0)
|
||||
@Field(index = 1, type = DataType.DWORD, desc = "ID", version = 1)
|
||||
private int id;
|
||||
@Field(index = 3, type = DataType.BCD8421, desc = "日期", version = {0, 1})
|
||||
private LocalDateTime dateTime;
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
@ -62,8 +65,6 @@ public class Test {
|
|||
this.name = name;
|
||||
}
|
||||
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID", version = 0)
|
||||
@Field(index = 1, type = DataType.DWORD, desc = "ID", version = 1)
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
@ -72,7 +73,6 @@ public class Test {
|
|||
this.id = id;
|
||||
}
|
||||
|
||||
@Field(index = 3, type = DataType.BCD8421, desc = "日期", version = {0, 1})
|
||||
public LocalDateTime getDateTime() {
|
||||
return dateTime;
|
||||
}
|
||||
|
|
|
@ -3,8 +3,8 @@ package io.github.yezhihao.protostar.simple;
|
|||
import io.github.yezhihao.protostar.DataType;
|
||||
import io.github.yezhihao.protostar.FieldFactory;
|
||||
import io.github.yezhihao.protostar.ProtostarUtil;
|
||||
import io.github.yezhihao.protostar.Schema;
|
||||
import io.github.yezhihao.protostar.annotation.Field;
|
||||
import io.github.yezhihao.protostar.schema.RuntimeSchema;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import io.netty.buffer.Unpooled;
|
||||
|
@ -17,16 +17,24 @@ public class Test {
|
|||
public static void main(String[] args) {
|
||||
FieldFactory.EXPLAIN = true;
|
||||
|
||||
Map<Integer, Schema<Foo>> multiVersionSchema = ProtostarUtil.getSchema(Foo.class);
|
||||
Schema<Foo> schema = multiVersionSchema.get(0);
|
||||
Map<Integer, RuntimeSchema<Foo>> bodySchemas = ProtostarUtil.getRuntimeSchema(Foo.class);
|
||||
RuntimeSchema<Foo> bodySchema = bodySchemas.get(0);
|
||||
|
||||
Map<Integer, RuntimeSchema<BaseDO>> headSchemas = ProtostarUtil.getRuntimeSchema(BaseDO.class);
|
||||
RuntimeSchema<BaseDO> headSchema = headSchemas.get(0);
|
||||
|
||||
ByteBuf buffer = Unpooled.buffer(32);
|
||||
Foo foo = foo();
|
||||
schema.writeTo(buffer, foo);
|
||||
headSchema.writeTo(buffer, foo);
|
||||
bodySchema.writeTo(buffer, foo);
|
||||
|
||||
String hex = ByteBufUtil.hexDump(buffer);
|
||||
System.out.println(hex);
|
||||
|
||||
foo = schema.readFrom(buffer);
|
||||
|
||||
Foo foo1 = new Foo();
|
||||
headSchema.mergeFrom(buffer, foo1);
|
||||
bodySchema.mergeFrom(buffer, foo1);
|
||||
System.out.println(foo);
|
||||
}
|
||||
|
||||
|
@ -35,16 +43,45 @@ public class Test {
|
|||
foo.setName("张三");
|
||||
foo.setId(128);
|
||||
foo.setDateTime(LocalDateTime.of(2020, 7, 7, 19, 23, 59));
|
||||
|
||||
foo.setType(1);
|
||||
foo.setClientId("123qwe");
|
||||
return foo;
|
||||
}
|
||||
|
||||
public static class Foo {
|
||||
public static class BaseDO {
|
||||
|
||||
private String name;
|
||||
private int id;
|
||||
private LocalDateTime dateTime;
|
||||
@Field(index = 0, type = DataType.WORD, desc = "ID")
|
||||
protected int type;
|
||||
@Field(index = 1, type = DataType.STRING, length = 20, desc = "名称")
|
||||
protected String clientId;
|
||||
|
||||
public int getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
public void setType(int type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
public String getClientId() {
|
||||
return clientId;
|
||||
}
|
||||
|
||||
public void setClientId(String clientId) {
|
||||
this.clientId = clientId;
|
||||
}
|
||||
}
|
||||
|
||||
public static class Foo extends BaseDO {
|
||||
|
||||
@Field(index = 0, type = DataType.STRING, lengthSize = 1, desc = "名称")
|
||||
private String name;
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID")
|
||||
private int id;
|
||||
@Field(index = 3, type = DataType.BCD8421, desc = "日期")
|
||||
private LocalDateTime dateTime;
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
@ -53,7 +90,6 @@ public class Test {
|
|||
this.name = name;
|
||||
}
|
||||
|
||||
@Field(index = 1, type = DataType.WORD, desc = "ID")
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
|
@ -62,7 +98,6 @@ public class Test {
|
|||
this.id = id;
|
||||
}
|
||||
|
||||
@Field(index = 3, type = DataType.BCD8421, desc = "日期")
|
||||
public LocalDateTime getDateTime() {
|
||||
return dateTime;
|
||||
}
|
||||
|
@ -74,7 +109,9 @@ public class Test {
|
|||
@Override
|
||||
public String toString() {
|
||||
final StringBuilder sb = new StringBuilder("Foo{");
|
||||
sb.append("name='").append(name).append('\'');
|
||||
sb.append("type=").append(type);
|
||||
sb.append(", clientId='").append(clientId).append('\'');
|
||||
sb.append(", name='").append(name).append('\'');
|
||||
sb.append(", id=").append(id);
|
||||
sb.append(", dateTime=").append(dateTime);
|
||||
sb.append('}');
|
||||
|
|
Loading…
Reference in New Issue