Archived

This forum has been archived. Please start a new discussion on GitHub.

Without glacier,how the server side push some active message to the client side?

I am new to ICE,what I would like to know is:

1.Without glacier,how the server side actively push some message to the client side?
The client side of course do not use poll or request.
In slice,like:

["amd"] void pushSomeInfo(struct Info);

2.It is easier bug-prone using 3.4 new AMI method than the old style.Even though
using type-safe method,the logic codes become more complicated,requiring the
developers passing the right address of the successful method and/or failed method.

Actually,I would like to know an approach:
Using the old style,all operations share just one default failed method,dealing with
some unsatisfied condition and prompting to the user for example.I do not expect
in every cde_exception method adds some method named handle_exceptions,which
is quite boring,but use slice to auto generate it,and how could I do that ?

Thank you !

Comments

  • xdm
    xdm La Coruña, Spain
    1.Without glacier,how the server side actively push some message to the client side?
    The client side of course do not use poll or request.
    In slice,like:

    ["amd"] void pushSomeInfo(struct Info);

    See Bidirectional Connections - Ice 3.5 - ZeroC

    The demo Ice/bidir included in Ice distribution shows how to use bidirectional connections.
    2.It is easier bug-prone using 3.4 new AMI method than the old style.Even though
    using type-safe method,the logic codes become more complicated,requiring the
    developers passing the right address of the successful method and/or failed method.

    Actually,I would like to know an approach:
    Using the old style,all operations share just one default failed method,dealing with
    some unsatisfied condition and prompting to the user for example.I do not expect
    in every cde_exception method adds some method named handle_exceptions,which
    is quite boring,but use slice to auto generate it,and how could I do that ?

    Not sure why you think that was easier with the old mapping. In fact with the old mapping you need to inherit from a generated callback class with make that more difficult, you need to check the AMI documentation for the language mapping you are using.

    In c++
    MyCallbackPtr cb = new MyCallback;
    
    Callback_Employees_getNamePtr getNameCB =
        newCallback_Employees_getName(cb, &MyCallback::getNameCB, &MyCallback::failureCB);
    
    Callback_Employees_getNumberPtr getNumberCB =
        newCallback_Employees_getNumber(cb, &MyCallback::getNumberCB, &MyCallback::failureCB);
    
    e->begin_getName(99, getNameCB);
    e->begin_getNumber("Fred", getNumberCB);
    

    See: Asynchronous Method Invocation (AMI) in C++ - Ice 3.5 - ZeroC


    In C#
    C#
    MyCallback cb = new MyCallback();
    
    e.begin_getName(99).whenCompleted(cb.getNameCB, cb.failureCB);
    

    See: Asynchronous Method Invocation (AMI) in C-Sharp - Ice 3.5 - ZeroC

    In Java that cannot be done, as callbacks need to inherit from a generated class.

    Note that with new AMI there is also support for generic callbacks you should check the documentation for details.
  • Thank you a lot.

    1.It does help.Thanks again.

    2.Actually I already knew that the new style way could write some same
    exception call back.How to do this in the old style way is what I really
    want to know.

    3.When calling a RMI/RMD,we have to pass the interface name in string
    in the protocol,which consumes a lot bytes.For example,we call an interface
    named "[ami,amd] void hello()".In the byte streams,we have to use 5 bytes
    to write "hello".Why do we not adopt the way that use a protocol number to
    indicate which interface,whereas it just needs 4 bytes or less?Like,Num. 1
    indicates it is "hello" interface,while Num. 2 the next interface.

    4.I would like to build ICE into my project with source codes instead of share lib,
    then I could look into some problems step by step,or just to know about how ICE runs,
    How could I do that ?

    5.I hope someday there are some project file in ICE,like vc++,Xcode.
  • xdm
    xdm La Coruña, Spain
    2.Actually I already knew that the new style way could write some same
    exception call back.How to do this in the old style way is what I really
    want to know.

    There wasn't an easy way to do that with the old AMI mapping, that is one of the reasons to introduce a new AMI mapping, as the old mapping is now deprecated you should consider to move to the new mapping.
    3.When calling a RMI/RMD,we have to pass the interface name in string
    in the protocol,which consumes a lot bytes.For example,we call an interface
    named "[ami,amd] void hello()".In the byte streams,we have to use 5 bytes
    to write "hello".Why do we not adopt the way that use a protocol number to
    indicate which interface,whereas it just needs 4 bytes or less?Like,Num. 1
    indicates it is "hello" interface,while Num. 2 the next interface.

    The main reason to not use integers, is that it would make harder to maintain compatibility between different version of the same interface.
    4.I would like to build ICE into my project with source codes instead of share lib,
    then I could look into some problems step by step,or just to know about how ICE runs,
    How could I do that ?

    If you want to look into some problems step by step, just use the debugger, you don't need to build Ice into your project for that. Note that in Windows you must install Ice PDBs using Ice-PDBs-3.5.1-1.msi installer to get debug information.
    5.I hope someday there are some project file in ICE,like vc++,Xcode.
    We provide VC and XCode demo projects to build Ice demos.
  • xdm wrote: »
    If you want to look into some problems step by step, just use the debugger, you don't need to build Ice into your project for that. Note that in Windows you must install Ice PDBs using Ice-PDBs-3.5.1-1.msi installer to get debug information.

    In Linux,enter top_dir/cpp/src/Ice,do:
    g++ -m64 -Wall -Werror -pthread -fPIC -g -L../../lib -o test *.o -lIceUtil -lbz2 -ldl
    I remove the flags which would be passed to linker.
    In this way,I could debug step by step into the Ice source codes.
    please tell me there are some potential problems or not by doing this.
    xdm wrote: »
    We provide VC and XCode demo projects to build Ice demos.

    I have downloaded the source codes,but did NOT find any projects but Makefile.
    Where is VC and Xcode projects?


    One more,we see that IceUtil::Timer uses some thread separately from the dispatch thread of the
    AMD/AMI call.How could I achieve that the timer thread and dispatch thread both are thread-safe?
    When implementing the interface,there need some timers to do something.If they are thread-safe,we do not need to consider any sync conditions.

    Thank you very much!
  • xdm
    xdm La Coruña, Spain
    In Linux,enter top_dir/cpp/src/Ice,do:
    g++ -m64 -Wall -Werror -pthread -fPIC -g -L../../lib -o test *.o -lIceUtil -lbz2 -ldl
    I remove the flags which would be passed to linker.
    In this way,I could debug step by step into the Ice source codes.
    please tell me there are some potential problems or not by doing this.

    You don't need to do that, you should build Ice in debug mode using the provided Makefiles, then build your program in debug mode and link it with Ice and IceUtil libraries, finally use GDB to debug your program.
    I have downloaded the source codes,but did NOT find any projects but Makefile.
    Where is VC and Xcode projects?

    The Visual Studio projects for Ice demos are part of Windows source and demo distributions, Ice-3.5.1.zip and Ice-3.5.1-demos.zip files from the download page, the Visual Studio projects solutions are in Ice-3.5.1/cpp/demo/ and Ice-3.5.1-demos/demo directories.

    For Xcode we currently only have demo projects for Ice Touch not for Ice.

    If you want to use Visual Studio with Ice the simple is to use Ice Visual Studio Adddin the add-in is used by Ice demo projects an is installed by the Windows Ice installer.

    To use Ice with Xcode you can also use the Ice Xcode plug-in, the plug-in is installed by IceTouch installer and can be used to build IceTouch and Ice based projects.
    One more,we see that IceUtil::Timer uses some thread separately from the dispatch thread of the
    AMD/AMI call.How could I achieve that the timer thread and dispatch thread both are thread-safe?
    When implementing the interface,there need some timers to do something.If they are thread-safe,we do not need to consider any sync conditions.

    As you have found the timer uses a separate thread and you must use the appropriate synchronization mechanism when accessing shared data.
  • I have looked into some Ice sources and ran some examples.Then I bring more questions :)

    1.It is highly cost to maintain sessions between the server and the client by using polling repeatly as shown demo/Ice/session,especially when there are thousands of clients connected to the server.
    And there is no more reasons to use Glacier.So,what is the better solution of implementing sessions? Shall we add some ConnectionEvent-like class,doing the callbacks just at the time establishing a new connection or losing one?

    May I add a hook on ConnectionI::setState(Active) indicating a new ready connection,catching the loseConnection exception which indicating a lost connection?

    2.I run demo/Ice/hello server on one host,client on my macbook pro using IceTouch on the same LAN. It runs well.Then I switch off my wifi on my macbook.The tcp connection seems never closed using 'netstat -pta|grep server' on the host. Does this a bug or need to be done by ourself? ( OS X 10.9 Xcode 5.1.1 Ice3.5.1 IceTouch1.3.2)

    3.At src/EndpointFactoryManager.cpp:103,I think it could add a break when finding one factory.:)

    4.At HelloController.mm:76,hellocpp project of IceTouch 1.3.2 demo,it should be "hello:tcp -h" instead of "Hello:tcp -h".The hello example in Ice3.5.1 uses "hello".:)

    5.The rest projects except hellocpp say "can not find cassert" at line 151,file "Config.h",IceTouch 1.3.2 demo.The environment is the same with hellocpp,which compiles and runs well.I have set the Additional Sdks as:/Library/Developer/IceTouch-1.3.2/SDKs/Cpp/iphonesimulator.sdk.
  • xdm
    xdm La Coruña, Spain
    1.It is highly cost to maintain sessions between the server and the client by using polling repeatly as shown demo/Ice/session,especially when there are thousands of clients connected to the server.
    And there is no more reasons to use Glacier.So,what is the better solution of implementing sessions? Shall we add some ConnectionEvent-like class,doing the callbacks just at the time establishing a new connection or losing one?

    May I add a hook on ConnectionI::setState(Active) indicating a new ready connection,catching the loseConnection exception which indicating a lost connection?

    The session demo doesn't really use polling, it actively sends data (refresSession calls) so it could detect connection problems in a timely manner, otherwise could take much more time to detect a connection lost.

    You could adjust the time that a session sends a refreshMessage and split seessions into multiple servers, next Ice release will add some improvements to session management.

    See also Why does Ice not provide a callback to notify of connection closure?
    2.I run demo/Ice/hello server on one host,client on my macbook pro using IceTouch on the same LAN. It runs well.Then I switch off my wifi on my macbook.The tcp connection seems never closed using 'netstat -pta|grep server' on the host. Does this a bug or need to be done by ourself? ( OS X 10.9 Xcode 5.1.1 Ice3.5.1 IceTouch1.3.2)
    It will take time for the OS to detect the connection lost in this case that the server isn't actively sending data. the connection will be eventually closed, you don't need to close any connections manually when using Ice.
    3.At src/EndpointFactoryManager.cpp:103,I think it could add a break when finding one factory.
    Thanks for pointing this, it shouldn't be a problem in practice.
    4.At HelloController.mm:76,hellocpp project of IceTouch 1.3.2 demo,it should be "hello:tcp -h" instead of "Hello:tcp -h".The hello example in Ice3.5.1 uses "hello".

    I have review the demo archive and it has the correct endpoints, maybe you accidentally change it or you are looking at the wrong file.
    5.The rest projects except hellocpp say "can not find cassert" at line 151,file "Config.h",IceTouch 1.3.2 demo.The environment is the same with hellocpp,which compiles and runs well.I have set the Additional Sdks as:/Library/Developer/IceTouch-1.3.2/SDKs/Cpp/iphonesimulator.sdk.

    You don't need to configure anything to build the demo projects, the rest of the projects use the ObjC SDK not the C++ SDK. Best try to start with a clean demo distribution, and review the release notes.
  • It seems that we can NOT do the bidir/callback demo in the iPhone simulator,why ?
    It would block for ever.It has some limitations?
    When a client provides callback or using bidir,it is being a "server" role then.
    Why not just reuse the same connection which connected to the server previously?
  • xdm
    xdm La Coruña, Spain
    Bidir connections are supported with both iPhone and iPhone simulator, it's difficult to help with out more info.
  • First of all,the demo/bidir runs well between my macbook pro and my another host.
    The client on iPhone simulator could connect to the server and receive the validation connection message from the network and protocol trace.

    The client logs:
    -- 05/22/14 10:49:51.011 Network: trying to establish tcp connection to 192.168.2.151:10020
    -- 05/22/14 10:49:51.042 Network: tcp connection established
    local address = 192.168.3.114:51547
    remote address = 192.168.2.151:10020
    -- 05/22/14 10:49:51.042 Network: received 14 of 14 bytes via tcp
    local address = 192.168.3.114:51547
    remote address = 192.168.2.151:10020
    -- 05/22/14 10:49:51.042 Protocol: received validate connection
    message type = 3 (validate connection)
    compression status = 0 (not compressed; do not compress response, if any)
    message size = 14

    Then it would block for ever instead of sending ice_isA query message.

    For convenience,I add these codes to the hellocpp project:

    initData.properties->setProperty("CallbackSender.Proxy", "sender:tcp -h 192.168.2.151 -p 10020");
    initData.properties->setProperty("Ice.Trace.Network", "3");
    initData.properties->setProperty("Ice.Trace.Protocol", "1");
    initData.dispatcher = new Dispatcher();
    _communicator = Ice::initialize(initData);

    CallbackSenderPrx server = CallbackSenderPrx::checkedCast( _communicator->propertyToProxy("CallbackSender.Proxy"));
    if( ! server )
    {
    assert(false);
    }
    Ice::ObjectAdapterPtr adapter = _communicator->createObjectAdapter("");
    Ice::Identity ident;
    ident.name = IceUtil::generateUUID();
    ident.category = "";
    CallbackReceiverPtr cr = new CallbackReceiverI;
    adapter->add(cr, ident);
    adapter->activate();
    server->ice_getConnection()->setAdapter(adapter);
    server->addClient(ident);

    In xcode,I can not step into the source code to find out where it blocks.
  • xdm
    xdm La Coruña, Spain
    This seems a problem with doing a synchronous call from the main thread and using a Dispatcher that dispatches to this same thread. You shouldn't be doing a synchronous call from the main thread.

    See Dispatcher Implementation Notes