private void WriteCast(Expression Expression)
 {
     CastExpression cast = (CastExpression)Expression;
     if (_context.OutputTypeInformation && !(cast.Expression is ReferenceExpression))
         _jsonWriter.WriteCast(cast.ResultType);
     Write(cast.Expression);
 }
        /// <summary>
        /// Evaluates the expression and populates an existing object with keys and values.
        /// </summary>
        /// <param name="expression">the expression to evaluate</param>
        /// <param name="existingObject">the existing object to populate</param>
        /// <param name="deserializer">the deserializer instance to use to deserialize other expressions</param>
        /// <returns>a populated object</returns>
        public override object Evaluate(Expression expression, object existingObject, IDeserializerHandler deserializer)
        {
            Type _dictionaryKeyType = typeof(string);
            Type _dictionaryValueType = null;
            Type genDict = existingObject.GetType().GetInterface(typeof(IDictionary<,>).Name);
            // attempt to figure out what the types of the values are, if no type is set already
            if (genDict != null)
            {
                Type[] genArgs = genDict.GetGenericArguments();
                _dictionaryKeyType = genArgs[0];
                _dictionaryValueType = genArgs[1];
            }

            ObjectExpression objectExpression = (ObjectExpression)expression;
            foreach (KeyValueExpression keyValue in objectExpression.Properties)
            {
                // if no type set, set one
                keyValue.KeyExpression.ResultType = _dictionaryKeyType;
                if (_dictionaryValueType != null)
                    keyValue.ValueExpression.ResultType = _dictionaryValueType;

                object keyObject = deserializer.Evaluate(keyValue.KeyExpression);
                object result = deserializer.Evaluate(keyValue.ValueExpression);
                ((IDictionary)existingObject)[keyObject] = result;
            }
            return existingObject;
        }
        /// <summary>
        /// Evaluates the expression and populates an existing object with the expression's properties
        /// </summary>
        /// <param name="expression">json object expression</param>
        /// <param name="existingObject">the existing object to populate</param>
        /// <param name="deserializer">deserializer for deserializing key values</param>
        /// <returns>deserialized object</returns>
        public override object Evaluate(Expression expression, object existingObject, IDeserializerHandler deserializer)
        {
            TypeData typeHandler = Context.GetTypeHandler(existingObject.GetType());
            ObjectExpression objectExpression = (ObjectExpression)expression;
            foreach (KeyValueExpression Item in objectExpression.Properties)
            {
                // evaluate the item and let it assign itself?
                IPropertyData hndlr = typeHandler.FindProperty(Item.Key);
                if (hndlr == null)
                {
                    throw new Exception(string.Format("Could not find property {0} for type {1}", Item.Key, typeHandler.ForType));
                }
                if (hndlr.Ignored)
                {
                    switch (Context.IgnoredPropertyAction)
                    {
                        case SerializationContext.IgnoredPropertyOption.Ignore:
                            continue;
                        case SerializationContext.IgnoredPropertyOption.SetIfPossible:
                            if (!hndlr.CanWrite)
                                continue;
                            break;
                        case SerializationContext.IgnoredPropertyOption.ThrowException:
                            throw new Exception(string.Format("Can not set property {0} for type {1} because it is ignored and IgnorePropertyAction is set to ThrowException", Item.Key, typeHandler.ForType));
                    }
                }
                Expression valueExpression = Item.ValueExpression;
                valueExpression.ResultType = hndlr.PropertyType;
                object result = null;
                TypeConverterExpressionHandler converterHandler = null;
                IJsonTypeConverter converter = null;
                if (hndlr.HasConverter)
                {
                    converterHandler = (TypeConverterExpressionHandler) Context.ExpressionHandlers.Find(typeof(TypeConverterExpressionHandler));
                    converter = hndlr.TypeConverter;
                }

                if (!hndlr.CanWrite)
                {
                    result = hndlr.GetValue(existingObject);
                    if (converterHandler != null)
                    {
                        converterHandler.Evaluate(valueExpression, result, deserializer, converter);

                    }
                    else
                    {
                        deserializer.Evaluate(valueExpression, result);
                    }
                }
                else
                {
                    if (hndlr.HasConverter)
                        hndlr.SetValue(existingObject, converterHandler.Evaluate(valueExpression,deserializer,converter));
                    else
                        hndlr.SetValue(existingObject, deserializer.Evaluate(valueExpression));
                }
            }
            return existingObject;
        }
 public Expression Execute(Expression root)
 {
     IList<ReferenceExpression> references = CollectReferences(root);
     foreach (ReferenceExpression reference in references)
         ResolveReference(reference, root);
     return root;
 }
 /// <summary>
 /// Evaluates the expression and deserializes it.
 /// </summary>
 /// <param name="expression">json object expression</param>
 /// <param name="deserializer">deserializer for deserializing key values</param>
 /// <returns>deserialized object</returns>
 public override object Evaluate(Expression expression, IDeserializerHandler deserializer)
 {
     object value = ConstructObject((ObjectExpression)expression, deserializer);
     value = Evaluate(expression, value, deserializer);
     if (value is IDeserializationCallback)
         ((IDeserializationCallback)value).OnAfterDeserialization();
     return value;
 }
 private static void ResolveReference(ReferenceExpression reference, Expression root)
 {
     ReferenceVisitor visitor = new ReferenceVisitor(reference.Path);
     visitor.Visit(root);
     if (visitor.ReferencedExpression == null)
         throw new ParseException("Unable to resolve reference to " + reference.Path);
     reference.ReferencedExpression = visitor.ReferencedExpression;
 }
 private void WriteList(Expression Expression)
 {
     ArrayExpression list = (ArrayExpression)Expression;
     _jsonWriter.WriteArrayStart();
     foreach (Expression item in list.Items)
         Write(item);
     _jsonWriter.WriteArrayEnd();
 }
 public override object Evaluate(Expression Expression, object existingObject, IDeserializerHandler deserializer)
 {
     Expression.OnObjectConstructed(existingObject);
     Type itemType = GetItemType(existingObject.GetType());
     EvaluateItems((ArrayExpression) Expression, existingObject, itemType, deserializer);
     if (existingObject is IDeserializationCallback)
         ((IDeserializationCallback)existingObject).OnAfterDeserialization();
     return existingObject;
 }
 /// <summary>
 /// Deserializes an expression by populating an existing object collection with the expression's items.
 /// </summary>
 /// <param name="expression">the expression to deserialize</param>
 /// <param name="existingObject">the collection to populate</param>
 /// <param name="deserializer">deserializer to deserialize list items</param>
 /// <returns>deserialized object</returns>
 public override object Evaluate(Expression expression, object existingObject, IDeserializerHandler deserializer)
 {
     Type ItemType;
     ArrayExpression list = (ArrayExpression)expression;
     ICollectionBuilder builder = ConstructBuilder(existingObject, list, out ItemType);
     object result = EvaluateItems(list, builder, ItemType, deserializer);
     if (result is IDeserializationCallback)
     {
         ((IDeserializationCallback)result).OnAfterDeserialization();
     }
     return result;
 }
 public override object Evaluate(Expression expression, IDeserializerHandler deserializer)
 {
     ValueExpression value = (ValueExpression)expression;
     if (value.ResultType.IsEnum)
         return Enum.Parse(value.ResultType, value.StringValue);
     else if (value.ResultType == typeof(object))
         return value.StringValue;
     else if (value.ResultType == typeof(string))
         return value.StringValue;
     else
         return Convert.ChangeType(value.Value, value.ResultType, CultureInfo.InvariantCulture);
 }
        /// <summary>
        /// Converts an expression to an object by first Evaluating the expression as its converted type and
        /// then converting that result using a type converter.
        /// </summary>
        /// <param name="expression">the expression to convert</param>
        /// <param name="deserializer">deserializer instance</param>
        /// <returns>an object created from the expression</returns>
        public override object Evaluate(Expression expression, IDeserializerHandler deserializer)
        {
            Type sourceType = expression.ResultType;
            TypeData handler = Context.TypeHandlerFactory[sourceType];
            IJsonTypeConverter converter;
            if (typeof(IJsonTypeConverter).IsAssignableFrom(sourceType))
            {
                converter = (IJsonTypeConverter) Activator.CreateInstance(sourceType);
            }
            else
            {
                converter = handler.TypeConverter;
            }

            return Evaluate(expression, deserializer, converter);
        }
 public void VisitComplexBase(ComplexExpressionBase expression)
 {
     if (_refID.Top == JsonPath.Root)
     {
         if (expression.Parent != null)
         {
             throw new ArgumentException("Reference for this passed to object that is not at the root", "refID");
         }
     }
     else
     {
         // have to assume that the parent checked that we were the right reference
         // should only get here if we have a parent, if no parent we're not valid
         if (expression.Parent == null)
             throw new ArgumentException("Invalid reference", "refID");
     }
     // it is this object, check if we need to go further
     _refID = _refID.ChildReference();
     if (_refID.IsEmpty) {
         _expr = expression;
     }
 }
 /// <summary>
 /// Converts an expression to an object by first Evaluating the expression as its converted type and
 /// then converting that result using the specified type converter.
 /// </summary>
 /// <param name="expression">the expression to convert</param>
 /// <param name="deserializer">deserializer instance</param>
 /// <param name="converter">the converter to use to convert the object</param>
 /// <returns>an object created from the expression</returns>
 public object Evaluate(Expression expression, IDeserializerHandler deserializer, IJsonTypeConverter converter)
 {
     Type sourceType = expression.ResultType;
     Type destType = converter.GetSerializedType(sourceType);
     expression.ResultType = destType;
     object tempResult = deserializer.Evaluate(expression);
     object result = converter.ConvertTo(tempResult, sourceType, Context);
     expression.OnObjectConstructed(result);
     if (result is IDeserializationCallback)
     {
         ((IDeserializationCallback)result).OnAfterDeserialization();
     }
     return result;
 }
 public override object Evaluate(Expression Expression, IDeserializerHandler deserializer)
 {
     object collection = ConstructCollection((ArrayExpression)Expression, deserializer);
     return Evaluate(Expression, collection, deserializer);
 }
 private void WriteBoolean(Expression expression)
 {
     _jsonWriter.WriteValue((bool)((BooleanExpression)expression).Value);
 }
 public void Write(Expression expression)
 {
     _actions[expression.GetType()](expression);
 }
 public static void Write(IJsonWriter writer, SerializationContext context, Expression expression)
 {
     new ExpressionWriter(writer, context).Write(expression);
 }
 private void WriteValue(Expression expression)
 {
     ValueExpression value = (ValueExpression)expression;
     _jsonWriter.WriteQuotedValue(value.StringValue);
 }
 /// <summary>
 /// Checks to see if this handler is able to convert the expression back into an object.
 /// </summary>
 /// <param name="expression">the expression that will be deserialized</param>
 /// <returns>true if this handler can handle the expression</returns>
 public virtual bool CanHandle(Expression expression)
 {
     return false;
 }
 /// <summary>
 /// Converts the expression back into an object
 /// </summary>
 /// <param name="expression">the expression</param>
 /// <param name="deserializer">the deserializer</param>
 /// <returns>null</returns>
 public override object Evaluate(Expression expression, IDeserializerHandler deserializer)
 {
     if (!(expression is NullExpression))
         throw new ArgumentException("expression should be NullExpression");
     return null;
 }
 private void WriteNull(Expression expression)
 {
     if (!(expression is NullExpression))
         throw new ArgumentException("Expression should be a NullExpression");
     _jsonWriter.WriteSpecialValue("null");
 }
 /// <summary>
 /// This method is invalid for TypeConverterExpressionHandler
 /// </summary>
 /// <exception cref="NotSupportedException">Evaluating an existing object is not supported by TypeConverterExpressionHandler</exception>
 public void Evaluate(Expression valueExpression, object result, IDeserializerHandler deserializer, IJsonTypeConverter converter)
 {
     //TODO: possibly allow this if the type implements IJsonTypeConverter itself
     throw new NotSupportedException("Cannot convert an existing object.");
 }
 /// <summary>
 /// Determines whether this handler can deserialize a specific expression.  The NullExpressionHandler
 /// only handles NullExpressions.
 /// </summary>
 /// <param name="expression">the expression</param>
 /// <returns>true if this handler handles the expression</returns>
 public override bool CanHandle(Expression expression)
 {
     return (expression is NullExpression);
 }
 public void Add(Expression item)
 {
     _items.Add(item);
     item.Parent = this;
 }
 /// <summary>
 /// Converts an existing object
 /// </summary>
 /// <param name="expression">the expression</param>
 /// <param name="existingObject">an existing object</param>
 /// <param name="deserializer">deserializer</param>
 /// <returns>the existing object</returns>
 public override object Evaluate(Expression expression, object existingObject, IDeserializerHandler deserializer)
 {
     return existingObject;
 }
 private void WriteNumeric(Expression expression)
 {
     NumericExpression numeric = (NumericExpression)expression;
     object value = numeric.Value;
     switch (Type.GetTypeCode(value.GetType()))
     {
         case TypeCode.Double:
             _jsonWriter.WriteValue((double)value);
             break;
         case TypeCode.Single:
             _jsonWriter.WriteValue((float)value);
             break;
         case TypeCode.Int64:
             _jsonWriter.WriteValue((long)value);
             break;
         case TypeCode.Decimal:
         case TypeCode.UInt64:
             _jsonWriter.WriteSpecialValue(string.Format("{0}", value));
             break;
         default:
             _jsonWriter.WriteValue((long)Convert.ChangeType(value, typeof(long), CultureInfo.InvariantCulture));
             break;
     }
 }
 public override object Evaluate(Expression expression, IDeserializerHandler deserializer)
 {
     ValueExpression valueExpr = (ValueExpression)expression;
     return DateTime.ParseExact(valueExpr.StringValue, dateFormat, Culture, dateTimeStyle);
 }
 private void WriteObject(Expression Expression)
 {
     ObjectExpression obj = (ObjectExpression)Expression;
     bool hasConstructor = false;
     if (obj.ConstructorArguments.Count > 0)
     {
         hasConstructor = true;
         _jsonWriter.WriteConstructorStart(obj.ResultType);
         _jsonWriter.WriteConstructorArgsStart();
         foreach (Expression ctorArg in obj.ConstructorArguments)
         {
             Write(ctorArg);
         }
         _jsonWriter.WriteConstructorArgsEnd();
     }
     if (!hasConstructor || obj.Properties.Count > 0)
     {
         _jsonWriter.WriteObjectStart();
         foreach (KeyValueExpression keyValue in obj.Properties)
         {
             _jsonWriter.WriteKey(keyValue.Key);
             Write(keyValue.ValueExpression);
         }
         _jsonWriter.WriteObjectEnd();
     }
     if (hasConstructor)
         _jsonWriter.WriteConstructorEnd();
 }
 /// <summary>
 /// Convert the expression into an object by populating an existing object with any necessary values.
 /// The existingObject will usually come from the get method of a property on an object that doesn't
 /// allow writing to the property.
 /// </summary>
 /// <param name="expression">the epxression to deserialize</param>
 /// <param name="existingObject">an existing object to populate</param>
 /// <param name="deserializer">deserializer instance to use to deserialize any child expressions</param>
 /// <returns>a fully deserialized object</returns>
 public abstract object Evaluate(Expression expression, object existingObject, IDeserializerHandler deserializer);
 private void WriteReference(Expression Expression)
 {
     ReferenceExpression refExpr = (ReferenceExpression)Expression;
     _jsonWriter.WriteSpecialValue(refExpr.Path.ToString());
 }