Skip to content

Commit

Permalink
Allow switchboard client connections.
Browse files Browse the repository at this point in the history
  • Loading branch information
daid committed Oct 16, 2019
1 parent e1bc894 commit 7f9d70e
Show file tree
Hide file tree
Showing 2 changed files with 53 additions and 5 deletions.
10 changes: 9 additions & 1 deletion include/sp2/multiplayer/client.h
Expand Up @@ -6,6 +6,7 @@
#include <sp2/multiplayer/base.h>
#include <sp2/io/dataBuffer.h>
#include <sp2/io/network/tcpSocket.h>
#include <sp2/io/http/websocket.h>


#include <list>
Expand All @@ -29,13 +30,20 @@ class Client : public Updatable, public Base
Client(const string& game_name, uint32_t game_version);
~Client();

void connect(const string& hostname, int port_nr);
// Connect directly to a server with a tcp IP connection.
bool connect(const string& hostname, int port_nr);
// Connect to a server by using a switchboard.
// The hotname and port_nr are the hostname and port of the switchboard server.
// The given key is the game key given to the server that we want to connect to,
// generally entered by the user.
bool connectBySwitchboard(const string& hostname, int port_nr, const string& key);

State getState() const { return state; }

virtual uint32_t getClientId() override;
private:
io::network::TcpSocket socket;
io::http::Websocket websocket;
std::list<io::DataBuffer> send_queue;
State state = State::Disconnected;
uint32_t client_id = 0;
Expand Down
48 changes: 44 additions & 4 deletions src/multiplayer/client.cpp
@@ -1,12 +1,15 @@
#include <sp2/multiplayer/client.h>
#include <sp2/multiplayer/registry.h>
#include <sp2/io/http/request.h>
#include <sp2/logging.h>
#include <sp2/assert.h>
#include <sp2/engine.h>
#include <sp2/scene/scene.h>
#include <sp2/scene/node.h>
#include <private/multiplayer/packetIDs.h>

#include <json11/json11.hpp>

namespace sp {
namespace multiplayer {

Expand All @@ -20,12 +23,48 @@ Client::~Client()
{
}

void Client::connect(const string& hostname, int port_nr)
bool Client::connect(const string& hostname, int port_nr)
{
if (state != State::Disconnected)
return false;

LOG(Info, "Multiplayer client connecting:", hostname, port_nr);
socket.connect(io::network::Address(hostname), port_nr);
if (!socket.connect(io::network::Address(hostname), port_nr))
return false;

state = State::Connecting;
return true;
}

bool Client::connectBySwitchboard(const string& hostname, int port_nr, const string& key)
{
if (state != State::Disconnected)
return false;

// First, request the json game information from the switchboard.
// As we might just be able to do a direct connection.
io::http::Request request(hostname, port_nr);
auto response = request.get("/game/connect/" + key);
if (response.status != 200)
return false;
std::string err;
auto json = json11::Json::parse(response.body, err);
if (!err.empty())
return false;
int server_port = json["port"].int_value();
for(auto json_address : json["address"].array_items())
{
LOG(Info, "Attempting to direct connect to", json_address.string_value(), "address aquired by switchboard");
if (socket.connect(io::network::Address(json_address.string_value()), server_port))
{
state = State::Connecting;
return true;
}
}
LOG(Info, "No suitable address from switchboard archieved. Using switchboard websocket connection");
if (!websocket.connect(hostname, port_nr, "/game/connect/" + key))
return false;
return true;
}

uint32_t Client::getClientId()
Expand All @@ -37,7 +76,7 @@ void Client::onUpdate(float delta)
{
io::DataBuffer packet;

while(socket.receive(packet))
while(socket.receive(packet) || websocket.receive(packet))
{
uint8_t command_id;
packet.read(command_id);
Expand Down Expand Up @@ -142,7 +181,7 @@ void Client::onUpdate(float delta)
}
it->second->multiplayer.prepared_calls.clear();
}
if (!socket.isConnected() && state != State::Disconnected)
if (!socket.isConnected() && !websocket.isConnected() && !websocket.isConnecting() && state != State::Disconnected)
{
LOG(Info, "Multiplayer client disconnect");
state = State::Disconnected;
Expand All @@ -159,6 +198,7 @@ void Client::onUpdate(float delta)
void Client::send(const io::DataBuffer& packet)
{
socket.send(packet);
websocket.send(packet);
}


Expand Down

0 comments on commit 7f9d70e

Please sign in to comment.