Skip to content

Commit

Permalink
Allow websocket to connect by specifying the lose parts of the URL, j…
Browse files Browse the repository at this point in the history
…ust like the http::Request does.
  • Loading branch information
daid committed Oct 16, 2019
1 parent 8b4a040 commit ebaea3a
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 5 deletions.
8 changes: 8 additions & 0 deletions include/sp2/io/http/websocket.h
Expand Up @@ -13,6 +13,13 @@ namespace http {
class Websocket : public sp::NonCopyable
{
public:
enum class Scheme
{
Auto,
Http,
Https
};

Websocket();
Websocket(Websocket&& other);
~Websocket();
Expand All @@ -24,6 +31,7 @@ class Websocket : public sp::NonCopyable
/// Returns true when the initial connection is done. But actual protocol negotiation is still happening.
/// isConnected will become true when negotiation is done.
bool connect(const string& url);
bool connect(const string& hostname, int port, const string& path, Scheme scheme=Scheme::Auto);
void close();

void setHeader(const string& key, const string& value);
Expand Down
25 changes: 22 additions & 3 deletions src/io/http/websocket.cpp
Expand Up @@ -47,6 +47,7 @@ Websocket& Websocket::operator=(Websocket&& other)
socket = std::move(other.socket);
buffer = std::move(other.buffer);
received_fragment = std::move(other.received_fragment);
other.close();
return *this;
}

Expand All @@ -57,13 +58,17 @@ void Websocket::setHeader(const string& key, const string& value)

bool Websocket::connect(const string& url)
{
state = State::Disconnected;
close();

Scheme scheme = Scheme::Http;
int scheme_length = 5;
if (!url.startswith("ws://") && !url.startswith("wss://"))
return false;
if (url.startswith("wss://"))
{
scheme_length = 6;
scheme = Scheme::Https;
}
int end_of_hostname = url.find("/", scheme_length);
string hostname = url.substr(scheme_length, end_of_hostname);
int port = 80;
Expand All @@ -72,7 +77,19 @@ bool Websocket::connect(const string& url)
port = sp::stringutil::convert::toInt(hostname.substr(hostname.find(":") + 1));
hostname = hostname.substr(0, hostname.find(":"));
}
if (url.startswith("wss://"))
string path = url.substr(end_of_hostname);

return connect(hostname, port, path, scheme);
}

bool Websocket::connect(const string& hostname, int port, const string& path, Scheme scheme)
{
close();

if (scheme == Scheme::Auto)
scheme = port == 443 ? Scheme::Https : Scheme::Http;

if (scheme == Scheme::Https)
{
if (!socket.connectSSL(sp::io::network::Address(hostname), port))
return false;
Expand All @@ -82,7 +99,7 @@ bool Websocket::connect(const string& url)
if (!socket.connect(sp::io::network::Address(hostname), port))
return false;
}
string path = url.substr(end_of_hostname);

for(int n=0;n<16;n++)
websock_key += char(sp::irandom(0, 255));
websock_key = sp::stringutil::base64::encode(websock_key);
Expand All @@ -109,6 +126,8 @@ void Websocket::close()
{
socket.close();
state = State::Disconnected;
buffer.clear();
received_fragment.clear();
}

bool Websocket::isConnected()
Expand Down
4 changes: 2 additions & 2 deletions src/multiplayer/server.cpp
Expand Up @@ -71,10 +71,10 @@ bool Server::listenOnSwitchboard(const string& hostname, int port)
switchboard_secret = response_json["secret"].string_value();
if (switchboard_key == "" || switchboard_secret == "")
return false;

switchboard_connection.setHeader("Game-Key", switchboard_key);
switchboard_connection.setHeader("Game-Secret", switchboard_secret);
if (!switchboard_connection.connect("ws://" + hostname + ":" + string(port) + "/game/master"))
if (!switchboard_connection.connect(hostname, port, "/game/master"))
return false;
LOG(Debug, "Registered on switchboard, key:", switchboard_key);
return true;
Expand Down

0 comments on commit ebaea3a

Please sign in to comment.