Подтвердить что ты не робот

Как написать службу WCF с постоянным хранилищем в памяти?

Я написал службу WCF, но данные, хранящиеся в реализации Service, не сохраняются между вызовами, даже если они хранятся в статической переменной. Что я могу сделать?

Реализация службы выглядит следующим образом:

public class Storage : IStorage
{
    protected static object[] _data;

    #region IStorage Members

    public void Insert(object[] data)
    {
        lock (_data)
        {
             _data = _data.Concat(data).ToArray();
        }
    }

    public object[] SelectAll()
    {
        lock (_data)
        {
            return (object[])_data.Clone();
        }
    }

    #endregion
}

Хост службы представляет собой консольное приложение:

static void Main(string[] args)
{
    ServiceHost serviceHost =
       new ServiceHost(typeof(TimeSpanStorage));
    serviceHost.Open();
    Console.WriteLine("Service running.  Please 'Enter' to exit...");
    Console.ReadLine();
}
4b9b3361

Ответ 1

По умолчанию для WCF instanceMode установлено значение "Вызов", то есть данные, используемые в службе, специфичны для этого клиента для этого вызова метода.

В своей реализации попробуйте добавить

[ServiceBehavior(InstanceContextMode=InstanceContextMode.Single, ConcurrencyMode=ConcurrencyMode.Single)]
public class MyService: IService

Это делает сервис по существу одноэлементным.

Ответ 2

Что вам нужно сделать, это создать долговечный сервис:

WCF Долговечные услуги - это услуги WCF в которых операции могут запоминаться значения частных переменных (= состояние услуги) между перезапусками serivcehost и/или клиент.

Ответ 3

Вы хотите сохранить данные за пределами вашего экземпляра ServiceHost? Если это так, то я согласен с тем, что долговременное обслуживание имеет смысл.

Однако, если вы только хотите сохранить данные между вызовами вашей службы WCF, пока служба жива, то долговременная услуга является излишней в моем скромном мнении. Использование статических данных вполне приемлемо; это то, что я делаю в своем проекте WCF. Фактически, код, который вы показали, должен работать, поэтому здесь происходит что-то еще.

Является ли метод Main() фактическим, как вы его показали? Если это так, то это проблема. Как только ваше консольное приложение с поддержкой WCF запустится, он немедленно отключится, запустив с ним службу WCF. У вас должна быть некоторая логика, чтобы поддерживать консольное приложение, потому что служба WCF останется только "размещенной", пока консольное приложение запущено.

Если это не проблема, сообщите мне, и я добавлю полный код простого приложения, демонстрирующего, как это сделать.

Ответ 4

Добавить

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single, ConcurrencyMode = ConcurrencyMode.Multiple)]

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

Теперь вам нужно позаботиться о том, чтобы ваша собственность читала/записывала, т.е. использовала блокировки, как вы уже сделали (или какую-то другую технику).