Archived

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

How to keep the data accord in all servers?

For one client,the server compute it's connected with server,it returns the sum,but now every server count from 0.whY?

My Engilish is very poor!

application.xml
<icegrid>
<application name="Simple">

<server-template id="SimpleServer">
<parameter name="index"/>
<server id="SimpleServer-${index}" exe="server" activation="on-demand">
<adapter name="Hello" endpoints="tcp" replica-group="ReplicatedHelloAdapter"/>
<property name="Identity" value="hello"/>
</server>
</server-template>

<replica-group id="ReplicatedHelloAdapter">
<load-balancing type="random" n-replicas="2"/>
<object identity="hello" type="::Demo::Hello"/>
</replica-group>

<node name="node1">
<server-instance template="SimpleServer" index="1"/>
<server-instance template="SimpleServer" index="2"/>
</node>
<node name="node2">
<server-instance template="SimpleServer" index="3"/>
<server-instance template="SimpleServer" index="4"/>
</node>

</application>

</icegrid>

Comments

  • benoit
    benoit Rennes, France
    Hi,

    Each server has its own state and each server computation will be done independently from each other. IceGrid replica groups provide replication features to locate replicated Ice objects but it's up to you to implement the replication of their state if needed. If this doesn't answer your question, could you describe a little more through an example what you expect?

    Cheers,
    Benoit.
  • thank you!

    If have 1 server,it returns 1,2,3,4,5,6....
    but if have n server,every server will return 1,2,3,4,5,6.....I need they only have 1 sequence.

    For example:

    HelloI.cs

    using System;
    using System.Collections.Generic;
    using System.Text;
    using Test;

    namespace Server{
    public class HelloI:Test.TestClassDisp_
    {
    int temp = 0;
    public override int GetCount(Ice.Current current__)
    {
    temp += 1;
    return temp;
    //throw new NotImplementedException();
    }
    }
    }


    Server.cs
    using System;
    using System.Collections.Generic;
    //using System.Linq;
    using System.Text;
    using System.Reflection;

    namespace Server
    {
    public class Server
    {
    public class App : Ice.Application
    {
    public override int run(string[] args)
    {
    if (args.Length > 0)
    {
    System.Console.Error.WriteLine(appName() + ": too many arguments");
    return 1;
    }

    Ice.ObjectAdapter adapter = communicator().createObjectAdapter("Hello");
    Ice.Properties properties = communicator().getProperties();
    Ice.Identity id = communicator().stringToIdentity(properties.getProperty("Identity"));
    adapter.add(new HelloI(properties.getProperty("Ice.ProgramName")), id);
    adapter.activate();
    communicator().waitForShutdown();
    return 0;
    }
    }

    static public void Main(string[] args)
    {
    App app = new App();
    int status = app.main(args);
    if (status != 0)
    {
    System.Environment.Exit(status);
    }
    }
    }

    }

    Client.cs

    using Test;
    using System;
    using System.Reflection;

    public class Client
    {
    public class App : Ice.Application
    {
    private void menu()
    {
    Console.WriteLine(
    "usage:\n" +
    "g: get num\n" +
    "x: exit\n" +
    "?: help\n");
    }

    public override int run(string[] args)
    {
    if (args.Length > 0)
    {
    Console.Error.WriteLine(appName() + ": too many arguments");
    return 1;
    }

    if (args.Length > 0)
    {
    Console.Error.WriteLine(appName() + ": too many arguments");
    return 1;
    }

    Ice.ObjectPrx obj = communicator().stringToProxy("hello");
    obj = obj.ice_connectionCached(false);
    obj = obj.ice_locatorCacheTimeout(0);
    TestClassPrx hello = TestClassPrxHelper.checkedCast(obj);

    if (hello == null)
    {
    Console.WriteLine("couldn't find a `::Demo::Hello' object");
    return 1;
    }

    menu();

    string line = null;
    do
    {
    try
    {
    Console.Write("==> ");
    Console.Out.Flush();
    line = Console.In.ReadLine();
    if (line == null)
    {
    break;
    }

    if (line.Equals("g"))
    {
    int send = 1000;
    int get = 1000;
    int delay = 1000;

    for (int i = 1; i < send; i++)
    {
    System.Threading.Thread.Sleep(delay);
    int s = hello.GetCount();
    Console.WriteLine("The Client have connect " + s.ToString() + " times");
    }

    }
    else if (line.Equals("x"))
    {
    // Nothing to do
    }
    else if (line.Equals("?"))
    {
    menu();
    }
    else
    {
    Console.WriteLine("unknown command `" + line + "'");
    menu();
    }
    }
    catch (Ice.LocalException ex)
    {
    Console.WriteLine(ex);
    }
    }
    while (!line.Equals("x"));

    return 0;
    }
    }

    public static void Main(string[] args)
    {
    App app = new App();
    int status = app.main(args, "config.client");
    if (status != 0)
    {
    System.Environment.Exit(status);
    }
    }
    }
  • benoit
    benoit Rennes, France
    Hi,

    As mentioned in my first post, it's your responsibility to implement replication in the servant implementation. In other words, the implementation of the GetCount method needs to synchronize with other servers in order to share the same counter variable. How you implement this is up to you. You could for example simply use a remote SQL database where you store the counter value or synchronize the state of the servant yourself using some known replication technique (such as master/slave replication for example).

    I recommend to take a look at my newsletter article on replication here. It presents one way to design your interfaces to support some simple master/slave replication.

    Cheers,
    Benoit.
  • Thank you for your advise,your article about master/slave give me a good idea!
    thanks