DataContractJsonSerializer и maxItemsInObjectGraph - PullRequest
1 голос
/ 03 мая 2011

Как я могу установить maxItemsInObjectGraph для DataContractJsonSerializer?

Я получаю сообщение об ошибке "Maximum number of items that can be serialized or deserialized in an object graph is '65536'. Change the object graph or increase the MaxItemsInObjectGraph quota."

Откуда происходит число 65536.В документации для DataContractJsonSerializer говорится, что по умолчанию используется значение Int32.MaxValue.

Я попытался установить его в конфигурации поведения:

 <endpointBehaviors>
    <behavior name="WebBehavior">
      <webHttp />
      <dataContractJsonSerializer maxItemsInObjectGraph="500000"/>
    </behavior>
 </endpointBehaviors>

, но я получаю сообщение об ошибке:"Invalid element in configuration. The extension name 'dataContractJsonSerializer' is not registered in the collection at system.serviceModel/extensions/behaviorExtensions."

Изменение поведения на <dataContractSerializer maxItemsInObjectGraph="500000"/> не вызывает ошибок, но не меняет значение (что неудивительно, поскольку я не использую dataContractSerializer)

Клиент созданс ChannelFactory, поэтому я не могу использовать атрибут ServiceBehavior, как описано здесь здесь

1 Ответ

2 голосов
/ 26 мая 2011

Я не знаю, можете ли вы сделать это через config (не пробовал), но вы можете увеличить свойство MaxItemsInObjectGraph в коде, и оно должно работать.В приведенном ниже примере, если я не увеличу его, вызов не будет выполнен;в противном случае это удастся.

public class StackOverflow_5867304_751090
{
    public class Product
    {
        public string Name { get; set; }
        public int Price { get; set; }
    }
    [ServiceContract]
    public interface ITest
    {
        [WebGet(ResponseFormat = WebMessageFormat.Json)]
        List<Product> GetProducts(int size);
    }
    public class Service : ITest
    {
        public List<Product> GetProducts(int size)
        {
            List<Product> result = new List<Product>();
            for (int i = 0; i < size; i++)
            {
                result.Add(new Product { Name = "Prod " + i, Price = i });
            }
            return result;
        }
    }
    static Binding GetBinding()
    {
        return new WebHttpBinding() { MaxReceivedMessageSize = int.MaxValue };
    }
    static void AddBehavior(ServiceEndpoint endpoint)
    {
        endpoint.Behaviors.Add(new WebHttpBehavior());
        foreach (var operation in endpoint.Contract.Operations)
        {
            DataContractSerializerOperationBehavior dcsob = operation.Behaviors.Find<DataContractSerializerOperationBehavior>();
            if (dcsob != null)
            {
                dcsob.MaxItemsInObjectGraph = 1000000;
            }
        }
    }
    public static void Test()
    {
        string baseAddress = "http://" + Environment.MachineName + ":8000/Service";
        ServiceHost host = new ServiceHost(typeof(Service), new Uri(baseAddress));
        ServiceEndpoint endpoint = host.AddServiceEndpoint(typeof(ITest), GetBinding(), "");
        AddBehavior(endpoint);
        host.Open();
        Console.WriteLine("Host opened");

        ChannelFactory<ITest> factory = new ChannelFactory<ITest>(GetBinding(), new EndpointAddress(baseAddress));
        AddBehavior(factory.Endpoint);
        ITest proxy = factory.CreateChannel();
        Console.WriteLine(proxy.GetProducts(100000).Count);

        Console.Write("Press ENTER to close the host");
        Console.ReadLine();
        host.Close();
    }
}
...