From 683b9d3ac0df33eb9b8375357bb36a27484ab3f3 Mon Sep 17 00:00:00 2001 From: huanghaiquan Date: Wed, 19 Jun 2019 10:41:59 +0800 Subject: [PATCH] Refactored the processing of bytes values of ContractEventSendOperation; --- .../com/jd/blockchain/consts/DataCodes.java | 17 - .../binaryproto/BinaryProtocol.java | 2 + .../contract/jvm/AbstractContractCode.java | 30 +- .../contract/ContractSerializeUtils.java | 330 +++++++++--------- .../contract/ContractSerializeUtils2.java | 195 ----------- .../jd/blockchain/contract/ContractType.java | 6 +- .../blockchain/contract/param/WRAP_BYTES.java | 13 - .../blockchain/contract/param/WRAP_INT.java | 13 - .../blockchain/contract/param/WRAP_LONG.java | 13 - .../blockchain/contract/param/WRAP_SHORT.java | 13 - .../contract/param/WRAP_STRING.java | 13 - .../blockchain/ledger/BytesValueEncoding.java | 60 ++++ .../transaction/ContractInvocation.java | 8 +- .../ContractInvocationHandler.java | 42 +-- 14 files changed, 247 insertions(+), 508 deletions(-) delete mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils2.java delete mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_BYTES.java delete mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_INT.java delete mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_LONG.java delete mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_SHORT.java delete mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_STRING.java create mode 100644 source/ledger/ledger-model/src/main/java/com/jd/blockchain/ledger/BytesValueEncoding.java diff --git a/source/base/src/main/java/com/jd/blockchain/consts/DataCodes.java b/source/base/src/main/java/com/jd/blockchain/consts/DataCodes.java index e764c3f3..e2f8d65b 100644 --- a/source/base/src/main/java/com/jd/blockchain/consts/DataCodes.java +++ b/source/base/src/main/java/com/jd/blockchain/consts/DataCodes.java @@ -85,26 +85,9 @@ public interface DataCodes { //contract related; public static final int CONTRACT = 0xA00; - public static final int CONTRACT_BYTE = 0xA01; - public static final int CONTRACT_SHORT = 0xA02; - public static final int CONTRACT_INT = 0xA03; - - public static final int CONTRACT_LONG = 0xA04; - - public static final int CONTRACT_STRING = 0xA05; - - public static final int CONTRACT_BYTES = 0xA06; - - public static final int CONTRACT_BIG_INT = 0xA07; //...0xA19 - public static final int CONTRACT_BIZ_CONTENT = 0xA20; - - public static final int CONTRACT_ARGS = 0xA21; - - public static final int CONTRACT_RETURN = 0xA22; - public static final int HASH = 0xB00; public static final int HASH_OBJECT = 0xB10; diff --git a/source/binary-proto/src/main/java/com/jd/blockchain/binaryproto/BinaryProtocol.java b/source/binary-proto/src/main/java/com/jd/blockchain/binaryproto/BinaryProtocol.java index e0b17277..ddf8e012 100644 --- a/source/binary-proto/src/main/java/com/jd/blockchain/binaryproto/BinaryProtocol.java +++ b/source/binary-proto/src/main/java/com/jd/blockchain/binaryproto/BinaryProtocol.java @@ -57,5 +57,7 @@ public class BinaryProtocol { } + + } diff --git a/source/contract/contract-jvm/src/main/java/com/jd/blockchain/contract/jvm/AbstractContractCode.java b/source/contract/contract-jvm/src/main/java/com/jd/blockchain/contract/jvm/AbstractContractCode.java index 3dfc4c58..e8ebb6a3 100644 --- a/source/contract/contract-jvm/src/main/java/com/jd/blockchain/contract/jvm/AbstractContractCode.java +++ b/source/contract/contract-jvm/src/main/java/com/jd/blockchain/contract/jvm/AbstractContractCode.java @@ -11,6 +11,8 @@ import com.jd.blockchain.contract.ContractException; import com.jd.blockchain.contract.EventProcessingAware; import com.jd.blockchain.contract.engine.ContractCode; import com.jd.blockchain.ledger.BytesValue; +import com.jd.blockchain.ledger.BytesValueEncoding; +import com.jd.blockchain.ledger.BytesValueList; import com.jd.blockchain.utils.Bytes; /** @@ -29,7 +31,7 @@ public abstract class AbstractContractCode implements ContractCode { this.version = version; this.contractDefinition = contractDefinition; } - + public ContractDefinition getContractDefinition() { return contractDefinition; } @@ -48,6 +50,7 @@ public abstract class AbstractContractCode implements ContractCode { public BytesValue processEvent(ContractEventContext eventContext) { EventProcessingAware evtProcAwire = null; Object retn = null; + Method handleMethod = null; Exception error = null; try { // 执行预处理; @@ -61,17 +64,19 @@ public abstract class AbstractContractCode implements ContractCode { } // 反序列化参数; - Method handleMethod = contractDefinition.getType().getHandleMethod(eventContext.getEvent()); + handleMethod = contractDefinition.getType().getHandleMethod(eventContext.getEvent()); if (handleMethod == null) { throw new ContractException( String.format("Contract[%s:%s] has no handle method to handle event[%s]!", address.toString(), contractDefinition.getType().getDeclaredClass().toString(), eventContext.getEvent())); } - - Object[] args = resolveArgs(); + + BytesValueList bytesValues = eventContext.getArgs(); + Object[] args = BytesValueEncoding.decode(bytesValues, handleMethod.getParameterTypes()); + retn = ReflectionUtils.invokeMethod(handleMethod, contractInstance, args); - + } catch (Exception e) { error = e; } @@ -91,23 +96,10 @@ public abstract class AbstractContractCode implements ContractCode { eventContext.getEvent(), address.toString(), error.getMessage()), error); } - BytesValue retnBytes = resolveResult(retn); + BytesValue retnBytes = BytesValueEncoding.encode(retn, handleMethod.getReturnType()); return retnBytes; } protected abstract Object getContractInstance(); - private BytesValue resolveResult(Object retn) { - if (retn == null) { - return null; - } - // TODO: resolve result in bytes; - throw new IllegalStateException("Not implemented!"); - } - - private Object[] resolveArgs() { - // TODO Auto-generated method stub - throw new IllegalStateException("Not implemented!"); - } - } diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils.java index 1f73a29f..e7cc92ef 100644 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils.java +++ b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils.java @@ -1,165 +1,165 @@ -package com.jd.blockchain.contract; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -import com.jd.blockchain.binaryproto.BinaryProtocol; -import com.jd.blockchain.binaryproto.DataContract; -import com.jd.blockchain.binaryproto.DataContractRegistry; -import com.jd.blockchain.contract.param.WRAP_BYTES; -import com.jd.blockchain.contract.param.WRAP_INT; -import com.jd.blockchain.contract.param.WRAP_LONG; -import com.jd.blockchain.contract.param.WRAP_SHORT; -import com.jd.blockchain.contract.param.WRAP_STRING; -import com.jd.blockchain.ledger.BytesValue; -import com.jd.blockchain.ledger.BytesValueList; -import com.jd.blockchain.utils.io.BytesUtils; - -public class ContractSerializeUtils { - - final static int INT_LENGTH = 4; - - static Map, Class> MAP = new HashMap<>(); - - static { - MAP.put(byte[].class, WRAP_BYTES.class); - MAP.put(Short.class, WRAP_SHORT.class); - MAP.put(short.class, WRAP_SHORT.class); - MAP.put(Integer.class, WRAP_INT.class); - MAP.put(int.class, WRAP_INT.class); - MAP.put(Long.class, WRAP_LONG.class); - MAP.put(long.class, WRAP_LONG.class); - MAP.put(String.class, WRAP_STRING.class); - - DataContractRegistry.register(WRAP_BYTES.class); - DataContractRegistry.register(WRAP_SHORT.class); - DataContractRegistry.register(WRAP_INT.class); - DataContractRegistry.register(WRAP_LONG.class); - DataContractRegistry.register(WRAP_STRING.class); - } - - public static boolean support(Class clazz) { - if (clazz.isAnnotationPresent(DataContract.class) || MAP.containsKey(clazz)) { - return true; - } - return false; - } - - public static BytesValue serialize(Object data) { - - if (data == null) { - return null; - } - - Class clazz = data.getClass(); - Class serialClass; - Object wrapData = data; - if (clazz.isAnnotationPresent(DataContract.class)) { - serialClass = clazz; - } else { - // 判断类型是否可以序列化 - Class wrapClass = MAP.get(clazz); - if (wrapClass == null) { - throw new IllegalArgumentException("There are Un-Support Type !!!"); - } - serialClass = wrapClass; - - if (wrapClass.equals(WRAP_BYTES.class)) { - wrapData = (WRAP_BYTES) () -> (byte[]) data; - } else if (wrapClass.equals(WRAP_INT.class)) { - wrapData = (WRAP_INT) () -> (int) data; - } else if (wrapClass.equals(WRAP_LONG.class)) { - wrapData = (WRAP_LONG) () -> (long) data; - } else if (wrapClass.equals(WRAP_SHORT.class)) { - wrapData = (WRAP_SHORT) () -> (short) data; - } else if (wrapClass.equals(WRAP_STRING.class)) { - wrapData = (WRAP_STRING) () -> (String) data; - } - } - // 按照对应接口进行序列化 - // 生成该接口对应的对象 - return BinaryProtocol.encode(wrapData, serialClass); - } - - public static BytesValueList serializeArray(Object[] datas) { - if (datas == null || datas.length == 0) { - return null; - } - int contentBytesSize = 0; - byte[] header = new byte[(datas.length + 1) * 4]; - System.arraycopy(BytesUtils.toBytes(datas.length), 0, header, 0, INT_LENGTH); - int offset = INT_LENGTH; - - List serialBytesList = new ArrayList<>(); - for (Object data : datas) { - // 按照对应接口进行序列化 - byte[] currBytes = serialize(data); - // 长度写入 - System.arraycopy(BytesUtils.toBytes(currBytes.length), 0, header, offset, INT_LENGTH); - serialBytesList.add(currBytes); - contentBytesSize += currBytes.length; - offset += INT_LENGTH; - } - - // 填充content - byte[] content = new byte[contentBytesSize]; - offset = 0; - for (byte[] bytes : serialBytesList) { - System.arraycopy(bytes, 0, content, offset, bytes.length); - offset += bytes.length; - } - // 将header和content组装 - return BytesUtils.concat(header, content); - } - - public static Object[] resolveArray(byte[] bytes) { - if (bytes == null || bytes.length == 0) { - return null; - } - byte[] lengthBytes = new byte[INT_LENGTH]; - System.arraycopy(bytes, 0, lengthBytes, 0, INT_LENGTH); - int length = BytesUtils.toInt(lengthBytes); - Object[] datas = new Object[length]; - - int headerOffset = INT_LENGTH; - int contentStart = (length + 1) * INT_LENGTH; - - for (int i = 0; i < length; i++) { - byte[] currDataLengthBytes = new byte[INT_LENGTH]; - System.arraycopy(bytes, headerOffset, currDataLengthBytes, 0, INT_LENGTH); - int currDataLength = BytesUtils.toInt(currDataLengthBytes); - // 读取 - byte[] dataBytes = new byte[currDataLength]; - System.arraycopy(bytes, contentStart, dataBytes, 0, currDataLength); - - datas[i] = resolve(dataBytes); - - contentStart += currDataLength; - headerOffset += INT_LENGTH; - } - - return datas; - } - - public static Object resolve(BytesValue bytes) { - // 反序列化该接口 - Object currData = BinaryProtocol.decode(bytes); - - // 代理对象类型不能使用class判断,只能使用instanceof - if (currData instanceof WRAP_STRING) { - return ((WRAP_STRING) currData).getValue(); - } else if (currData instanceof WRAP_INT) { - return ((WRAP_INT) currData).getValue(); - } else if (currData instanceof WRAP_LONG) { - return ((WRAP_LONG) currData).getValue(); - } else if (currData instanceof WRAP_BYTES) { - return ((WRAP_BYTES) currData).getValue(); - } else if (currData instanceof WRAP_SHORT) { - return ((WRAP_SHORT) currData).getValue(); - } else { - return currData; - } - } -} +//package com.jd.blockchain.contract; +// +//import java.util.ArrayList; +//import java.util.HashMap; +//import java.util.List; +//import java.util.Map; +// +//import com.jd.blockchain.binaryproto.BinaryProtocol; +//import com.jd.blockchain.binaryproto.DataContract; +//import com.jd.blockchain.binaryproto.DataContractRegistry; +//import com.jd.blockchain.contract.param.WRAP_BYTES; +//import com.jd.blockchain.contract.param.WRAP_INT; +//import com.jd.blockchain.contract.param.WRAP_LONG; +//import com.jd.blockchain.contract.param.WRAP_SHORT; +//import com.jd.blockchain.contract.param.WRAP_STRING; +//import com.jd.blockchain.ledger.BytesValue; +//import com.jd.blockchain.ledger.BytesValueList; +//import com.jd.blockchain.utils.io.BytesUtils; +// +//public class ContractSerializeUtils { +// +// final static int INT_LENGTH = 4; +// +// static Map, Class> MAP = new HashMap<>(); +// +// static { +// MAP.put(byte[].class, WRAP_BYTES.class); +// MAP.put(Short.class, WRAP_SHORT.class); +// MAP.put(short.class, WRAP_SHORT.class); +// MAP.put(Integer.class, WRAP_INT.class); +// MAP.put(int.class, WRAP_INT.class); +// MAP.put(Long.class, WRAP_LONG.class); +// MAP.put(long.class, WRAP_LONG.class); +// MAP.put(String.class, WRAP_STRING.class); +// +// DataContractRegistry.register(WRAP_BYTES.class); +// DataContractRegistry.register(WRAP_SHORT.class); +// DataContractRegistry.register(WRAP_INT.class); +// DataContractRegistry.register(WRAP_LONG.class); +// DataContractRegistry.register(WRAP_STRING.class); +// } +// +// public static boolean support(Class clazz) { +// if (clazz.isAnnotationPresent(DataContract.class) || MAP.containsKey(clazz)) { +// return true; +// } +// return false; +// } +// +// public static BytesValue serialize(Object data) { +// +// if (data == null) { +// return null; +// } +// +// Class clazz = data.getClass(); +// Class serialClass; +// Object wrapData = data; +// if (clazz.isAnnotationPresent(DataContract.class)) { +// serialClass = clazz; +// } else { +// // 判断类型是否可以序列化 +// Class wrapClass = MAP.get(clazz); +// if (wrapClass == null) { +// throw new IllegalArgumentException("There are Un-Support Type !!!"); +// } +// serialClass = wrapClass; +// +// if (wrapClass.equals(WRAP_BYTES.class)) { +// wrapData = (WRAP_BYTES) () -> (byte[]) data; +// } else if (wrapClass.equals(WRAP_INT.class)) { +// wrapData = (WRAP_INT) () -> (int) data; +// } else if (wrapClass.equals(WRAP_LONG.class)) { +// wrapData = (WRAP_LONG) () -> (long) data; +// } else if (wrapClass.equals(WRAP_SHORT.class)) { +// wrapData = (WRAP_SHORT) () -> (short) data; +// } else if (wrapClass.equals(WRAP_STRING.class)) { +// wrapData = (WRAP_STRING) () -> (String) data; +// } +// } +// // 按照对应接口进行序列化 +// // 生成该接口对应的对象 +// return BinaryProtocol.encode(wrapData, serialClass); +// } +// +// public static BytesValueList serializeArray(Object[] datas) { +// if (datas == null || datas.length == 0) { +// return null; +// } +// int contentBytesSize = 0; +// byte[] header = new byte[(datas.length + 1) * 4]; +// System.arraycopy(BytesUtils.toBytes(datas.length), 0, header, 0, INT_LENGTH); +// int offset = INT_LENGTH; +// +// List serialBytesList = new ArrayList<>(); +// for (Object data : datas) { +// // 按照对应接口进行序列化 +// byte[] currBytes = serialize(data); +// // 长度写入 +// System.arraycopy(BytesUtils.toBytes(currBytes.length), 0, header, offset, INT_LENGTH); +// serialBytesList.add(currBytes); +// contentBytesSize += currBytes.length; +// offset += INT_LENGTH; +// } +// +// // 填充content +// byte[] content = new byte[contentBytesSize]; +// offset = 0; +// for (byte[] bytes : serialBytesList) { +// System.arraycopy(bytes, 0, content, offset, bytes.length); +// offset += bytes.length; +// } +// // 将header和content组装 +// return BytesUtils.concat(header, content); +// } +// +// public static Object[] resolveArray(byte[] bytes) { +// if (bytes == null || bytes.length == 0) { +// return null; +// } +// byte[] lengthBytes = new byte[INT_LENGTH]; +// System.arraycopy(bytes, 0, lengthBytes, 0, INT_LENGTH); +// int length = BytesUtils.toInt(lengthBytes); +// Object[] datas = new Object[length]; +// +// int headerOffset = INT_LENGTH; +// int contentStart = (length + 1) * INT_LENGTH; +// +// for (int i = 0; i < length; i++) { +// byte[] currDataLengthBytes = new byte[INT_LENGTH]; +// System.arraycopy(bytes, headerOffset, currDataLengthBytes, 0, INT_LENGTH); +// int currDataLength = BytesUtils.toInt(currDataLengthBytes); +// // 读取 +// byte[] dataBytes = new byte[currDataLength]; +// System.arraycopy(bytes, contentStart, dataBytes, 0, currDataLength); +// +// datas[i] = resolve(dataBytes); +// +// contentStart += currDataLength; +// headerOffset += INT_LENGTH; +// } +// +// return datas; +// } +// +// public static Object resolve(BytesValue bytes) { +// // 反序列化该接口 +// Object currData = BinaryProtocol.decode(bytes); +// +// // 代理对象类型不能使用class判断,只能使用instanceof +// if (currData instanceof WRAP_STRING) { +// return ((WRAP_STRING) currData).getValue(); +// } else if (currData instanceof WRAP_INT) { +// return ((WRAP_INT) currData).getValue(); +// } else if (currData instanceof WRAP_LONG) { +// return ((WRAP_LONG) currData).getValue(); +// } else if (currData instanceof WRAP_BYTES) { +// return ((WRAP_BYTES) currData).getValue(); +// } else if (currData instanceof WRAP_SHORT) { +// return ((WRAP_SHORT) currData).getValue(); +// } else { +// return currData; +// } +// } +//} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils2.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils2.java deleted file mode 100644 index 22bbdb38..00000000 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractSerializeUtils2.java +++ /dev/null @@ -1,195 +0,0 @@ -//package com.jd.blockchain.contract; -// -//import com.jd.blockchain.binaryproto.BinaryProtocol; -//import com.jd.blockchain.binaryproto.DataContract; -//import com.jd.blockchain.consts.DataCodes; -//import com.jd.blockchain.ledger.*; -//import com.jd.blockchain.utils.Bytes; -//import com.jd.blockchain.utils.IllegalDataException; -//import org.springframework.util.ReflectionUtils; -// -//import java.nio.ByteBuffer; -//import java.util.Arrays; -//import java.util.HashMap; -//import java.util.List; -//import java.util.Map; -// -///** -// * @author zhaogw -// * date 2019/5/16 18:05 -// */ -//public class ContractSerializeUtils { -// public static Map> DATA_CONTRACT_MAP = new HashMap<>(); -// public static final Integer[] PRIMITIVE_DATA_CODES = {DataCodes.CONTRACT_INT8, DataCodes.CONTRACT_INT16, DataCodes.CONTRACT_INT32, -// DataCodes.CONTRACT_INT64, DataCodes.CONTRACT_BIG_INT,DataCodes.CONTRACT_TEXT, DataCodes.CONTRACT_BINARY }; -// -// /** -// * serialize the Object[] by List list; -// * @param objArr -// * @param dataContractList -// * @return -// */ -// public static byte[] serializeMethodParam(Object[] objArr,List dataContractList) { -// byte[][] result = new byte[objArr.length][]; -// //将method中形参转换为实体对象,每个形参都必须为@DataContract类型;每个形参使用系统的BinaryProtocol来进行序列化,如果有5个参数,则使用5次序列化; -// int sum = 0; -// -// for(int i=0;i dataContractList) { -// Object result[] = new Object[dataContractList.size()]; -// ByteBuffer byteBuffer = ByteBuffer.allocate(params.length); -// byteBuffer.put(params); -// int paramNums = byteBuffer.getInt(0); -// -// if(paramNums != dataContractList.size()){ -// throw new IllegalArgumentException("deserialize Method param. params'length in byte[] != method's param length"); -// } -// -// int offsetPosition = (1 + dataContractList.size())*4; //start position of real data; -// for(int i=0; i classObj = getDataIntf().get(dataContract.code()); -// try { -// result[i] = ReflectionUtils.invokeMethod(classObj.getMethod("getValue"),object); -// } catch (NoSuchMethodException e) { -// throw new IllegalStateException("no getValue(). detail="+e.getMessage()); -// } -// }else { -// result[i] = object; -// } -// byteBuffer1.clear(); -// } -// -// return result; -// } -// -// -// /** -// * the param types that we can support; -// * @param -// * @return -// */ -// public static Map > getDataIntf(){ -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_INT8, CONTRACT_INT8.class); -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_INT16, CONTRACT_INT16.class); -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_INT32, CONTRACT_INT32.class); -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_INT64, CONTRACT_INT64.class); -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_TEXT, CONTRACT_TEXT.class); -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_BINARY, CONTRACT_BINARY.class); -// DATA_CONTRACT_MAP.put(DataCodes.CONTRACT_BIZ_CONTENT, ContractBizContent.class); -// return DATA_CONTRACT_MAP; -// } -// -// public static boolean isPrimitiveType(int dataContractCode){ -// return Arrays.asList(PRIMITIVE_DATA_CODES).contains(dataContractCode); -// } -// -// private static Object regenObj(DataContract dataContract, Object object){ -// if(getDataIntf().get(dataContract.code()).equals(CONTRACT_INT8.class)){ -// -// return (CONTRACT_INT8) () -> Byte.parseByte(object.toString()); -// }else if(getDataIntf().get(dataContract.code()).equals(CONTRACT_INT16.class)){ -// return (CONTRACT_INT16) () -> Short.parseShort(object.toString()); -// }else if(getDataIntf().get(dataContract.code()).equals(CONTRACT_INT32.class)){ -// return (CONTRACT_INT32) () -> Integer.parseInt(object.toString()); -// }else if(getDataIntf().get(dataContract.code()).equals(CONTRACT_INT64.class)){ -// return (CONTRACT_INT64) () -> Long.parseLong(object.toString()); -// }else if(getDataIntf().get(dataContract.code()).equals(CONTRACT_TEXT.class)){ -// return (CONTRACT_TEXT) () -> object.toString(); -// }else if(getDataIntf().get(dataContract.code()).equals(CONTRACT_BINARY.class)){ -// return (CONTRACT_BINARY) () -> (Bytes) object; -// }else if(getDataIntf().get(dataContract.code()).equals(ContractBizContent.class)){ -// ContractBizContent contractBizContent = (ContractBizContent)object; -// return contractBizContent; -// }else { -// throw new IllegalDataException("cann't get new Object by dataContract and object."); -// } -// } -// -// /** -// * get contractType(contain @DataContract) by primitive class type; -// * some class type can be supported default (byte/char/int/long/String/Bytes, and so on). -// * in other words, need not contain the @DataContract in its class for contract param's serialization or deserialization. -// * @param classType -// * @return -// */ -// private static Class getContractTypeByPrimitiveType(Class classType) { -// if(classType.equals(byte.class) || classType.equals(Byte.class)){ -// return CONTRACT_INT8.class; -// }else if(classType.equals(char.class) || classType.equals(Character.class)){ -// return CONTRACT_INT16.class; -// }else if(classType.equals(int.class) || classType.equals(Integer.class)){ -// return CONTRACT_INT32.class; -// }else if(classType.equals(long.class) || classType.equals(Long.class)){ -// return CONTRACT_INT64.class; -// }else if(classType.equals(String.class)){ -// return CONTRACT_TEXT.class; -// }else if(classType.equals(Bytes.class)){ -// return CONTRACT_BINARY.class; -// }else { -// throw new IllegalDataException(String.format("no support the classType=%s, please check @DataContract.",classType.toString())); -// } -// } -// -// public static DataContract parseDataContract(Class classType){ -// DataContract dataContract = classType.getAnnotation(DataContract.class); -// //if the param's class Type don't contain @DataContract, then check parameterAnnotations of this method. -// if(dataContract == null){ -// boolean canPass = false; -// //if parameterAnnotations don't contain @DataContract, is it primitive type? -// Class contractType = getContractTypeByPrimitiveType(classType); -// dataContract = contractType.getAnnotation(DataContract.class); -// } -// if(!getDataIntf().containsKey(dataContract.code())){ -// throw new IllegalArgumentException(String.format( -// "for now, this @dataContract(code=%s) is forbidden in the param list.",dataContract.code())); -// } -// return dataContract; -// } -//} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractType.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractType.java index e70b385e..b0f5efbe 100644 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractType.java +++ b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/ContractType.java @@ -5,7 +5,7 @@ import java.util.HashMap; import java.util.Map; import java.util.Set; -import com.jd.blockchain.contract.ContractSerializeUtils; +import com.jd.blockchain.ledger.BytesValueEncoding; import com.jd.blockchain.utils.IllegalDataException; public class ContractType { @@ -113,7 +113,7 @@ public class ContractType { // check param's type is fit for need. Class[] paramTypes = method.getParameterTypes(); for (Class currParamType : paramTypes) { - if (!ContractSerializeUtils.support(currParamType)) { + if (!BytesValueEncoding.supportType(currParamType)) { throw new IllegalStateException( String.format("Param Type = %s can not support !!!", currParamType.getName())); } @@ -121,7 +121,7 @@ public class ContractType { // 判断返回值是否可序列化 Class returnType = method.getReturnType(); - if (!ContractSerializeUtils.support(returnType)) { + if (!BytesValueEncoding.supportType(returnType)) { throw new IllegalStateException( String.format("Return Type = %s can not support !!!", returnType.getName())); } diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_BYTES.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_BYTES.java deleted file mode 100644 index b99e6786..00000000 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_BYTES.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.jd.blockchain.contract.param; - -import com.jd.blockchain.binaryproto.DataContract; -import com.jd.blockchain.binaryproto.DataField; -import com.jd.blockchain.binaryproto.PrimitiveType; -import com.jd.blockchain.consts.DataCodes; - -@DataContract(code = DataCodes.CONTRACT_BYTES) -public interface WRAP_BYTES { - - @DataField(order = 1, primitiveType = PrimitiveType.BYTES) - byte[] getValue(); -} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_INT.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_INT.java deleted file mode 100644 index 48e2d1d9..00000000 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_INT.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.jd.blockchain.contract.param; - -import com.jd.blockchain.binaryproto.DataContract; -import com.jd.blockchain.binaryproto.DataField; -import com.jd.blockchain.binaryproto.PrimitiveType; -import com.jd.blockchain.consts.DataCodes; - -@DataContract(code = DataCodes.CONTRACT_INT) -public interface WRAP_INT { - - @DataField(order = 1, primitiveType = PrimitiveType.INT32) - int getValue(); -} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_LONG.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_LONG.java deleted file mode 100644 index 8b402b04..00000000 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_LONG.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.jd.blockchain.contract.param; - -import com.jd.blockchain.binaryproto.DataContract; -import com.jd.blockchain.binaryproto.DataField; -import com.jd.blockchain.binaryproto.PrimitiveType; -import com.jd.blockchain.consts.DataCodes; - -@DataContract(code = DataCodes.CONTRACT_LONG) -public interface WRAP_LONG { - - @DataField(order = 1, primitiveType = PrimitiveType.INT64) - long getValue(); -} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_SHORT.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_SHORT.java deleted file mode 100644 index d30cc366..00000000 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_SHORT.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.jd.blockchain.contract.param; - -import com.jd.blockchain.binaryproto.DataContract; -import com.jd.blockchain.binaryproto.DataField; -import com.jd.blockchain.binaryproto.PrimitiveType; -import com.jd.blockchain.consts.DataCodes; - -@DataContract(code = DataCodes.CONTRACT_SHORT) -public interface WRAP_SHORT { - - @DataField(order = 1, primitiveType = PrimitiveType.INT16) - short getValue(); -} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_STRING.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_STRING.java deleted file mode 100644 index 7c475c79..00000000 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/contract/param/WRAP_STRING.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.jd.blockchain.contract.param; - -import com.jd.blockchain.binaryproto.DataContract; -import com.jd.blockchain.binaryproto.DataField; -import com.jd.blockchain.binaryproto.PrimitiveType; -import com.jd.blockchain.consts.DataCodes; - -@DataContract(code = DataCodes.CONTRACT_STRING) -public interface WRAP_STRING { - - @DataField(order = 1, primitiveType = PrimitiveType.TEXT) - String getValue(); -} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/ledger/BytesValueEncoding.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/ledger/BytesValueEncoding.java new file mode 100644 index 00000000..d95aab99 --- /dev/null +++ b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/ledger/BytesValueEncoding.java @@ -0,0 +1,60 @@ +package com.jd.blockchain.ledger; + +public class BytesValueEncoding { + + + + + public static BytesValue encode(Object value, Class type) { + + } + + public static BytesValueList encode(Object[] values, Class[] types) { + + } + + public static Object decode(BytesValue value, Class type) { + + } + + public static Object[] decode(BytesValueList values, Class[] types) { + + } + + public static Object getDefaultValue(Class type) { + if (type == void.class || type == Void.class) { + return null; + } + + if (!type.isPrimitive()) { + // 非基本类型 + return null; + } else { + // 基本类型需要处理返回值,目前采用枚举遍历方式 + // 八种基本类型:int, double, float, long, short, boolean, byte, char, void + if (type.equals(int.class)) { + return 0; + } else if (type.equals(double.class)) { + return 0.0D; + } else if (type.equals(float.class)) { + return 0F; + } else if (type.equals(long.class)) { + return 0L; + } else if (type.equals(short.class)) { + return (short) 0; + } else if (type.equals(boolean.class)) { + return Boolean.FALSE; + } else if (type.equals(byte.class)) { + return (byte) 0; + } else if (type.equals(char.class)) { + return (char) 0; + } + return null; + } + } + + public static boolean supportType(Class currParamType) { + // TODO Auto-generated method stub + return false; + } +} diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocation.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocation.java index 100d1a75..cab7df0c 100644 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocation.java +++ b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocation.java @@ -6,6 +6,7 @@ import java.util.concurrent.Future; import com.jd.blockchain.contract.ContractType; import com.jd.blockchain.ledger.BytesValue; +import com.jd.blockchain.ledger.BytesValueEncoding; /** * ContractInvocation 包装了客户端发起的一次合约方法调用的相关信息,用于在客户端交易处理上下文进行共享处理状态; @@ -53,14 +54,9 @@ class ContractInvocation implements OperationReturnValueHandler { @Override public Object setReturnValue(BytesValue bytesValue) { // Resolve BytesValue to an value object with the return type; - Object returnValue = resolveValue(bytesValue, method.getReturnType()); + Object returnValue = BytesValueEncoding.decode(bytesValue, method.getReturnType()); returnValueFuture.complete(returnValue); return returnValue; } - private Object resolveValue(BytesValue bytesValue, Class returnType) { - // TODO: Resolve BytesValue to an value object with the return type; - throw new IllegalStateException("Not implemented!"); - } - } diff --git a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocationHandler.java b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocationHandler.java index 313fa9df..744eab47 100644 --- a/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocationHandler.java +++ b/source/ledger/ledger-model/src/main/java/com/jd/blockchain/transaction/ContractInvocationHandler.java @@ -5,8 +5,8 @@ import java.lang.reflect.Method; import java.util.Arrays; import com.jd.blockchain.contract.ContractException; -import com.jd.blockchain.contract.ContractSerializeUtils; import com.jd.blockchain.contract.ContractType; +import com.jd.blockchain.ledger.BytesValueEncoding; import com.jd.blockchain.ledger.BytesValueList; import com.jd.blockchain.utils.Bytes; import com.jd.blockchain.utils.IllegalDataException; @@ -52,7 +52,8 @@ public class ContractInvocationHandler implements InvocationHandler { method.toString())); } // 序列化调用参数; - BytesValueList argBytes = serializeArgs(args); + Class[] argTypes = method.getParameterTypes(); + BytesValueList argBytes = BytesValueEncoding.encode(args, argTypes); // 定义合约调用操作; ContractEventSendOpTemplate opTemplate = (ContractEventSendOpTemplate) sendOpBuilder.send(contractAddress, @@ -68,42 +69,7 @@ public class ContractInvocationHandler implements InvocationHandler { ContractInvocationStub.set(invocation); // 返回类型的默认值 - return getDefaultValue(method.getReturnType()); + return BytesValueEncoding.getDefaultValue(method.getReturnType()); } - private BytesValueList serializeArgs(Object[] args) { - return ContractSerializeUtils.serializeArray(args); - } - - private Object getDefaultValue(Class returnType) { - if (returnType == void.class || returnType == Void.class) { - return null; - } - - if (!returnType.isPrimitive()) { - // 非基本类型 - return null; - } else { - // 基本类型需要处理返回值,目前采用枚举遍历方式 - // 八种基本类型:int, double, float, long, short, boolean, byte, char, void - if (returnType.equals(int.class)) { - return 0; - } else if (returnType.equals(double.class)) { - return 0.0D; - } else if (returnType.equals(float.class)) { - return 0F; - } else if (returnType.equals(long.class)) { - return 0L; - } else if (returnType.equals(short.class)) { - return (short) 0; - } else if (returnType.equals(boolean.class)) { - return Boolean.FALSE; - } else if (returnType.equals(byte.class)) { - return (byte) 0; - } else if (returnType.equals(char.class)) { - return (char) 0; - } - return null; - } - } }