Account objects are special objects which represent accounts of clients subscribed into the simulation. Each client node has exactly one account object. Client node and account object are tightly coupled together. The account object represents gateway from the client to the simulation. Before new client nodes can connect for the first time to the simulation, their account objects must be created.
Because server nodes can't trust any data from client nodes, there are many restriction on communication between client and server nodes for security purposes (see Section 6.10.2, “Migration From Client To Server Nodes”). One of these restrictions is that any client node can interact with the simulation only through its account object. Thus the entire traffic from clients to servers is under control, which leaves only a small gap how clients can possibly (either willingly or by aaccident) break the simulation.
Each client has its own account object. Once the client gets connected to the simulation, disconnects from the simulation, etc., the Core notifies its account object about the event. This allows to hook specific actions associated with the event. Its up to the account object to do whatever is appropriate.
When a client is connecting to the simulation, the Core initializes network connections among the client and other server nodes only. Once the network connections are established, the Core leaves all other communication on the account object. The account object usually does application specific actions. For example, if the application was some RPG game, the account object would probably wake the client's hero up (which is another managed object) and put him into the simulated world, so that he could fight another horde of monsters.
Client nodes can migrate objects to their account objects only. If the rule is violated the Core disconnects the client from the simulation.
Each node object must be derived from Massiv::Core::AccountObjectInterface abstract class.
class AccountObjectInterface : public Object { public: virtual void client_connected ( const WeakPointer< NodeObjectInterface > & node_object ) = 0; virtual void client_disconnected() = 0; virtual bool check_client_rpc_request ( const Pointer< RPCObject > & request ) const = 0; }; |
The client_connected() method is called by the Core when the client with this account gets connected to the simulation. The Core calls the method using asynchronous RPC. node_object is a pointer to the node object representing the client's node. Account objects usually remember this pointer so that they could communicate with the connected client's node.
The client_disconnected() is called by the Core whenever the client of the account object gets disconnected from the simulation. There are many reasons why the client can be disconnected. For example the client intentionally quit from the simulation or network connection to the client was lost etc. Account objects usually forget the reference to the client's node object (that was remembered when client_connected() had been called) as no more messages can be delivered to the disconnected client.
Note that calls to client_connected() and client_disconnected() don't need to be properly paired. The Core ensures that for one client_connected() there will be at least one call to client_disconnected(), but there may be more calls to the client_disconnected() and so the account objects should count on it.
The check_client_rpc_request() is used to verify RPCObjects received from the client. When delivering a RPC request from the client to an object on a server, the Core checks whether the RPC callee inherits from AccountObjectInterface) and then calls this method which should perform additional, application specific, tests. Their purpose is to check that properites of the RPCObject are valid and that the client is not trying to call a "private" method, etc.
In the Massiv Demo, which is a sample application showing how the Massiv should be used in practice, the account objects serves for many purposes. This section gives you a simple overview how the account objects works in the Demo and how they can be used in real applications.
Player control
In the Demo each client has its own player. The player is an entity which can be moved around the map. Because the client can't communicate with its player directly, the account object receives input from the client and forwards it to the player which is able to react to the client's orders.
Replication
The account objects manage replication of the simulated world to the client. Once the client gets connected to the account object and starts controlling its player entity, the account object starts replicating an area around the player (this inludes surrounding map and nearby entities like sheep). Also the inventory with all items the player has is replicated to the client so it can manipulate with the inventory as well.
Console commands
The account object gives the client ability to execute some commands. The commands are sent by the client to the account object in a textual form. The commands are called console commands because the client's application provides a console, which can be used by the client to enter commands.
The console commands sent by the client are executed either directly by the account object or are forwarded to some node object (the console is "connected to"). The account object is always linked with some node object. If a received command is not recognized by the account object, it forwards the command to the node object the account object is linked with.
Some commands are accessible only for administrators. Whether a client is an administrator is determined by its account object. In the Demo there are two types of account objects: normal and root. The normal account object supports only some of all available commands. The root account object supports all commands.
The account object supports commands which manipulate the client's player entity. For example the client can change name or chat color of the player. Other commands supported by the account object include commands for modifying elevation of the simulated map. These commands can be executed only by root account objects. Administrators can use these commands to modify map of the simulated world (although the Demo provides map editor which can be used to manipulate the map with few mouse clicks so there is no reason why to modify the map via account commands).