예제 #1
0
        private static object ReadFieldValue(this TProtocol protocol, TType thriftType, Type targetType)
        {
            switch (thriftType)
            {
            //case TType.Void:
            //    return null;
            case TType.Bool:
                return(protocol.ReadBool());

            case TType.Byte:
                return(protocol.ReadByte());

            case TType.I16:
                return(protocol.ReadI16());

            case TType.I32:
                return(protocol.ReadI32());

            case TType.I64:
                return(protocol.ReadI64());

            case TType.Double:
                return(protocol.ReadDouble());

            case TType.String:
                if (targetType == typeof(string) ||
                    targetType == typeof(Guid))
                {
                    return(protocol.ReadString());
                }
                else
                {
                    return(protocol.ReadBinary());
                }

            case TType.Struct:
                return(protocol.ReadStruct(targetType));

            case TType.List:
                var result = Activator.CreateInstance(targetType);
                var list   = result as IList;

                // 只考虑泛型list
                if (targetType.IsGenericType)
                {
                    var genericType = targetType.GetGenericArguments()[0];
                    var tlist       = protocol.ReadListBegin();
                    for (int i = 0; i < tlist.Count; i++)
                    {
                        var item = protocol.ReadFieldValue(genericType.ToThriftType(), genericType);
                        list.Add(item);
                    }
                    protocol.ReadListEnd();
                }

                return(result);

            case TType.Map:
                var resultMap = Activator.CreateInstance(targetType);
                var dic       = resultMap as IDictionary;

                // 只考虑泛型map
                if (targetType.IsGenericType)
                {
                    var genericTypes     = targetType.GetGenericArguments();
                    var genericTypeKey   = genericTypes[0];
                    var genericTypeValue = genericTypes[1];

                    var tmap = protocol.ReadMapBegin();
                    for (int i = 0; i < tmap.Count; i++)
                    {
                        var key   = protocol.ReadFieldValue(genericTypeKey.ToThriftType(), genericTypeKey);
                        var value = protocol.ReadFieldValue(genericTypeValue.ToThriftType(), genericTypeValue);
                        dic.Add(key, value);
                    }
                    protocol.ReadMapEnd();
                }

                return(resultMap);

            default:
                TProtocolUtil.Skip(protocol, thriftType);
                return(null);
            }
        }
예제 #2
0
        public static object ReadStruct(this TProtocol protocol, Type targetType)
        {
            object result   = null;
            var    dicProps = new Dictionary <int, PropertyInfo>();

            result = Activator.CreateInstance(targetType);

            if (targetType.IsClass)
            {
                var props = targetType.GetProperties();
                foreach (var prop in props)
                {
                    var attrs = prop.GetCustomAttributes(typeof(ThriftSMemberAttribute), false);
                    if (attrs.Any())
                    {
                        dicProps.Add((attrs[0] as ThriftSMemberAttribute).Tag, prop);
                    }
                }
            }

            var @struct = protocol.ReadStructBegin();

            while (true)
            {
                var field = protocol.ReadFieldBegin();
                if (field.Type == TType.Stop)
                {
                    break;
                }

                // 跳过不存在的字段
                if (dicProps.ContainsKey(field.ID))
                {
                    var fieldValue = protocol.ReadFieldValue(field.Type, dicProps[field.ID].PropertyType);

                    if (dicProps[field.ID].PropertyType == typeof(Guid))
                    {
                        dicProps[field.ID].SetValue(result, new Guid(fieldValue.ToString()));
                    }
                    else if (dicProps[field.ID].PropertyType == typeof(DateTime))
                    {
                        dicProps[field.ID].SetValue(result, DateTimeHelper.ToDateTime((long)fieldValue));
                    }
                    else if (dicProps[field.ID].PropertyType.IsEnum)
                    {
                        var enumValue = Enum.Parse(dicProps[field.ID].PropertyType, fieldValue.ToString());
                        dicProps[field.ID].SetValue(result, enumValue);
                    }
                    else if (dicProps[field.ID].PropertyType.IsValueType &&
                             dicProps[field.ID].PropertyType != fieldValue.GetType())
                    {
                        // ex: double --> decimal
                        var newFieldValue = Convert.ChangeType(fieldValue, dicProps[field.ID].PropertyType);
                        dicProps[field.ID].SetValue(result, newFieldValue);
                    }
                    else
                    {
                        dicProps[field.ID].SetValue(result, fieldValue);
                    }
                }

                protocol.ReadFieldEnd();
            }

            protocol.ReadStructEnd();
            return(result);
        }