JObject.cs :  » Development » Json.NET » Newtonsoft » Json » Linq » C# / CSharp Open Source

Home
C# / CSharp Open Source
1.2.6.4 mono .net core
2.2.6.4 mono core
3.Aspect Oriented Frameworks
4.Bloggers
5.Build Systems
6.Business Application
7.Charting Reporting Tools
8.Chat Servers
9.Code Coverage Tools
10.Content Management Systems CMS
11.CRM ERP
12.Database
13.Development
14.Email
15.Forum
16.Game
17.GIS
18.GUI
19.IDEs
20.Installers Generators
21.Inversion of Control Dependency Injection
22.Issue Tracking
23.Logging Tools
24.Message
25.Mobile
26.Network Clients
27.Network Servers
28.Office
29.PDF
30.Persistence Frameworks
31.Portals
32.Profilers
33.Project Management
34.RSS RDF
35.Rule Engines
36.Script
37.Search Engines
38.Sound Audio
39.Source Control
40.SQL Clients
41.Template Engines
42.Testing
43.UML
44.Web Frameworks
45.Web Service
46.Web Testing
47.Wiki Engines
48.Windows Presentation Foundation
49.Workflows
50.XML Parsers
C# / C Sharp
C# / C Sharp by API
C# / CSharp Tutorial
C# / CSharp Open Source » Development » Json.NET 
Json.NET » Newtonsoft » Json » Linq » JObject.cs
#region License
// Copyright (c) 2007 James Newton-King
//
// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use,
// copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the
// Software is furnished to do so, subject to the following
// conditions:
//
// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
// OTHER DEALINGS IN THE SOFTWARE.
#endregion

using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.ComponentModel;
using System.Linq;
using System.IO;
using Newtonsoft.Json.Utilities;
using System.Globalization;
#if !PocketPC && !SILVERLIGHT
using Newtonsoft.Json.Linq.ComponentModel;
#endif

namespace Newtonsoft.Json.Linq{
  /// <summary>
  /// Represents a JSON object.
  /// </summary>
#if !PocketPC && !SILVERLIGHT
  [TypeDescriptionProvider(typeof(JTypeDescriptionProvider))]
#endif
  public class JObject : JContainer, IDictionary<string, JToken>, INotifyPropertyChanged
#if !PocketPC && !SILVERLIGHT && !NET20
    , INotifyPropertyChanging
#endif
  {
    /// <summary>
    /// Occurs when a property value changes.
    /// </summary>
    public event PropertyChangedEventHandler PropertyChanged;

#if !PocketPC && !SILVERLIGHT && !NET20
    /// <summary>
    /// Occurs when a property value is changing.
    /// </summary>
    public event PropertyChangingEventHandler PropertyChanging;
#endif

    /// <summary>
    /// Initializes a new instance of the <see cref="JObject"/> class.
    /// </summary>
    public JObject()
    {
    }

    /// <summary>
    /// Initializes a new instance of the <see cref="JObject"/> class from another <see cref="JObject"/> object.
    /// </summary>
    /// <param name="other">A <see cref="JObject"/> object to copy from.</param>
    public JObject(JObject other)
      : base(other)
    {
    }

    /// <summary>
    /// Initializes a new instance of the <see cref="JObject"/> class with the specified content.
    /// </summary>
    /// <param name="content">The contents of the object.</param>
    public JObject(params object[] content)
      : this((object)content)
    {
    }

    /// <summary>
    /// Initializes a new instance of the <see cref="JObject"/> class with the specified content.
    /// </summary>
    /// <param name="content">The contents of the object.</param>
    public JObject(object content)
    {
      Add(content);
    }

    internal override bool DeepEquals(JToken node)
    {
      JObject t = node as JObject;
      return (t != null && ContentsEqual(t));
    }

    internal override void ValidateToken(JToken o, JToken existing)
    {
      ValidationUtils.ArgumentNotNull(o, "o");

      if (o.Type != JTokenType.Property)
        throw new ArgumentException("Can not add {0} to {1}.".FormatWith(CultureInfo.InvariantCulture, o.GetType(), GetType()));

      // looping over all properties every time isn't good
      // need to think about performance here
      JProperty property = (JProperty)o;
      foreach (JProperty childProperty in Children())
      {
        if (childProperty != existing && string.Equals(childProperty.Name, property.Name, StringComparison.Ordinal))
          throw new ArgumentException("Can not add property {0} to {1}. Property with the same name already exists on object.".FormatWith(CultureInfo.InvariantCulture, property.Name, GetType()));
      }
    }

    internal void InternalPropertyChanged(JProperty childProperty)
    {
      OnPropertyChanged(childProperty.Name);
#if !SILVERLIGHT
      OnListChanged(new ListChangedEventArgs(ListChangedType.ItemChanged, IndexOfItem(childProperty)));
#else
      OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Replace, childProperty, childProperty, IndexOfItem(childProperty)));
#endif
    }

    internal void InternalPropertyChanging(JProperty childProperty)
    {
#if !PocketPC && !SILVERLIGHT && !NET20
      OnPropertyChanging(childProperty.Name);
#endif
    }

    internal override JToken CloneToken()
    {
      return new JObject(this);
    }

    /// <summary>
    /// Gets the node type for this <see cref="JToken"/>.
    /// </summary>
    /// <value>The type.</value>
    public override JTokenType Type
    {
      get { return JTokenType.Object; }
    }

    /// <summary>
    /// Gets an <see cref="IEnumerable{JProperty}"/> of this object's properties.
    /// </summary>
    /// <returns>An <see cref="IEnumerable{JProperty}"/> of this object's properties.</returns>
    public IEnumerable<JProperty> Properties()
    {
      return Children().Cast<JProperty>();
    }

    /// <summary>
    /// Gets a <see cref="JProperty"/> the specified name.
    /// </summary>
    /// <param name="name">The property name.</param>
    /// <returns>A <see cref="JProperty"/> with the specified name or null.</returns>
    public JProperty Property(string name)
    {
      return Properties()
        .Where(p => string.Equals(p.Name, name, StringComparison.Ordinal))
        .SingleOrDefault();
    }

    /// <summary>
    /// Gets an <see cref="JEnumerable{JToken}"/> of this object's property values.
    /// </summary>
    /// <returns>An <see cref="JEnumerable{JToken}"/> of this object's property values.</returns>
    public JEnumerable<JToken> PropertyValues()
    {
      return new JEnumerable<JToken>(Properties().Select(p => p.Value));
    }

    /// <summary>
    /// Gets the <see cref="JToken"/> with the specified key.
    /// </summary>
    /// <value>The <see cref="JToken"/> with the specified key.</value>
    public override JToken this[object key]
    {
      get
      {
        ValidationUtils.ArgumentNotNull(key, "o");

        string propertyName = key as string;
        if (propertyName == null)
          throw new ArgumentException("Accessed JObject values with invalid key value: {0}. Object property name expected.".FormatWith(CultureInfo.InvariantCulture, MiscellaneousUtils.ToString(key)));

        return this[propertyName];
      }
      set
      {
        ValidationUtils.ArgumentNotNull(key, "o");

        string propertyName = key as string;
        if (propertyName == null)
          throw new ArgumentException("Set JObject values with invalid key value: {0}. Object property name expected.".FormatWith(CultureInfo.InvariantCulture, MiscellaneousUtils.ToString(key)));

        this[propertyName] = value;
      }
    }

    /// <summary>
    /// Gets or sets the <see cref="Newtonsoft.Json.Linq.JToken"/> with the specified property name.
    /// </summary>
    /// <value></value>
    public JToken this[string propertyName]
    {
      get
      {
        ValidationUtils.ArgumentNotNull(propertyName, "propertyName");

        JProperty property = Property(propertyName);

        return (property != null) ? property.Value : null;
      }
      set
      {
        JProperty property = Property(propertyName);
        if (property != null)
        {
          property.Value = value;
        }
        else
        {
#if !PocketPC && !SILVERLIGHT && !NET20
          OnPropertyChanging(propertyName);
#endif
          Add(new JProperty(propertyName, value));
          OnPropertyChanged(propertyName);
        }
      }
    }

    /// <summary>
    /// Loads an <see cref="JObject"/> from a <see cref="JsonReader"/>. 
    /// </summary>
    /// <param name="reader">A <see cref="JsonReader"/> that will be read for the content of the <see cref="JObject"/>.</param>
    /// <returns>A <see cref="JObject"/> that contains the JSON that was read from the specified <see cref="JsonReader"/>.</returns>
    public static JObject Load(JsonReader reader)
    {
      ValidationUtils.ArgumentNotNull(reader, "reader");

      if (reader.TokenType == JsonToken.None)
      {
        if (!reader.Read())
          throw new Exception("Error reading JObject from JsonReader.");
      }
      if (reader.TokenType != JsonToken.StartObject)
        throw new Exception(
          "Error reading JObject from JsonReader. Current JsonReader item is not an object: {0}".FormatWith(
            CultureInfo.InvariantCulture, reader.TokenType));

      JObject o = new JObject();
      o.SetLineInfo(reader as IJsonLineInfo);
      
      if (!reader.Read())
        throw new Exception("Error reading JObject from JsonReader.");

      o.ReadContentFrom(reader);

      return o;
    }

    /// <summary>
    /// Load a <see cref="JObject"/> from a string that contains JSON.
    /// </summary>
    /// <param name="json">A <see cref="String"/> that contains JSON.</param>
    /// <returns>A <see cref="JObject"/> populated from the string that contains JSON.</returns>
    public static JObject Parse(string json)
    {
      JsonReader jsonReader = new JsonTextReader(new StringReader(json));

      return Load(jsonReader);
    }

    /// <summary>
    /// Creates a <see cref="JObject"/> from an object.
    /// </summary>
    /// <param name="o">The object that will be used to create <see cref="JObject"/>.</param>
    /// <returns>A <see cref="JObject"/> with the values of the specified object</returns>
    public static new JObject FromObject(object o)
    {
      return FromObject(o, new JsonSerializer());
    }

    /// <summary>
    /// Creates a <see cref="JArray"/> from an object.
    /// </summary>
    /// <param name="o">The object that will be used to create <see cref="JArray"/>.</param>
    /// <param name="jsonSerializer">The <see cref="JsonSerializer"/> that will be used to read the object.</param>
    /// <returns>A <see cref="JArray"/> with the values of the specified object</returns>
    public static new JObject FromObject(object o, JsonSerializer jsonSerializer)
    {
      JToken token = FromObjectInternal(o, jsonSerializer);

      if (token != null && token.Type != JTokenType.Object)
        throw new ArgumentException("Object serialized to {0}. JObject instance expected.".FormatWith(CultureInfo.InvariantCulture, token.Type));

      return (JObject)token;
    }

    /// <summary>
    /// Writes this token to a <see cref="JsonWriter"/>.
    /// </summary>
    /// <param name="writer">A <see cref="JsonWriter"/> into which this method will write.</param>
    /// <param name="converters">A collection of <see cref="JsonConverter"/> which will be used when writing the token.</param>
    public override void WriteTo(JsonWriter writer, params JsonConverter[] converters)
    {
      writer.WriteStartObject();

      foreach (JProperty property in ChildrenInternal())
      {
        property.WriteTo(writer, converters);
      }

      writer.WriteEndObject();
    }

    #region IDictionary<string,JToken> Members
    /// <summary>
    /// Adds the specified property name.
    /// </summary>
    /// <param name="propertyName">Name of the property.</param>
    /// <param name="value">The value.</param>
    public void Add(string propertyName, JToken value)
    {
      Add(new JProperty(propertyName, value));
    }

    bool IDictionary<string, JToken>.ContainsKey(string key)
    {
      return (Property(key) != null);
    }

    ICollection<string> IDictionary<string, JToken>.Keys
    {
      get { throw new NotImplementedException(); }
    }

    /// <summary>
    /// Removes the property with the specified name.
    /// </summary>
    /// <param name="propertyName">Name of the property.</param>
    /// <returns>true if item was successfully removed; otherwise, false.</returns>
    public bool Remove(string propertyName)
    {
      JProperty property = Property(propertyName);
      if (property == null)
        return false;

      property.Remove();
      return true;
    }

    /// <summary>
    /// Tries the get value.
    /// </summary>
    /// <param name="propertyName">Name of the property.</param>
    /// <param name="value">The value.</param>
    /// <returns>true if a value was successfully retrieved; otherwise, false.</returns>
    public bool TryGetValue(string propertyName, out JToken value)
    {
      JProperty property = Property(propertyName);
      if (property == null)
      {
        value = null;
        return false;
      }

      value = property.Value;
      return true;
    }

    ICollection<JToken> IDictionary<string, JToken>.Values
    {
      get { throw new NotImplementedException(); }
    }

    #endregion

    #region ICollection<KeyValuePair<string,JToken>> Members

    void ICollection<KeyValuePair<string,JToken>>.Add(KeyValuePair<string, JToken> item)
    {
      Add(new JProperty(item.Key, item.Value));
    }

    void ICollection<KeyValuePair<string, JToken>>.Clear()
    {
      RemoveAll();
    }

    bool ICollection<KeyValuePair<string,JToken>>.Contains(KeyValuePair<string, JToken> item)
    {
      JProperty property = Property(item.Key);
      if (property == null)
        return false;

      return (property.Value == item.Value);
    }

    void ICollection<KeyValuePair<string,JToken>>.CopyTo(KeyValuePair<string, JToken>[] array, int arrayIndex)
    {
      if (array == null)
        throw new ArgumentNullException("array");
      if (arrayIndex < 0)
        throw new ArgumentOutOfRangeException("arrayIndex", "arrayIndex is less than 0.");
      if (arrayIndex >= array.Length)
        throw new ArgumentException("arrayIndex is equal to or greater than the length of array.");
      if (Count > array.Length - arrayIndex)
        throw new ArgumentException("The number of elements in the source JObject is greater than the available space from arrayIndex to the end of the destination array.");

      int index = 0;
      foreach (JProperty property in Properties())
      {
        array[arrayIndex + index] = new KeyValuePair<string, JToken>(property.Name, property.Value);
        index++;
      }
    }

    /// <summary>
    /// Gets the number of elements contained in the <see cref="T:System.Collections.Generic.ICollection`1"/>.
    /// </summary>
    /// <value></value>
    /// <returns>The number of elements contained in the <see cref="T:System.Collections.Generic.ICollection`1"/>.</returns>
    public int Count
    {
      get { return Children().Count(); }
    }

    bool ICollection<KeyValuePair<string,JToken>>.IsReadOnly
    {
      get { return false; }
    }

    bool ICollection<KeyValuePair<string,JToken>>.Remove(KeyValuePair<string, JToken> item)
    {
      if (!((ICollection<KeyValuePair<string,JToken>>)this).Contains(item))
        return false;

      ((IDictionary<string, JToken>)this).Remove(item.Key);
      return true;
    }

    #endregion

    internal override int GetDeepHashCode()
    {
      return ContentsHashCode();
    }

    /// <summary>
    /// Returns an enumerator that iterates through the collection.
    /// </summary>
    /// <returns>
    /// A <see cref="T:System.Collections.Generic.IEnumerator`1"/> that can be used to iterate through the collection.
    /// </returns>
    public IEnumerator<KeyValuePair<string, JToken>> GetEnumerator()
    {
      foreach (JProperty property in Properties())
      {
        yield return new KeyValuePair<string, JToken>(property.Name, property.Value);
      }
    }

    /// <summary>
    /// Raises the <see cref="PropertyChanged"/> event with the provided arguments.
    /// </summary>
    /// <param name="propertyName">Name of the property.</param>
    protected virtual void OnPropertyChanged(string propertyName)
    {
      if (PropertyChanged != null)
        PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }

#if !PocketPC && !SILVERLIGHT && !NET20
    /// <summary>
    /// Raises the <see cref="PropertyChanging"/> event with the provided arguments.
    /// </summary>
    /// <param name="propertyName">Name of the property.</param>
    protected virtual void OnPropertyChanging(string propertyName)
    {
      if (PropertyChanging != null)
        PropertyChanging(this, new PropertyChangingEventArgs(propertyName));
    }
#endif
  }
}
www.java2v.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.