Improve socket connection style
Previously, a new socket was being opened and closed on every call. Now, there is one socket per client which is used continuously until the connection closes.
This commit is contained in:
parent
c9a50d363e
commit
0e3b79dc88
@ -72,7 +72,7 @@ std::pair<bool, std::string> echo(std::vector<std::string> args)
|
|||||||
|
|
||||||
std::cout << std::endl;
|
std::cout << std::endl;
|
||||||
|
|
||||||
return {true, "Echo Successful"};
|
return {true, ""};
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char **argv)
|
int main(int argc, char **argv)
|
||||||
@ -101,7 +101,7 @@ int main(int argc, char **argv)
|
|||||||
client.call("echo", {"Hello", "World"});
|
client.call("echo", {"Hello", "World"});
|
||||||
client.call("movePlayer", {"1", "5", "5"});
|
client.call("movePlayer", {"1", "5", "5"});
|
||||||
client.call("movePlayer", {"1", "6", "6"});
|
client.call("movePlayer", {"1", "6", "6"});
|
||||||
auto ret = client.call("echol", {"Goodbye", "World"});
|
auto ret = client.call("echo", {"Goodbye", "World"});
|
||||||
|
|
||||||
std::cout << "Result: " << ret << std::endl;
|
std::cout << "Result: " << ret << std::endl;
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,6 @@
|
|||||||
#include <arpa/inet.h>
|
#include <arpa/inet.h>
|
||||||
#include <stdexcept>
|
#include <stdexcept>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <iostream>
|
|
||||||
|
|
||||||
int msgIdCounter = 0;
|
int msgIdCounter = 0;
|
||||||
|
|
||||||
@ -24,15 +23,7 @@ namespace eRPC
|
|||||||
}
|
}
|
||||||
|
|
||||||
this->serverAddress = serverAddress;
|
this->serverAddress = serverAddress;
|
||||||
}
|
|
||||||
|
|
||||||
Client::~Client()
|
|
||||||
{
|
|
||||||
closeConnection();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Client::openConnection()
|
|
||||||
{
|
|
||||||
if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0)
|
if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0)
|
||||||
{
|
{
|
||||||
throw std::runtime_error("Failed to create socket");
|
throw std::runtime_error("Failed to create socket");
|
||||||
@ -44,16 +35,19 @@ namespace eRPC
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Client::closeConnection()
|
Client::~Client()
|
||||||
{
|
{
|
||||||
|
Request request(msgIdCounter++, "disconnect", {});
|
||||||
|
|
||||||
|
auto serialized = request.serialize();
|
||||||
|
write(sockfd, serialized.c_str(), serialized.size() + 1);
|
||||||
|
|
||||||
close(sockfd);
|
close(sockfd);
|
||||||
sockfd = -1;
|
sockfd = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Client::call(std::string method, std::vector<std::string> params)
|
std::string Client::call(std::string method, std::vector<std::string> params)
|
||||||
{
|
{
|
||||||
Client::openConnection();
|
|
||||||
|
|
||||||
Request request(msgIdCounter++, method, params);
|
Request request(msgIdCounter++, method, params);
|
||||||
auto serialized = request.serialize();
|
auto serialized = request.serialize();
|
||||||
write(sockfd, serialized.c_str(), serialized.size() + 1);
|
write(sockfd, serialized.c_str(), serialized.size() + 1);
|
||||||
@ -61,8 +55,6 @@ namespace eRPC
|
|||||||
char buffer[1024] = {0};
|
char buffer[1024] = {0};
|
||||||
read(sockfd, buffer, 1024);
|
read(sockfd, buffer, 1024);
|
||||||
|
|
||||||
Client::closeConnection();
|
|
||||||
|
|
||||||
Response response(buffer);
|
Response response(buffer);
|
||||||
|
|
||||||
if (!response.isOk())
|
if (!response.isOk())
|
||||||
|
@ -17,9 +17,6 @@ namespace eRPC
|
|||||||
private:
|
private:
|
||||||
int sockfd;
|
int sockfd;
|
||||||
sockaddr_in serverAddress;
|
sockaddr_in serverAddress;
|
||||||
|
|
||||||
void openConnection();
|
|
||||||
void closeConnection();
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -7,6 +7,7 @@
|
|||||||
#include <stdexcept>
|
#include <stdexcept>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
#include <thread>
|
||||||
|
|
||||||
namespace eRPC
|
namespace eRPC
|
||||||
{
|
{
|
||||||
@ -50,11 +51,47 @@ namespace eRPC
|
|||||||
while (running)
|
while (running)
|
||||||
{
|
{
|
||||||
auto connfd = accept(sockfd, (sockaddr *)NULL, NULL);
|
auto connfd = accept(sockfd, (sockaddr *)NULL, NULL);
|
||||||
|
if (connfd < 0)
|
||||||
|
{
|
||||||
|
throw std::runtime_error("Failed to accept connection");
|
||||||
|
}
|
||||||
|
|
||||||
|
// Start a new thread to serve the client
|
||||||
|
std::thread(&Server::serveClient, this, connfd).detach();
|
||||||
|
}
|
||||||
|
|
||||||
|
close(sockfd);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Server::stop()
|
||||||
|
{
|
||||||
|
running = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Server::bindMethod(std::string method, std::function<std::pair<bool, std::string>(std::vector<std::string>)> callback)
|
||||||
|
{
|
||||||
|
methods[method] = callback;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Server::serveClient(int connfd)
|
||||||
|
{
|
||||||
|
while (true)
|
||||||
|
{
|
||||||
char buffer[1024] = {0};
|
char buffer[1024] = {0};
|
||||||
read(connfd, buffer, 1024);
|
if (read(connfd, buffer, 1024) <= 0)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse the request
|
||||||
Request request(buffer);
|
Request request(buffer);
|
||||||
|
|
||||||
|
if (request.getMethod() == "disconnect")
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Call the method if it exists to generate a response
|
||||||
std::unique_ptr<Response> response;
|
std::unique_ptr<Response> response;
|
||||||
if (methods.find(request.getMethod()) != methods.end())
|
if (methods.find(request.getMethod()) != methods.end())
|
||||||
{
|
{
|
||||||
@ -76,20 +113,8 @@ namespace eRPC
|
|||||||
|
|
||||||
auto serialized = response->serialize();
|
auto serialized = response->serialize();
|
||||||
write(connfd, serialized.c_str(), serialized.size() + 1);
|
write(connfd, serialized.c_str(), serialized.size() + 1);
|
||||||
|
|
||||||
close(connfd);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
close(sockfd);
|
close(connfd);
|
||||||
}
|
|
||||||
|
|
||||||
void Server::stop()
|
|
||||||
{
|
|
||||||
running = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Server::bindMethod(std::string method, std::function<std::pair<bool, std::string>(std::vector<std::string>)> callback)
|
|
||||||
{
|
|
||||||
methods[method] = callback;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -21,7 +21,7 @@ namespace eRPC
|
|||||||
~Server();
|
~Server();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Start the server loop.
|
* Start the server loop. This will block until the server is stopped.
|
||||||
*/
|
*/
|
||||||
void start();
|
void start();
|
||||||
|
|
||||||
@ -39,6 +39,11 @@ namespace eRPC
|
|||||||
int sockfd;
|
int sockfd;
|
||||||
bool running;
|
bool running;
|
||||||
std::unordered_map<std::string, std::function<std::pair<bool, std::string>(std::vector<std::string>)>> methods;
|
std::unordered_map<std::string, std::function<std::pair<bool, std::string>(std::vector<std::string>)>> methods;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Keep a socket open and serve a client until they disconnect.
|
||||||
|
*/
|
||||||
|
void serveClient(int connfd);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user