Remoting - przekazywanie zmiennych

0

Mam problem ze zdalnie wywoływanym obiektem w technologii Remoting. Serwer udostępnia klientowi obiekt Coordinator (kod podaję poniżej). Obiekt jest uruchamiany na serwerze w trybie SingleCall.

public class Coordinator : MarshalByRefObject, ICoordinator
    {
        public int Test(int var)
        {
        }
    }

Wywołanie obiektu i jego metody po stronie klienta wygląda tak:

ICoordinator coord = (ICoordinator)Activator.GetObject(
                    typeof(ICoordinator), "tcp://localhost:2000/Coordinator");
coord.test(1);

Jednak serwer posiada też kilka zmiennych określających jego stan i nie wiem jak te zmienne przekazać do obiektu Coordinator. Coordinator musi mieć do nich dostęp w trakcie działania.

Przez konstruktor nie da rady ich przekazać do klasy Coordinator. Jak można to obejść?

0

tzn. chcesz w kliencie do zmiennych z obiektu Coordinator bedacego na serwerze dobrac sie za pomoca proxy ICoordinator ? no to wprost:

  • napisac szereg funkcji TYP getZmienna(); i je wywolywac?
  • albo zamiast tego - propertiesy z getterami?
    i uzywac jak test()..

czy w ogole nie zrozumialem pytania?

0

Nie nie. Na serwerze jest sobie obiekt typu Coordinator. Na serwerze są też jakieś zmienne serwera.
Niestety Coordinator nie ma dostępu do tych zmiennych. Normalnie uporałbym sie z tym prosto: w konstruktorze dałbym Coordinatorowi referencje do tych zmiennych:

public Coordinator(myClass zmienna1, myClass2 zmienna2) {...}

Ale niestety tak nie mogę, bo konstrukora obiektu Coordinator nie wywołuję bezpośrednio na serwerze. Wywołuję go na kliencie za pomocą metody Activator.GetObject:

ICoordinator coord = (ICoordinator)Activator.GetObject(
                    typeof(ICoordinator), "tcp://localhost:2000/Coordinator");

I teraz jak przekazać obiektowi typu Coordinator te zmienne z serwer? W jaki sposób dać mu do nich dostęp? :)

0

hejhej.. hola. czy mnie pamiec myli, czy ten kodzik co podales tworzy po stornie klienta obiekt-PROXY sluzacy sie do przezroczystego laczenia sie z prawdziwym obiektem JUZ ISTNIEJACYM na serwerze..? (moja watpliwosc: czy JUZ on istnieje, czy wlasnie teraz zostanie stworzony na potrzeby wywolania..)

patrz ze mylisz strony.. chcesz aby klient przekazywal/nakazywal obiektwi serwerowemu dane pochodzace ze strony serwerowej? klient nie ma do nich dostepu jak sam mowisz:)

najprostsze rozwiazanie:

w obiekcie serwerowym, cacheowane property:

private Typ? _zmienna;
public Typ Zmienna
{
    get
    {   if(_zmienna != null) return null;
        else
            ..pobierz ustawienie z settingsow, pczypisz do zmiennej, i zwroc
    }
}
  • w ten sposob, obiekt Coordinator PO STRONIE SERWERA bedzie udostepnial pewne property pozwalajace dobrac sie do ustawien serwera.

  • w ten sposob, obiekt Coordinator PO STORNIE SERWERA bedzie mogl sobie te wartosc odczytywac bardzo szybko (ale bedzie niewrażliwy na jej zmiany w runtime.. aby to miec, trzeba zaimplementowac w/w bez cacheingu )

  • w ten sposob, wygenerowane PROXY rowniez bedzie mialo ten property

  • w ten sposob, KLIENT poprzez obiekt-PROXY bedzie mial dostep do tej zmiennej poprzez metode/property ICoordinator::Zmienna ktore polaczy sie transparentnie z SERWEROWYM Coordinator::Zmienna i sciagnie wartosc

..caly sek ktory mi albo Tobie sie myli: Coordinator istnieje na SERWERZE. na KLIENCIE jest tylko PROXY.. (patrz model ala CORBA)

0

Dzięki za próby pomocy, ale chyba źle wytłumaczyłem o o mi chodziło. :) Wystarczyło po prostu zastosować zmienne statyczne, dzieki czemu stawały sie one dostępne w całym programi za pomocą nazwy klasy, w której sie znajdowały, czyli np: Coordinator.zmiennaStatyczna = 2.0; Ale i tak dzięki. :)

Mam teraz inne pytanie, ciąg dalszy Remoting'u. Jeszcze z jedną rzeczą nie mogę sobie poradzić. Jak utworzyć kilka kanałów na raz? Konkretnie potrzebuję 2.

  1. Serwer musi udostępniać zdalny obiekt jednej grupie klientów (o tym już pisałem) na jednym kanale.
  2. A oprócz tego musi udostępniać inny zdalny obiekt drugiej grupie klientów. Próbowałem to zrobić tak:
   TcpChannel kanal1 = new TcpChannel(port);
   ChannelServices.RegisterChannel(kanal1);
   
   // Na razie wszystko jest OK, program działa.
   // Nastepnie rejestruje drugi kanal:

   TcpChannel kanal2 = new TcpChannel(innyPort);
   ChannelServices.RegisterChannel(kanal2);

I w tym momencie wywala wyjątek:

channel 'tcp' is already registered

Czyli może wystąpić tylko jedna rejestracja kanału. W dokumentacji jest jakiś przykład z rejestrowaniem kilku portów w jednym kanale (trzeba im wtedy chyba nadać jakieś nazwy, czy coś), ale nie mogę sie w nim połapać.

1 użytkowników online, w tym zalogowanych: 0, gości: 1