change an annotation-utility in Java. it allows users to pack and unpack a List object.

This commit is contained in:
Muga Nishizawa 2010-09-15 22:28:46 +09:00
parent 56ece4db0f
commit 9eeb702ca5
3 changed files with 499 additions and 313 deletions

View File

@ -6,6 +6,6 @@ import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target; import java.lang.annotation.Target;
@Target(ElementType.TYPE) @Target(ElementType.TYPE)
@Retention(RetentionPolicy.CLASS) @Retention(RetentionPolicy.RUNTIME)
public @interface MessagePackUnpackable { public @interface MessagePackUnpackable {
} }

View File

@ -3,9 +3,14 @@ package org.msgpack.util.annotation;
import java.io.ByteArrayInputStream; import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream; import java.io.ByteArrayOutputStream;
import java.io.IOException; import java.io.IOException;
import java.lang.annotation.Annotation;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier; import java.lang.reflect.Modifier;
import java.lang.reflect.ParameterizedType;
import java.math.BigInteger; import java.math.BigInteger;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentHashMap;
@ -14,7 +19,6 @@ import javassist.CannotCompileException;
import javassist.ClassPool; import javassist.ClassPool;
import javassist.CtClass; import javassist.CtClass;
import javassist.CtConstructor; import javassist.CtConstructor;
import javassist.CtField;
import javassist.CtMethod; import javassist.CtMethod;
import javassist.CtNewConstructor; import javassist.CtNewConstructor;
import javassist.CtNewMethod; import javassist.CtNewMethod;
@ -33,51 +37,16 @@ public class PackUnpackUtil {
static final String KEYWORD_MODIFIER_PUBLIC = "public"; static final String KEYWORD_MODIFIER_PUBLIC = "public";
static final String KEYWORD_FOR = "for";
static final String KEYWORD_THROWS = "throws"; static final String KEYWORD_THROWS = "throws";
static final String KEYWORD_NEW = "new";
static final String TYPE_NAME_VOID = void.class.getName(); static final String TYPE_NAME_VOID = void.class.getName();
static final String TYPE_NAME_BOOLEAN = boolean.class.getName();
static final String TYPE_NAME_BYTE = byte.class.getName();
static final String TYPE_NAME_DOUBLE = double.class.getName();
static final String TYPE_NAME_FLOAT = float.class.getName();
static final String TYPE_NAME_INT = int.class.getName();
static final String TYPE_NAME_LONG = long.class.getName();
static final String TYPE_NAME_SHORT = short.class.getName();
static final String TYPE_NAME_OBJECT = Object.class.getName(); static final String TYPE_NAME_OBJECT = Object.class.getName();
static final String TYPE_NAME_BIGINTEGER = BigInteger.class.getName();
static final String TYPE_NAME_STRING = String.class.getName();
static final String TYPE_NAME_BOOLEAN2 = Boolean.class.getName();
static final String TYPE_NAME_BYTE2 = Byte.class.getName();
static final String TYPE_NAME_DOUBLE2 = Double.class.getName();
static final String TYPE_NAME_FLOAT2 = Float.class.getName();
static final String TYPE_NAME_INT2 = Integer.class.getName();
static final String TYPE_NAME_LONG2 = Long.class.getName();
static final String TYPE_NAME_SHORT2 = Short.class.getName();
//static final String TYPE_NAME_BYTEARRAY = byte[].class.getName();
static final String TYPE_NAME_BYTEARRAY = "byte[]";
static final String TYPE_NAME_LIST = List.class.getName();
static final String TYPE_NAME_MAP = Map.class.getName();
static final String TYPE_NAME_IOEXCEPTION = IOException.class.getName(); static final String TYPE_NAME_IOEXCEPTION = IOException.class.getName();
static final String TYPE_NAME_PACKER = Packer.class.getName(); static final String TYPE_NAME_PACKER = Packer.class.getName();
@ -111,6 +80,10 @@ public class PackUnpackUtil {
static final String CHAR_NAME_EQUAL = "="; static final String CHAR_NAME_EQUAL = "=";
static final String CHAR_NAME_PLUS = "+";
static final String CHAR_NAME_LESSTHAN = "<";
static final String CHAR_NAME_RIGHT_PARENTHESIS = ")"; static final String CHAR_NAME_RIGHT_PARENTHESIS = ")";
static final String CHAR_NAME_LEFT_PARENTHESIS = "("; static final String CHAR_NAME_LEFT_PARENTHESIS = "(";
@ -127,8 +100,16 @@ public class PackUnpackUtil {
static final String VARIABLE_NAME_OBJ = "obj"; static final String VARIABLE_NAME_OBJ = "obj";
static final String VARIABLE_NAME_SIZE = "len";
static final String VARIABLE_NAME_I = "i";
static final String METHOD_NAME_VALUEOF = "valueOf"; static final String METHOD_NAME_VALUEOF = "valueOf";
static final String METHOD_NAME_ADD = "add";
static final String METHOD_NAME_PUT = "put";
static final String METHOD_NAME_MSGPACK = "messagePack"; static final String METHOD_NAME_MSGPACK = "messagePack";
static final String METHOD_NAME_MSGUNPACK = "messageUnpack"; static final String METHOD_NAME_MSGUNPACK = "messageUnpack";
@ -192,73 +173,68 @@ public class PackUnpackUtil {
String origName = origClass.getName(); String origName = origClass.getName();
String enhName = origName + Constants.POSTFIX_TYPE_NAME_ENHANCER; String enhName = origName + Constants.POSTFIX_TYPE_NAME_ENHANCER;
CtClass origCtClass = pool.get(origName); CtClass origCtClass = pool.get(origName);
checkClassValidation(origCtClass); checkClassValidation(origClass);
checkDefaultConstructorValidation(origCtClass); checkDefaultConstructorValidation(origClass);
CtClass enhCtClass = pool.makeClass(enhName); CtClass enhCtClass = pool.makeClass(enhName);
setSuperclass(enhCtClass, origCtClass); setSuperclass(enhCtClass, origCtClass);
setInterfaces(enhCtClass); setInterfaces(enhCtClass);
addConstructor(enhCtClass); addConstructor(enhCtClass);
CtField[] fields = getDeclaredFields(origCtClass); Field[] fields = getDeclaredFields(origClass);
addMessagePackMethod(enhCtClass, origCtClass, fields); addMessagePackMethod(enhCtClass, origCtClass, fields);
addMessageUnpackMethod(enhCtClass, origCtClass, fields); addMessageUnpackMethod(enhCtClass, origCtClass, fields);
addMessageConvertMethod(enhCtClass, origCtClass, fields); addMessageConvertMethod(enhCtClass, origCtClass, fields);
return createClass(enhCtClass); return createClass(enhCtClass);
} }
private void checkClassValidation(CtClass origCtClass) { private void checkClassValidation(Class<?> origClass) {
// not public, abstract, final // not public, abstract, final
int mod = origCtClass.getModifiers(); int mod = origClass.getModifiers();
if ((!Modifier.isPublic(mod)) || Modifier.isAbstract(mod) if ((!(Modifier.isPublic(mod) || Modifier.isProtected(mod)))
|| Modifier.isFinal(mod)) { || Modifier.isAbstract(mod) || Modifier.isFinal(mod)) {
throwClassValidationException(origCtClass); throwClassValidationException(origClass);
} }
// interface, enum // interface, enum
if (origCtClass.isInterface() || origCtClass.isEnum()) { if (origClass.isInterface() || origClass.isEnum()) {
throwClassValidationException(origCtClass); throwClassValidationException(origClass);
} }
// annotation // annotation
checkPackUnpackAnnotation(origCtClass); checkPackUnpackAnnotation(origClass);
} }
private static void throwClassValidationException(CtClass origCtClass) { private static void throwClassValidationException(Class<?> origClass) {
throw new PackUnpackUtilException( throw new PackUnpackUtilException(
"it must be a public class and have @" "it must be a public class and have @"
+ MessagePackUnpackable.class.getName() + ": " + MessagePackUnpackable.class.getName() + ": "
+ origCtClass.getName()); + origClass.getName());
} }
private void checkPackUnpackAnnotation(CtClass origCtClass) { private void checkPackUnpackAnnotation(Class<?> origClass) {
try { Annotation anno = origClass
Object[] objs = origCtClass.getAnnotations(); .getAnnotation(MessagePackUnpackable.class);
for (Object obj : objs) { if (anno == null) {
if (obj instanceof MessagePackUnpackable) { throwClassValidationException(origClass);
return;
}
}
throwClassValidationException(origCtClass);
} catch (ClassNotFoundException e) {
throw new PackUnpackUtilException(e.getMessage(), e);
} }
} }
private void checkDefaultConstructorValidation(CtClass origCtClass) { private void checkDefaultConstructorValidation(Class<?> origClass) {
CtConstructor cons = null; Constructor<?> cons = null;
try { try {
cons = origCtClass.getDeclaredConstructor(new CtClass[0]); cons = origClass.getDeclaredConstructor(new Class[0]);
} catch (NotFoundException e) { } catch (Exception e1) {
throwConstructoValidationException(origCtClass); throwConstructoValidationException(origClass);
} }
int mod = cons.getModifiers(); int mod = cons.getModifiers();
if (!(Modifier.isPublic(mod) || Modifier.isProtected(mod))) { if (!(Modifier.isPublic(mod) || Modifier.isProtected(mod))) {
throwConstructoValidationException(origCtClass); throwConstructoValidationException(origClass);
} }
} }
private static void throwConstructoValidationException( private static void throwConstructoValidationException(
CtClass origCtClass) { Class<?> origClass) {
throw new PackUnpackUtilException( throw new PackUnpackUtilException(
"it must have a public zero-argument constructor: " "it must have a public zero-argument constructor: "
+ origCtClass.getName()); + origClass.getName());
} }
private void setSuperclass(CtClass enhCtClass, CtClass origCtClass) private void setSuperclass(CtClass enhCtClass, CtClass origCtClass)
@ -282,301 +258,430 @@ public class PackUnpackUtil {
enhCtClass.addConstructor(newCtCons); enhCtClass.addConstructor(newCtCons);
} }
private CtField[] getDeclaredFields(CtClass origCtClass) { private Field[] getDeclaredFields(Class<?> origClass) {
ArrayList<CtField> allFields = new ArrayList<CtField>(); ArrayList<Field> allFields = new ArrayList<Field>();
try { Class<?> nextClass = origClass;
CtClass nextCtClass = origCtClass; while (nextClass != Object.class) {
while (!nextCtClass Field[] fields = nextClass.getDeclaredFields();
.equals(pool.get(Constants.TYPE_NAME_OBJECT))) { for (Field field : fields) {
CtField[] fields = nextCtClass.getDeclaredFields();
for (CtField field : fields) {
try { try {
checkFieldValidation(field, allFields); checkFieldValidation(field, allFields);
allFields.add(field); allFields.add(field);
} catch (PackUnpackUtilException e) { // ignore } catch (PackUnpackUtilException e) { // ignore
} }
} }
nextCtClass = nextCtClass.getSuperclass(); nextClass = nextClass.getSuperclass();
}
return allFields.toArray(new Field[0]);
} }
} catch (NotFoundException e) { private void checkFieldValidation(Field field, List<Field> fields) {
throw new PackUnpackUtilException(e.getMessage(), e);
}
return allFields.toArray(new CtField[0]);
}
private void checkFieldValidation(CtField field,
ArrayList<CtField> allFields) {
// check modifiers (public or protected) // check modifiers (public or protected)
int mod = field.getModifiers(); int mod = field.getModifiers();
if ((!(Modifier.isPublic(mod) || Modifier.isProtected(mod))) if ((!(Modifier.isPublic(mod) || Modifier.isProtected(mod)))
|| Modifier.isStatic(mod) || Modifier.isFinal(mod) || Modifier.isStatic(mod) || Modifier.isFinal(mod)
|| Modifier.isTransient(mod)) { || Modifier.isTransient(mod) || field.isSynthetic()) {
throwFieldValidationException(field); throwFieldValidationException(field);
} }
// check same name // check same name
for (CtField f : allFields) { for (Field f : fields) {
if (f.getName().equals(field.getName())) { if (f.getName().equals(field.getName())) {
throwFieldValidationException(field); throwFieldValidationException(field);
} }
} }
} }
private static void throwFieldValidationException(CtField field) { private static void throwFieldValidationException(Field field) {
throw new PackUnpackUtilException("it must be a public field: " throw new PackUnpackUtilException("it must be a public field: "
+ field.getName()); + field.getName());
} }
private void addMessagePackMethod(CtClass enhCtClass, private void addMessagePackMethod(CtClass enhCtClass,
CtClass origCtClass, CtField[] fields) CtClass origCtClass, Field[] fields)
throws CannotCompileException, NotFoundException { throws CannotCompileException, NotFoundException {
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();
sb.append(Constants.KEYWORD_MODIFIER_PUBLIC).append( sb.append(Constants.KEYWORD_MODIFIER_PUBLIC);
Constants.CHAR_NAME_SPACE).append(Constants.TYPE_NAME_VOID) sb.append(Constants.CHAR_NAME_SPACE);
.append(Constants.CHAR_NAME_SPACE).append( sb.append(Constants.TYPE_NAME_VOID);
Constants.METHOD_NAME_MSGPACK).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_LEFT_PARENTHESIS).append( sb.append(Constants.METHOD_NAME_MSGPACK);
Constants.TYPE_NAME_PACKER).append( sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.TYPE_NAME_PACKER);
Constants.VARIABLE_NAME_PK).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_RIGHT_PARENTHESIS).append( sb.append(Constants.VARIABLE_NAME_PK);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
Constants.KEYWORD_THROWS).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.KEYWORD_THROWS);
Constants.TYPE_NAME_IOEXCEPTION).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.TYPE_NAME_IOEXCEPTION);
Constants.CHAR_NAME_LEFT_CURLY_BRACHET).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_SPACE); sb.append(Constants.CHAR_NAME_LEFT_CURLY_BRACHET);
sb.append(Constants.VARIABLE_NAME_PK).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_DOT).append( sb.append(Constants.VARIABLE_NAME_PK);
Constants.METHOD_NAME_PACKARRAY).append( sb.append(Constants.CHAR_NAME_DOT);
Constants.CHAR_NAME_LEFT_PARENTHESIS).append(fields.length) sb.append(Constants.METHOD_NAME_PACKARRAY);
.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS).append( sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
Constants.CHAR_NAME_SEMICOLON).append( sb.append(fields.length);
Constants.CHAR_NAME_SPACE); sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
for (CtField field : fields) { sb.append(Constants.CHAR_NAME_SEMICOLON);
insertCodeOfMessagePack(field, sb); sb.append(Constants.CHAR_NAME_SPACE);
for (Field field : fields) {
insertCodeOfMessagePack(sb, field);
} }
sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET); sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET);
System.out.println("messagePack method: " + sb.toString()); //System.out.println("messagePack method: " + sb.toString());
CtMethod newCtMethod = CtNewMethod.make(sb.toString(), enhCtClass); CtMethod newCtMethod = CtNewMethod.make(sb.toString(), enhCtClass);
enhCtClass.addMethod(newCtMethod); enhCtClass.addMethod(newCtMethod);
} }
private void insertCodeOfMessagePack(CtField field, StringBuilder sb) private void insertCodeOfMessagePack(StringBuilder sb, Field field) {
throws NotFoundException { sb.append(Constants.VARIABLE_NAME_PK);
sb.append(Constants.VARIABLE_NAME_PK).append( sb.append(Constants.CHAR_NAME_DOT);
Constants.CHAR_NAME_DOT).append(Constants.METHOD_NAME_PACK) sb.append(Constants.METHOD_NAME_PACK);
.append(Constants.CHAR_NAME_LEFT_PARENTHESIS).append( sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
field.getName()).append( sb.append(field.getName());
Constants.CHAR_NAME_RIGHT_PARENTHESIS).append( sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
Constants.CHAR_NAME_SEMICOLON).append( sb.append(Constants.CHAR_NAME_SEMICOLON);
Constants.CHAR_NAME_SPACE); sb.append(Constants.CHAR_NAME_SPACE);
} }
private void addMessageUnpackMethod(CtClass enhCtClass, private void addMessageUnpackMethod(CtClass enhCtClass,
CtClass origCtClass, CtField[] fields) CtClass origCtClass, Field[] fields)
throws CannotCompileException, NotFoundException { throws CannotCompileException, NotFoundException {
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();
sb.append(Constants.KEYWORD_MODIFIER_PUBLIC).append( sb.append(Constants.KEYWORD_MODIFIER_PUBLIC);
Constants.CHAR_NAME_SPACE).append(Constants.TYPE_NAME_VOID) sb.append(Constants.CHAR_NAME_SPACE);
.append(Constants.CHAR_NAME_SPACE).append( sb.append(Constants.TYPE_NAME_VOID);
Constants.METHOD_NAME_MSGUNPACK).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_LEFT_PARENTHESIS).append( sb.append(Constants.METHOD_NAME_MSGUNPACK);
Constants.TYPE_NAME_UNPACKER).append( sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.TYPE_NAME_UNPACKER);
Constants.VARIABLE_NAME_PK).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_RIGHT_PARENTHESIS).append( sb.append(Constants.VARIABLE_NAME_PK);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
Constants.KEYWORD_THROWS).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.KEYWORD_THROWS);
Constants.TYPE_NAME_MSGTYPEEXCEPTION).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_COMMA).append( sb.append(Constants.TYPE_NAME_MSGTYPEEXCEPTION);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.CHAR_NAME_COMMA);
Constants.TYPE_NAME_IOEXCEPTION).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_SPACE).append( sb.append(Constants.TYPE_NAME_IOEXCEPTION);
Constants.CHAR_NAME_LEFT_CURLY_BRACHET).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_SPACE); sb.append(Constants.CHAR_NAME_LEFT_CURLY_BRACHET);
sb.append(Constants.VARIABLE_NAME_PK).append( sb.append(Constants.CHAR_NAME_SPACE);
Constants.CHAR_NAME_DOT).append( sb.append(Constants.VARIABLE_NAME_PK);
Constants.METHOD_NAME_UNPACKARRAY).append( sb.append(Constants.CHAR_NAME_DOT);
Constants.CHAR_NAME_LEFT_PARENTHESIS).append( sb.append(Constants.METHOD_NAME_UNPACKARRAY);
Constants.CHAR_NAME_RIGHT_PARENTHESIS).append( sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
Constants.CHAR_NAME_SEMICOLON).append( sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
Constants.CHAR_NAME_SPACE); sb.append(Constants.CHAR_NAME_SEMICOLON);
for (CtField field : fields) { sb.append(Constants.CHAR_NAME_SPACE);
insertCodeOfMessageUnpack(field, sb); for (Field field : fields) {
insertCodeOfMessageUnpack(sb, field, field.getType());
} }
sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET); sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET);
System.out.println("messageUnpack method: " + sb.toString()); //System.out.println("messageUnpack method: " + sb.toString());
CtMethod newCtMethod = CtNewMethod.make(sb.toString(), enhCtClass); CtMethod newCtMethod = CtNewMethod.make(sb.toString(), enhCtClass);
enhCtClass.addMethod(newCtMethod); enhCtClass.addMethod(newCtMethod);
} }
private void insertCodeOfMessageUnpack(CtField field, StringBuilder sb) private void insertCodeOfMessageUnpack(StringBuilder sb, Field field,
throws NotFoundException { Class<?> type) throws NotFoundException {
CtClass type = field.getType(); if (type.isPrimitive()) {
insertRightVariable(sb, field, type); // primitive type
insertValueOfMethodAndLeftParenthesis(sb, type); insertCodeOfMessageUnpackForPrimitiveTypes(sb, field, type);
sb.append(Constants.VARIABLE_NAME_PK).append( } else if (type.equals(Boolean.class) || // Boolean
Constants.CHAR_NAME_DOT); type.equals(Byte.class) || // Byte
insertUnpackMethod(sb, type); type.equals(Double.class) || // Double
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS); type.equals(Float.class) || // Float
insertUnpackMethodArgumenet(sb, field, type); type.equals(Integer.class) || // Integer
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS); type.equals(Long.class) || // Long
insertValueOfMethodAndRightParenthesis(sb, type); type.equals(Short.class)) { // Short
sb.append(Constants.CHAR_NAME_SEMICOLON).append( // reference type (wrapper type)
Constants.CHAR_NAME_SPACE); insertCodeOfMessageUnpackForWrapperTypes(sb, field, type);
} else if (type.equals(BigInteger.class) || // BigInteger
} type.equals(String.class) || // String
type.equals(byte[].class)) { // byte[]
private void insertRightVariable(StringBuilder sb, CtField field, // reference type (other type)
CtClass type) throws NotFoundException { insertCodeOfMessageUnpackForPrimitiveTypes(sb, field, type);
if (type.isPrimitive()) { // primitive type } else if (List.class.isAssignableFrom(type)) {
sb.append(field.getName()).append(Constants.CHAR_NAME_SPACE) // List
.append(Constants.CHAR_NAME_EQUAL).append( insertCodeOfMessageUnpackForListType(sb, field, type);
Constants.CHAR_NAME_SPACE); } else if (Map.class.isAssignableFrom(type)) {
} else { // reference type // Map
if (type.equals(pool.get(Constants.TYPE_NAME_BOOLEAN2)) // Boolean insertCodeOfMessageUnpackForMapType(sb, field, type);
|| type.equals(pool.get(Constants.TYPE_NAME_BYTE2)) // Byte } else if (MessageUnpackable.class.isAssignableFrom(type)
|| type.equals(pool.get(Constants.TYPE_NAME_DOUBLE2)) // Double || (getCache(type.getName()) != null)) {
|| type.equals(pool.get(Constants.TYPE_NAME_FLOAT2)) // Float // MessageUnpackable
|| type.equals(pool.get(Constants.TYPE_NAME_INT2)) // Integer insertCodeOfMessageUnpackForMsgUnpackableType(sb, field, type);
|| type.equals(pool.get(Constants.TYPE_NAME_LONG2)) // Long
|| type.equals(pool.get(Constants.TYPE_NAME_SHORT2)) // Short
|| type
.equals(pool
.get(Constants.TYPE_NAME_BIGINTEGER)) // BigInteger
|| type.equals(pool.get(Constants.TYPE_NAME_STRING)) // String
|| type.equals(pool.get(Constants.TYPE_NAME_BYTEARRAY)) // byte[]
|| type.subtypeOf(pool.get(Constants.TYPE_NAME_LIST)) // List
|| type.subtypeOf(pool.get(Constants.TYPE_NAME_MAP)) // Map
) {
sb.append(field.getName())
.append(Constants.CHAR_NAME_SPACE).append(
Constants.CHAR_NAME_EQUAL).append(
Constants.CHAR_NAME_SPACE);
} else { // MessageUnpackable
return;
}
}
}
private void insertValueOfMethodAndLeftParenthesis(StringBuilder sb,
CtClass type) throws NotFoundException {
if (type.isPrimitive()) { // primitive type
return;
} else { // reference type
if (type.equals(pool.get(Constants.TYPE_NAME_BOOLEAN2)) // Boolean
|| type.equals(pool.get(Constants.TYPE_NAME_BYTE2)) // Byte
|| type.equals(pool.get(Constants.TYPE_NAME_DOUBLE2)) // Double
|| type.equals(pool.get(Constants.TYPE_NAME_FLOAT2)) // Float
|| type.equals(pool.get(Constants.TYPE_NAME_INT2)) // Integer
|| type.equals(pool.get(Constants.TYPE_NAME_LONG2)) // Long
|| type.equals(pool.get(Constants.TYPE_NAME_SHORT2)) // Short
) {
sb.append(type.getName()).append(Constants.CHAR_NAME_DOT)
.append(Constants.METHOD_NAME_VALUEOF).append(
Constants.CHAR_NAME_LEFT_PARENTHESIS);
} else { } else {
return; throw new NotFoundException("unknown type: " + type.getName());
}
} }
} }
private void insertUnpackMethod(StringBuilder sb, CtClass type) private void insertCodeOfMessageUnpackForPrimitiveTypes(
StringBuilder sb, Field field, Class<?> type)
throws NotFoundException { throws NotFoundException {
if (type.equals(CtClass.booleanType)) { // boolean // insert a right variable
if (field != null) {
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
}
sb.append(Constants.VARIABLE_NAME_PK);
sb.append(Constants.CHAR_NAME_DOT);
// insert unpack method
if (type.equals(boolean.class)) { // boolean
sb.append(Constants.METHOD_NAME_UNPACKBOOLEAN); sb.append(Constants.METHOD_NAME_UNPACKBOOLEAN);
} else if (type.equals(CtClass.byteType)) { // byte } else if (type.equals(byte.class)) { // byte
sb.append(Constants.METHOD_NAME_UNPACKBYTE); sb.append(Constants.METHOD_NAME_UNPACKBYTE);
} else if (type.equals(CtClass.doubleType)) { // double } else if (type.equals(double.class)) { // double
sb.append(Constants.METHOD_NAME_UNPACKDOUBLE); sb.append(Constants.METHOD_NAME_UNPACKDOUBLE);
} else if (type.equals(CtClass.floatType)) { // float } else if (type.equals(float.class)) { // float
sb.append(Constants.METHOD_NAME_UNPACKFLOAT); sb.append(Constants.METHOD_NAME_UNPACKFLOAT);
} else if (type.equals(CtClass.intType)) { // int } else if (type.equals(int.class)) { // int
sb.append(Constants.METHOD_NAME_UNPACKINT); sb.append(Constants.METHOD_NAME_UNPACKINT);
} else if (type.equals(CtClass.longType)) { // long } else if (type.equals(long.class)) { // long
sb.append(Constants.METHOD_NAME_UNPACKLONG); sb.append(Constants.METHOD_NAME_UNPACKLONG);
} else if (type.equals(CtClass.shortType)) { // short } else if (type.equals(short.class)) { // short
sb.append(Constants.METHOD_NAME_UNPACKSHORT); sb.append(Constants.METHOD_NAME_UNPACKSHORT);
} else { // reference type } else { // reference type
Class<?> c = null; if (type.equals(BigInteger.class)) { // BigInteger
if (type.equals(pool.get(Constants.TYPE_NAME_BOOLEAN2))) { // Boolean
sb.append(Constants.METHOD_NAME_UNPACKBOOLEAN);
} else if (type.equals(pool.get(Constants.TYPE_NAME_BYTE2))) { // Byte
sb.append(Constants.METHOD_NAME_UNPACKBYTE);
} else if (type.equals(pool.get(Constants.TYPE_NAME_DOUBLE2))) { // Double
sb.append(Constants.METHOD_NAME_UNPACKDOUBLE);
} else if (type.equals(pool.get(Constants.TYPE_NAME_FLOAT2))) { // Float
sb.append(Constants.METHOD_NAME_UNPACKFLOAT);
} else if (type.equals(pool.get(Constants.TYPE_NAME_INT2))) { // Integer
sb.append(Constants.METHOD_NAME_UNPACKINT);
} else if (type.equals(pool.get(Constants.TYPE_NAME_LONG2))) { // Long
sb.append(Constants.METHOD_NAME_UNPACKLONG);
} else if (type.equals(pool.get(Constants.TYPE_NAME_SHORT2))) { // Short
sb.append(Constants.METHOD_NAME_UNPACKSHORT);
} else if (type
.equals(pool.get(Constants.TYPE_NAME_BIGINTEGER))) { // BigInteger
sb.append(Constants.METHOD_NAME_UNPACKBIGINTEGER); sb.append(Constants.METHOD_NAME_UNPACKBIGINTEGER);
} else if (type.equals(pool.get(Constants.TYPE_NAME_STRING))) { // String } else if (type.equals(String.class)) { // String
sb.append(Constants.METHOD_NAME_UNPACKSTRING); sb.append(Constants.METHOD_NAME_UNPACKSTRING);
} else if (type.equals(pool.get(Constants.TYPE_NAME_BYTEARRAY))) { // byte[] } else if (type.equals(byte[].class)) { // byte[]
sb.append(Constants.METHOD_NAME_UNPACKBYTEARRAY); sb.append(Constants.METHOD_NAME_UNPACKBYTEARRAY);
} else if (type.subtypeOf(pool.get(Constants.TYPE_NAME_LIST))) { // List
sb.append(Constants.METHOD_NAME_UNPACKARRAY);
} else if (type.subtypeOf(pool.get(Constants.TYPE_NAME_MAP))) { // Map
sb.append(Constants.METHOD_NAME_UNPACKMAP);
} else if (type.subtypeOf(pool
.get(Constants.TYPE_NAME_MSGUNPACKABLE))
|| ((c = getCache(type.getName())) != null)) { // MessageUnpackable
sb.append(Constants.METHOD_NAME_UNPACK);
} else { } else {
throw new NotFoundException("unknown type: " throw new NotFoundException("unknown type: "
+ type.getName()); + type.getName());
} }
} }
} sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
private void insertUnpackMethodArgumenet(StringBuilder sb,
CtField field, CtClass type) throws NotFoundException {
if (type.isPrimitive()) { // primitive type
return;
} else { // reference type
Class<?> c = null;
if (type.equals(pool.get(Constants.TYPE_NAME_MSGUNPACKABLE))
|| ((c = getCache(type.getName())) != null)) {
sb.append("(org.msgpack.MessageUnpackable)");
sb.append(field.getName());
} else {
return;
}
}
}
private void insertValueOfMethodAndRightParenthesis(StringBuilder sb,
CtClass type) throws NotFoundException {
if (type.isPrimitive()) { // primitive type
return;
} else { // reference type
if (type.equals(pool.get(Constants.TYPE_NAME_BOOLEAN2)) // Boolean
|| type.equals(pool.get(Constants.TYPE_NAME_BYTE2)) // Byte
|| type.equals(pool.get(Constants.TYPE_NAME_DOUBLE2)) // Double
|| type.equals(pool.get(Constants.TYPE_NAME_FLOAT2)) // Float
|| type.equals(pool.get(Constants.TYPE_NAME_INT2)) // Integer
|| type.equals(pool.get(Constants.TYPE_NAME_LONG2)) // Long
|| type.equals(pool.get(Constants.TYPE_NAME_SHORT2)) // Short
) {
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS); sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
if (field != null) {
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
}
}
private void insertCodeOfMessageUnpackForWrapperTypes(StringBuilder sb,
Field field, Class<?> type) throws NotFoundException {
// insert a right variable
if (field != null) {
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
}
sb.append(type.getName());
sb.append(Constants.CHAR_NAME_DOT);
sb.append(Constants.METHOD_NAME_VALUEOF);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.VARIABLE_NAME_PK);
sb.append(Constants.CHAR_NAME_DOT);
// insert the name of a unpack method
if (type.equals(Boolean.class)) { // Boolean
sb.append(Constants.METHOD_NAME_UNPACKBOOLEAN);
} else if (type.equals(Byte.class)) { // Byte
sb.append(Constants.METHOD_NAME_UNPACKBYTE);
} else if (type.equals(Double.class)) { // Double
sb.append(Constants.METHOD_NAME_UNPACKDOUBLE);
} else if (type.equals(Float.class)) { // Float
sb.append(Constants.METHOD_NAME_UNPACKFLOAT);
} else if (type.equals(Integer.class)) { // Integer
sb.append(Constants.METHOD_NAME_UNPACKINT);
} else if (type.equals(Long.class)) { // Long
sb.append(Constants.METHOD_NAME_UNPACKLONG);
} else if (type.equals(Short.class)) { // Short
sb.append(Constants.METHOD_NAME_UNPACKSHORT);
} else { } else {
return; throw new NotFoundException("unknown type: " + type.getName());
}
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
if (field != null) {
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
} }
} }
private void insertCodeOfMessageUnpackForListType(StringBuilder sb,
Field field, Class<?> type) throws NotFoundException {
ParameterizedType generic = (ParameterizedType) field
.getGenericType();
Class<?> genericType = (Class<?>) generic.getActualTypeArguments()[0];
// len
sb.append(int.class.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_SIZE);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_PK);
sb.append(Constants.CHAR_NAME_DOT);
sb.append(Constants.METHOD_NAME_UNPACKARRAY);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
// field initializer
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.KEYWORD_NEW);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(ArrayList.class.getName());
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
// for loop
sb.append(Constants.KEYWORD_FOR);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(int.class.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_I);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(0);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_I);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_LESSTHAN);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_SIZE);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_PLUS);
sb.append(Constants.CHAR_NAME_PLUS);
sb.append(Constants.VARIABLE_NAME_I);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_LEFT_CURLY_BRACHET);
sb.append(Constants.CHAR_NAME_SPACE);
// block
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_DOT);
sb.append(Constants.METHOD_NAME_ADD);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
insertCodeOfMessageUnpack(sb, null, genericType);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET);
sb.append(Constants.CHAR_NAME_SPACE);
}
private void insertCodeOfMessageUnpackForMapType(StringBuilder sb,
Field field, Class<?> type) throws NotFoundException {
ParameterizedType generic = (ParameterizedType) field
.getGenericType();
Class<?> genericType0 = (Class<?>) generic.getActualTypeArguments()[0];
Class<?> genericType1 = (Class<?>) generic.getActualTypeArguments()[1];
// len
sb.append(int.class.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_SIZE);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_PK);
sb.append(Constants.CHAR_NAME_DOT);
sb.append(Constants.METHOD_NAME_UNPACKMAP);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
// field initializer
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.KEYWORD_NEW);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(HashMap.class.getName());
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
// for loop
sb.append(Constants.KEYWORD_FOR);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(int.class.getName());
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_I);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_EQUAL);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(0);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_I);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_LESSTHAN);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.VARIABLE_NAME_SIZE);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_PLUS);
sb.append(Constants.CHAR_NAME_PLUS);
sb.append(Constants.VARIABLE_NAME_I);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_LEFT_CURLY_BRACHET);
sb.append(Constants.CHAR_NAME_SPACE);
// block map.
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_DOT);
sb.append(Constants.METHOD_NAME_PUT);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
insertCodeOfMessageUnpack(sb, null, genericType0);
sb.append(Constants.CHAR_NAME_COMMA);
sb.append(Constants.CHAR_NAME_SPACE);
insertCodeOfMessageUnpack(sb, null, genericType1);
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET);
sb.append(Constants.CHAR_NAME_SPACE);
}
private void insertCodeOfMessageUnpackForMsgUnpackableType(
StringBuilder sb, Field field, Class<?> type) {
// insert a right variable // ignore
sb.append(Constants.VARIABLE_NAME_PK);
sb.append(Constants.CHAR_NAME_DOT);
sb.append(Constants.METHOD_NAME_UNPACK);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_LEFT_PARENTHESIS);
sb.append(MessageUnpackable.class.getName());
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(field.getName());
sb.append(Constants.CHAR_NAME_RIGHT_PARENTHESIS);
sb.append(Constants.CHAR_NAME_SEMICOLON);
sb.append(Constants.CHAR_NAME_SPACE);
} }
private void addMessageConvertMethod(CtClass enhCtClass, private void addMessageConvertMethod(CtClass enhCtClass,
CtClass origCtClass, CtField[] fields) CtClass origCtClass, Field[] fields)
throws CannotCompileException { throws CannotCompileException {
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();
sb.append(Constants.KEYWORD_MODIFIER_PUBLIC).append( sb.append(Constants.KEYWORD_MODIFIER_PUBLIC).append(
@ -597,7 +702,7 @@ public class PackUnpackUtil {
Constants.CHAR_NAME_SPACE); Constants.CHAR_NAME_SPACE);
// TODO // TODO
sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET); sb.append(Constants.CHAR_NAME_RIGHT_CURLY_BRACHET);
System.out.println("messageConvert method: " + sb.toString()); //System.out.println("messageConvert method: " + sb.toString());
CtMethod newCtMethod = CtNewMethod.make(sb.toString(), enhCtClass); CtMethod newCtMethod = CtNewMethod.make(sb.toString(), enhCtClass);
enhCtClass.addMethod(newCtMethod); enhCtClass.addMethod(newCtMethod);
} }
@ -684,6 +789,6 @@ public class PackUnpackUtil {
ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray()); ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
Unpacker pac = new Unpacker(in); Unpacker pac = new Unpacker(in);
pac.unpack((MessageUnpackable) dst); pac.unpack((MessageUnpackable) dst);
System.out.println(src.equals(dst)); //System.out.println(src.equals(dst));
} }
} }

View File

@ -3,6 +3,9 @@ package org.msgpack.util.annotation;
import java.io.ByteArrayInputStream; import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream; import java.io.ByteArrayOutputStream;
import java.math.BigInteger; import java.math.BigInteger;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
@ -16,9 +19,9 @@ import org.msgpack.Unpacker;
public class TestMessagePackUnpackable extends TestCase { public class TestMessagePackUnpackable extends TestCase {
@Test @Test
public void testGeneralPrimitiveTypeFields() throws Exception { public void testPrimitiveTypeFields() throws Exception {
GeneralPrimitiveTypeFieldsClass src = (GeneralPrimitiveTypeFieldsClass) PackUnpackUtil PrimitiveTypeFieldsClass src = (PrimitiveTypeFieldsClass) PackUnpackUtil
.newEnhancedInstance(GeneralPrimitiveTypeFieldsClass.class); .newEnhancedInstance(PrimitiveTypeFieldsClass.class);
src.f0 = (byte) 0; src.f0 = (byte) 0;
src.f1 = 1; src.f1 = 1;
src.f2 = 2; src.f2 = 2;
@ -28,8 +31,8 @@ public class TestMessagePackUnpackable extends TestCase {
src.f6 = false; src.f6 = false;
ByteArrayOutputStream out = new ByteArrayOutputStream(); ByteArrayOutputStream out = new ByteArrayOutputStream();
new Packer(out).pack(src); new Packer(out).pack(src);
GeneralPrimitiveTypeFieldsClass dst = (GeneralPrimitiveTypeFieldsClass) PackUnpackUtil PrimitiveTypeFieldsClass dst = (PrimitiveTypeFieldsClass) PackUnpackUtil
.newEnhancedInstance(GeneralPrimitiveTypeFieldsClass.class); .newEnhancedInstance(PrimitiveTypeFieldsClass.class);
ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray()); ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
Unpacker pac = new Unpacker(in); Unpacker pac = new Unpacker(in);
pac.unpack((MessageUnpackable) dst); pac.unpack((MessageUnpackable) dst);
@ -43,7 +46,7 @@ public class TestMessagePackUnpackable extends TestCase {
} }
@MessagePackUnpackable @MessagePackUnpackable
public static class GeneralPrimitiveTypeFieldsClass { public static class PrimitiveTypeFieldsClass {
public byte f0; public byte f0;
public short f1; public short f1;
public int f2; public int f2;
@ -52,7 +55,7 @@ public class TestMessagePackUnpackable extends TestCase {
public double f5; public double f5;
public boolean f6; public boolean f6;
public GeneralPrimitiveTypeFieldsClass() { public PrimitiveTypeFieldsClass() {
} }
} }
@ -107,15 +110,93 @@ public class TestMessagePackUnpackable extends TestCase {
} }
} }
public void testListAndMap() throws Exception { public void testListTypes() throws Exception {
SampleListTypes src = (SampleListTypes) PackUnpackUtil
.newEnhancedInstance(SampleListTypes.class);
src.f0 = new ArrayList<Integer>();
src.f1 = new ArrayList<Integer>();
src.f1.add(1);
src.f1.add(2);
src.f1.add(3);
src.f2 = new ArrayList<String>();
src.f2.add("e1");
src.f2.add("e2");
src.f2.add("e3");
ByteArrayOutputStream out = new ByteArrayOutputStream();
new Packer(out).pack(src);
SampleListTypes dst = (SampleListTypes) PackUnpackUtil
.newEnhancedInstance(SampleListTypes.class);
ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
Unpacker pac = new Unpacker(in);
pac.unpack((MessageUnpackable) dst);
assertEquals(src.f0.size(), dst.f0.size());
assertEquals(src.f1.size(), dst.f1.size());
for (int i = 0; i < src.f1.size(); ++i) {
assertEquals(src.f1.get(i), dst.f1.get(i));
}
assertEquals(src.f2.size(), dst.f2.size());
for (int i = 0; i < src.f2.size(); ++i) {
assertEquals(src.f2.get(i), dst.f2.get(i));
}
} }
@MessagePackUnpackable @MessagePackUnpackable
public static class ListAndMapClass { public static class SampleListTypes {
public List<String> f0; public List<Integer> f0;
public Map<String, String> f1; public List<Integer> f1;
public List<String> f2;
public ListAndMapClass() { public SampleListTypes() {
}
}
public void testMapTypes() throws Exception {
SampleMapTypes src = (SampleMapTypes) PackUnpackUtil
.newEnhancedInstance(SampleMapTypes.class);
src.f0 = new HashMap<Integer, Integer>();
src.f1 = new HashMap<Integer, Integer>();
src.f1.put(1, 1);
src.f1.put(2, 2);
src.f1.put(3, 3);
src.f2 = new HashMap<String, Integer>();
src.f2.put("k1", 1);
src.f2.put("k2", 2);
src.f2.put("k3", 3);
ByteArrayOutputStream out = new ByteArrayOutputStream();
new Packer(out).pack(src);
SampleMapTypes dst = (SampleMapTypes) PackUnpackUtil
.newEnhancedInstance(SampleMapTypes.class);
ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
Unpacker pac = new Unpacker(in);
pac.unpack((MessageUnpackable) dst);
assertEquals(src.f0.size(), dst.f0.size());
assertEquals(src.f1.size(), dst.f1.size());
Iterator<Integer> srcf1 = src.f1.keySet().iterator();
Iterator<Integer> dstf1 = dst.f1.keySet().iterator();
while (srcf1.hasNext()) {
Integer s1 = srcf1.next();
Integer d1 = dstf1.next();
assertEquals(s1, d1);
assertEquals(src.f1.get(s1), dst.f1.get(d1));
}
assertEquals(src.f2.size(), dst.f2.size());
Iterator<String> srcf2 = src.f2.keySet().iterator();
Iterator<String> dstf2 = dst.f2.keySet().iterator();
while (srcf2.hasNext()) {
String s2 = srcf2.next();
String d2 = dstf2.next();
assertEquals(s2, d2);
assertEquals(src.f2.get(s2), dst.f2.get(d2));
}
}
@MessagePackUnpackable
public static class SampleMapTypes {
public Map<Integer, Integer> f0;
public Map<Integer, Integer> f1;
public Map<String, Integer> f2;
public SampleMapTypes() {
} }
} }