У меня есть вопрос о .Net Remoting, управлении версиями и создании объектов, активируемых клиентом.
Вот сценарий:
Есть 2 интерфейса, находящихся в собственной сборке «SharedTypes»: IServer и IAccount. IServer содержит методы «GetStatus», возвращающие строку, и «CreateAccount», возвращающие тип IAccount. Это зарегистрировано в GAC как v1.0.0.0.
Серверное приложение ссылается на SharedTypes и реализует IServer и IAccount с конкретными классами Server и Account. Это объекты MarshalByRefObject. Приложение Server маршалирует класс Server как одноэлементный объект.
Клиентское приложение ссылается на SharedTypes и успешно подключается к удаленному объекту сервера через интерфейс IServer. Здесь я могу успешно вызвать GetStatus и CreateAccount (которые возвращают объект, активированный клиентом). Пока все в порядке.
Теперь я увеличиваю версию SharedTypes до версии 2.0.0.0 и регистрируюсь в GAC, удаляя старую версию версии 1.0.0.0.
Серверное приложение создано для этой версии, а клиент — нет.
Теперь, когда я запускаю клиентское приложение, оно, как и ожидалось, будет жаловаться на System.IO.FileNotFoundException, т. е. не может найти v1.0.0.0 SharedTypes в GAC.
Если я скопирую v1.0.0.0 SharedTypes в каталог exe клиента, клиентское приложение в конечном итоге привязывается к этому (после неудачного поиска GAC). Клиентское приложение запускается, и я могу успешно вызвать GetStatus для объекта IServer (через одноэлементный объект). Однако, если я вызываю CreateAccount, который должен возвращать активированный клиентом объект, я получаю следующее исключение:
System.InvalidCastException: Return argument has an invalid type.
at System.Runtime.Remoting.Proxies.RealProxy.ValidateReturnArg(Object arg, Type paramType)
at System.Runtime.Remoting.Proxies.RealProxy.PropagateOutParameters(IMessage msg, Object[] outArgs, Object returnValue)
at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
at SharedTypes.IServer.GetAccount()
Мой вопрос заключается в том, почему вызов GetStatus на одноэлементном объекте, активированном сервером, от клиента (который использует v1.0.0.0) не вызывает это исключение, тогда как создание активированного клиентом объекта с помощью CreateAccount делает? Поскольку оба типа создаются на сервере, я бы подумал, что вызов GetStatus приведет к одному и тому же исключению?