Мой тест показывает, что .NET Remoting быстрее, чем WCF 4, в 1,5 раза - PullRequest
7 голосов
/ 10 февраля 2012

Чтобы определить, должен ли мой проект мигрировать с удаленного взаимодействия с .net на WCF, я извлек его сетевую коммуникационную часть и реализовал его с помощью WCF.Я запускаю версию remoting и версию wcf и в итоге обнаруживаю, что remoting быстрее, чем wcf, в 1,5 раза, что сильно отличается от статьи msdn .

Тестовой конфигурации

WCF и .NET Remoting оба используют tcp канал без шифрования, нет файла app.config.Скомпилировано в режиме релиза, без оптимизации.

Операции

Вот что делает моя программа.sequence diagram

Вы можете скачать два решения здесь.

Тест WCF

Сервисный хост

    ServiceHost host = new ServiceHost(typeof(Server), new Uri(string.Format("net.tcp://{0}:{1}/{2}", args[0], args[1], args[2])));
    var binding = new NetTcpBinding();
    binding.MaxReceivedMessageSize = 614400;
    binding.ReaderQuotas.MaxArrayLength = 512000;//a max picture of 500KB
    binding.Security.Mode = SecurityMode.None;
    host.AddServiceEndpoint(typeof(IServer), binding, string.Empty);
    host.Open();

Сервер

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single
    //, IncludeExceptionDetailInFaults = true
    , ConcurrencyMode = ConcurrencyMode.Reentrant
    )]
public class Server : IServer
{
    public EntryRequirement GetEntryRequirement()
    {
        return new EntryRequirement(new[] { "fuck", "sex" }, false);
    }

    public void AddClient()
    {
        var client = OperationContext.Current.GetCallbackChannel<IServerCallback>();
        var p = client.Profile;
        var x = client.Password;
        System.Diagnostics.Debug.WriteLine(p);
        System.Diagnostics.Debug.WriteLine(x);
    }
}

Клиентская сторона

    Player player = new Player();
    player.Password = "12423";
    player.Profile = new Contracts.PlayerProfile
                         {
                             Description = "I'm a man.",
                             HeadImage = imageData,
                             Name = "Loveright"
                         };


    var binding = new NetTcpBinding();
    binding.Security.Mode = SecurityMode.None;
    Stopwatch watch = new Stopwatch();
    watch.Start();
    for (int i = 0; i < 20; i++)
    {
        ServerProxy server = new ServerProxy(player, binding, 
            new EndpointAddress(string.Format("net.tcp://{0}:{1}/{2}", args[0], args[1], args[2])));
        server.GetEntryRequirement();
        server.AddClient();
    }

    watch.Stop();

HeadImage - изображение размером 139 КБ.

Класс игрока

[CallbackBehavior(ConcurrencyMode = ConcurrencyMode.Reentrant)]
class Player : IServerCallback
{
    public PlayerProfile Profile { get; set; }

    public string Password { get; set; }

    public void ClientCollectionChangedEventHandler(object sender, ControllersChangedEventArgs e)
    {

    }

    public void ClientUpdatedEventHandler(object sender, ClientUpdatedEventArgs e)
    {

    }
}

Тест удаленного взаимодействия .NET

Хост

    var serverProv = new BinaryServerFormatterSinkProvider();
    serverProv.TypeFilterLevel = System.Runtime.Serialization.Formatters.TypeFilterLevel.Full;
    var clientProv = new BinaryClientFormatterSinkProvider();
    IDictionary props = new Hashtable();
    props["port"] = args[1];
    props["name"] = "tcp server";
    var channel = new TcpChannel(props, clientProv, serverProv);

    ChannelServices.RegisterChannel(channel, false);

    System.Runtime.Remoting.RemotingConfiguration.RegisterWellKnownServiceType(typeof(Server),
                                args[2], System.Runtime.Remoting.WellKnownObjectMode.Singleton);

Клиент

    var serverProv = new BinaryServerFormatterSinkProvider();
    serverProv.TypeFilterLevel = System.Runtime.Serialization.Formatters.TypeFilterLevel.Full;
    var clientProv = new BinaryClientFormatterSinkProvider();
    IDictionary props = new Hashtable();
    props["name"] = "tcp client " + Guid.NewGuid();
    props["port"] = 0;

    var channel = new TcpChannel(props, clientProv, serverProv);
    ChannelServices.RegisterChannel(channel, false);

    FileStream stream = new FileStream(@"logotz6.png", FileMode.Open);
    byte[] imageData = new byte[stream.Length];
    stream.Read(imageData, 0, imageData.Length);
    stream.Close();
    Player player = new Player();
    player.Password = "12423";
    player.Profile = new PlayerProfile
    {
        Description = "I'm a man.",
        HeadImage = imageData,
        Name = "Loveright"
    };

    Stopwatch watch = new Stopwatch();
    watch.Start();
    for (int i = 0; i < 20; i++)
    {
        var serverProxy = (IServer)Activator.GetObject(typeof(IServer), string.Format("tcp://{0}:{1}/{2}", args[0], args[1], args[2]));
        serverProxy.GetEntryRequirement();
        serverProxy.AddClient(player);
    }
    watch.Stop();

Вы можете скачать два решения здесь.

Результат

enter image description here

Так я сделаю тест где-нибудь несправедливым по отношению к WCF?

1 Ответ

0 голосов
/ 09 августа 2013

Должно ли это быть король кодировки сообщений?

Использовали ли вы binaryMessageEncoding вместо textMessageEncoding или soapMessageEncoding?

Вы можете создать собственную привязку для этого:

internal sealed class MyBinding : CustomBinding
{
    private static readonly BindingElementCollection elementCollection;

    static MyBinding()
    {
        MessageEncodingBindingElement encoding = new BinaryMessageEncodingBindingElement();

        TcpTransportBindingElement transport = new TcpTransportBindingElement();

        elementCollection = new BindingElementCollection();
        elementCollection.Add(encoding);
        elementCollection.Add(transport);
    }

    internal MyBinding(string bindingName, string bindingNamespace)
        : base()
    {
        base.Namespace = bindingNamespace;
        base.Name = bindingName;
    }

    public override BindingElementCollection CreateBindingElements()
    {
        return elementCollection;
    }
}
...