reformat everything with clang-format

This commit is contained in:
Benjamin Sergeant 2019-09-23 10:25:23 -07:00
parent 398c4fbf99
commit cd3c9d879c
92 changed files with 3158 additions and 3348 deletions

View File

@ -10,14 +10,13 @@
namespace ix
{
CancellationRequest makeCancellationRequestWithTimeout(int secs,
std::atomic<bool>& requestInitCancellation)
CancellationRequest makeCancellationRequestWithTimeout(
int secs, std::atomic<bool>& requestInitCancellation)
{
auto start = std::chrono::system_clock::now();
auto timeout = std::chrono::seconds(secs);
auto isCancellationRequested = [&requestInitCancellation, start, timeout]() -> bool
{
auto isCancellationRequested = [&requestInitCancellation, start, timeout]() -> bool {
// Was an explicit cancellation requested ?
if (requestInitCancellation) return true;
@ -30,4 +29,4 @@ namespace ix
return isCancellationRequested;
}
}
} // namespace ix

View File

@ -10,7 +10,8 @@ namespace ix
{
std::atomic<uint64_t> ConnectionState::_globalId(0);
ConnectionState::ConnectionState() : _terminated(false)
ConnectionState::ConnectionState()
: _terminated(false)
{
computeId();
}
@ -39,5 +40,4 @@ namespace ix
{
_terminated = true;
}
}
} // namespace ix

View File

@ -5,22 +5,22 @@
*/
#include "IXDNSLookup.h"
#include "IXNetSystem.h"
#include <string.h>
#include "IXNetSystem.h"
#include <chrono>
#include <string.h>
#include <thread>
namespace ix
{
const int64_t DNSLookup::kDefaultWait = 1; // ms
DNSLookup::DNSLookup(const std::string& hostname, int port, int64_t wait) :
_hostname(hostname),
_port(port),
_wait(wait),
_res(nullptr),
_done(false)
DNSLookup::DNSLookup(const std::string& hostname, int port, int64_t wait)
: _hostname(hostname)
, _port(port)
, _wait(wait)
, _res(nullptr)
, _done(false)
{
;
}
@ -38,8 +38,7 @@ namespace ix
std::string sport = std::to_string(port);
struct addrinfo* res;
int getaddrinfo_result = getaddrinfo(hostname.c_str(), sport.c_str(),
&hints, &res);
int getaddrinfo_result = getaddrinfo(hostname.c_str(), sport.c_str(), &hints, &res);
if (getaddrinfo_result)
{
errMsg = gai_strerror(getaddrinfo_result);
@ -56,8 +55,8 @@ namespace ix
: resolveUnCancellable(errMsg, isCancellationRequested);
}
struct addrinfo* DNSLookup::resolveUnCancellable(std::string& errMsg,
const CancellationRequest& isCancellationRequested)
struct addrinfo* DNSLookup::resolveUnCancellable(
std::string& errMsg, const CancellationRequest& isCancellationRequested)
{
errMsg = "no error";
@ -71,8 +70,8 @@ namespace ix
return getAddrInfo(_hostname, _port, errMsg);
}
struct addrinfo* DNSLookup::resolveCancellable(std::string& errMsg,
const CancellationRequest& isCancellationRequested)
struct addrinfo* DNSLookup::resolveCancellable(
std::string& errMsg, const CancellationRequest& isCancellationRequested)
{
errMsg = "no error";
@ -126,7 +125,9 @@ namespace ix
return getRes();
}
void DNSLookup::run(std::weak_ptr<DNSLookup> self, std::string hostname, int port) // thread runner
void DNSLookup::run(std::weak_ptr<DNSLookup> self,
std::string hostname,
int port) // thread runner
{
// We don't want to read or write into members variables of an object that could be
// gone, so we use temporary variables (res) or we pass in by copy everything that
@ -167,4 +168,4 @@ namespace ix
std::lock_guard<std::mutex> lock(_resMutex);
return _res;
}
}
} // namespace ix

View File

@ -10,8 +10,7 @@
namespace ix
{
uint32_t calculateRetryWaitMilliseconds(
uint32_t retry_count,
uint32_t calculateRetryWaitMilliseconds(uint32_t retry_count,
uint32_t maxWaitBetweenReconnectionRetries)
{
uint32_t wait_time = std::pow(2, retry_count) * 100;
@ -23,4 +22,4 @@ namespace ix
return wait_time;
}
}
} // namespace ix

View File

@ -10,7 +10,6 @@
namespace ix
{
uint32_t calculateRetryWaitMilliseconds(
uint32_t retry_count,
uint32_t calculateRetryWaitMilliseconds(uint32_t retry_count,
uint32_t maxWaitBetweenReconnectionRetries);
} // namespace ix

View File

@ -5,9 +5,9 @@
*/
#include "IXHttp.h"
#include "IXCancellationRequest.h"
#include "IXSocket.h"
#include <sstream>
#include <vector>
@ -57,7 +57,8 @@ namespace ix
return std::make_pair(httpVersion, statusCode);
}
std::tuple<std::string, std::string, std::string> Http::parseRequestLine(const std::string& line)
std::tuple<std::string, std::string, std::string> Http::parseRequestLine(
const std::string& line)
{
// Request-Line = Method SP Request-URI SP HTTP-Version CRLF
std::string token;
@ -161,8 +162,6 @@ namespace ix
return false;
}
return response->payload.empty()
? true
: socket->writeBytes(response->payload, nullptr);
}
return response->payload.empty() ? true : socket->writeBytes(response->payload, nullptr);
}
} // namespace ix

View File

@ -115,8 +115,7 @@ namespace ix
std::shared_ptr<Socket> socket);
static bool sendResponse(HttpResponsePtr response, std::shared_ptr<Socket> socket);
static std::pair<std::string, int> parseStatusLine(
const std::string& line);
static std::pair<std::string, int> parseStatusLine(const std::string& line);
static std::tuple<std::string, std::string, std::string> parseRequestLine(
const std::string& line);
static std::string trim(const std::string& str);

View File

@ -5,17 +5,16 @@
*/
#include "IXHttpClient.h"
#include "IXSocketFactory.h"
#include "IXUrlParser.h"
#include "IXUserAgent.h"
#include "IXWebSocketHttpHeaders.h"
#include "IXSocketFactory.h"
#include <sstream>
#include <iomanip>
#include <vector>
#include <cstring>
#include <assert.h>
#include <cstring>
#include <iomanip>
#include <sstream>
#include <vector>
#include <zlib.h>
namespace ix
@ -26,7 +25,9 @@ namespace ix
const std::string HttpClient::kDel = "DEL";
const std::string HttpClient::kPut = "PUT";
HttpClient::HttpClient(bool async) : _async(async), _stop(false)
HttpClient::HttpClient(bool async)
: _async(async)
, _stop(false)
{
if (!_async) return;
@ -42,8 +43,7 @@ namespace ix
_thread.join();
}
HttpRequestArgsPtr HttpClient::createRequest(const std::string& url,
const std::string& verb)
HttpRequestArgsPtr HttpClient::createRequest(const std::string& url, const std::string& verb)
{
auto request = std::make_shared<HttpRequestArgs>();
request->url = url;
@ -106,8 +106,7 @@ namespace ix
}
}
HttpResponsePtr HttpClient::request(
const std::string& url,
HttpResponsePtr HttpClient::request(const std::string& url,
const std::string& verb,
const std::string& body,
HttpRequestArgsPtr args,
@ -131,9 +130,14 @@ namespace ix
{
std::stringstream ss;
ss << "Cannot parse url: " << url;
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::UrlMalformed,
headers, payload, ss.str(),
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::UrlMalformed,
headers,
payload,
ss.str(),
uploadSize,
downloadSize);
}
bool tls = protocol == "https";
@ -143,9 +147,14 @@ namespace ix
if (!_socket)
{
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::CannotCreateSocket,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::CannotCreateSocket,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
// Build request string
@ -155,7 +164,8 @@ namespace ix
if (args->compress)
{
ss << "Accept-Encoding: gzip" << "\r\n";
ss << "Accept-Encoding: gzip"
<< "\r\n";
}
// Append extra headers
@ -167,7 +177,8 @@ namespace ix
// Set a default Accept header if none is present
if (headers.find("Accept") == headers.end())
{
ss << "Accept: */*" << "\r\n";
ss << "Accept: */*"
<< "\r\n";
}
// Set a default User agent if none is present
@ -183,7 +194,8 @@ namespace ix
// Set default Content-Type if unspecified
if (args->extraHeaders.find("Content-Type") == args->extraHeaders.end())
{
ss << "Content-Type: application/x-www-form-urlencoded" << "\r\n";
ss << "Content-Type: application/x-www-form-urlencoded"
<< "\r\n";
}
ss << "\r\n";
ss << body;
@ -206,9 +218,14 @@ namespace ix
{
std::stringstream ss;
ss << "Cannot connect to url: " << url << " / error : " << errMsg;
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::CannotConnect,
headers, payload, ss.str(),
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::CannotConnect,
headers,
payload,
ss.str(),
uploadSize,
downloadSize);
}
// Make a new cancellation object dealing with transfer timeout
@ -222,8 +239,7 @@ namespace ix
<< "to " << host << ":" << port << std::endl
<< "request size: " << req.size() << " bytes" << std::endl
<< "=============" << std::endl
<< req
<< "=============" << std::endl
<< req << "=============" << std::endl
<< std::endl;
log(ss.str(), args);
@ -232,9 +248,14 @@ namespace ix
if (!_socket->writeBytes(req, isCancellationRequested))
{
std::string errorMsg("Cannot send request");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::SendError,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::SendError,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
uploadSize = req.size();
@ -246,9 +267,14 @@ namespace ix
if (!lineValid)
{
std::string errorMsg("Cannot retrieve status line");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::CannotReadStatusLine,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::CannotReadStatusLine,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
if (args->verbose)
@ -261,9 +287,14 @@ namespace ix
if (sscanf(line.c_str(), "HTTP/1.1 %d", &code) != 1)
{
std::string errorMsg("Cannot parse response code from status line");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::MissingStatus,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::MissingStatus,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
auto result = parseHttpHeaders(_socket, isCancellationRequested);
@ -273,9 +304,14 @@ namespace ix
if (!headersValid)
{
std::string errorMsg("Cannot parse http headers");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::HeaderParsingError,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::HeaderParsingError,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
// Redirect ?
@ -284,18 +320,28 @@ namespace ix
if (headers.find("Location") == headers.end())
{
std::string errorMsg("Missing location header for redirect");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::MissingLocation,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::MissingLocation,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
if (redirects >= args->maxRedirects)
{
std::stringstream ss;
ss << "Too many redirects: " << redirects;
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::TooManyRedirects,
headers, payload, ss.str(),
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::TooManyRedirects,
headers,
payload,
ss.str(),
uploadSize,
downloadSize);
}
// Recurse
@ -305,9 +351,14 @@ namespace ix
if (verb == "HEAD")
{
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::Ok,
headers, payload, std::string(),
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::Ok,
headers,
payload,
std::string(),
uploadSize,
downloadSize);
}
// Parse response:
@ -320,15 +371,19 @@ namespace ix
payload.reserve(contentLength);
auto chunkResult = _socket->readBytes(contentLength,
args->onProgressCallback,
isCancellationRequested);
auto chunkResult = _socket->readBytes(
contentLength, args->onProgressCallback, isCancellationRequested);
if (!chunkResult.first)
{
errorMsg = "Cannot read chunk";
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::ChunkReadError,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::ChunkReadError,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
payload += chunkResult.second;
}
@ -344,9 +399,14 @@ namespace ix
if (!lineResult.first)
{
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::ChunkReadError,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::ChunkReadError,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
uint64_t chunkSize;
@ -357,23 +417,26 @@ namespace ix
if (args->verbose)
{
std::stringstream oss;
oss << "Reading " << chunkSize << " bytes"
<< std::endl;
oss << "Reading " << chunkSize << " bytes" << std::endl;
log(oss.str(), args);
}
payload.reserve(payload.size() + (size_t) chunkSize);
// Read a chunk
auto chunkResult = _socket->readBytes((size_t) chunkSize,
args->onProgressCallback,
isCancellationRequested);
auto chunkResult = _socket->readBytes(
(size_t) chunkSize, args->onProgressCallback, isCancellationRequested);
if (!chunkResult.first)
{
errorMsg = "Cannot read chunk";
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::ChunkReadError,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::ChunkReadError,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
payload += chunkResult.second;
@ -382,9 +445,14 @@ namespace ix
if (!lineResult.first)
{
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::ChunkReadError,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::ChunkReadError,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
if (chunkSize == 0) break;
@ -397,9 +465,14 @@ namespace ix
else
{
std::string errorMsg("Cannot read http body");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::CannotReadBody,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::CannotReadBody,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
downloadSize = payload.size();
@ -411,32 +484,39 @@ namespace ix
if (!gzipInflate(payload, decompressedPayload))
{
std::string errorMsg("Error decompressing payload");
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::Gzip,
headers, payload, errorMsg,
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::Gzip,
headers,
payload,
errorMsg,
uploadSize,
downloadSize);
}
payload = decompressedPayload;
}
return std::make_shared<HttpResponse>(code, description, HttpErrorCode::Ok,
headers, payload, std::string(),
uploadSize, downloadSize);
return std::make_shared<HttpResponse>(code,
description,
HttpErrorCode::Ok,
headers,
payload,
std::string(),
uploadSize,
downloadSize);
}
HttpResponsePtr HttpClient::get(const std::string& url,
HttpRequestArgsPtr args)
HttpResponsePtr HttpClient::get(const std::string& url, HttpRequestArgsPtr args)
{
return request(url, kGet, std::string(), args);
}
HttpResponsePtr HttpClient::head(const std::string& url,
HttpRequestArgsPtr args)
HttpResponsePtr HttpClient::head(const std::string& url, HttpRequestArgsPtr args)
{
return request(url, kHead, std::string(), args);
}
HttpResponsePtr HttpClient::del(const std::string& url,
HttpRequestArgsPtr args)
HttpResponsePtr HttpClient::del(const std::string& url, HttpRequestArgsPtr args)
{
return request(url, kDel, std::string(), args);
}
@ -475,8 +555,7 @@ namespace ix
escaped.fill('0');
escaped << std::hex;
for (std::string::const_iterator i = value.begin(), n = value.end();
i != n; ++i)
for (std::string::const_iterator i = value.begin(), n = value.end(); i != n; ++i)
{
std::string::value_type c = (*i);
@ -504,9 +583,7 @@ namespace ix
for (auto&& it : httpParameters)
{
ss << urlEncode(it.first)
<< "="
<< urlEncode(it.second);
ss << urlEncode(it.first) << "=" << urlEncode(it.second);
if (i++ < (count - 1))
{
@ -516,9 +593,7 @@ namespace ix
return ss.str();
}
bool HttpClient::gzipInflate(
const std::string& in,
std::string& out)
bool HttpClient::gzipInflate(const std::string& in, std::string& out)
{
z_stream inflateState;
std::memset(&inflateState, 0, sizeof(inflateState));
@ -555,22 +630,19 @@ namespace ix
return false;
}
out.append(
reinterpret_cast<char *>(compressBuffer.get()),
kBufferSize - inflateState.avail_out
);
out.append(reinterpret_cast<char*>(compressBuffer.get()),
kBufferSize - inflateState.avail_out);
} while (inflateState.avail_out == 0);
inflateEnd(&inflateState);
return true;
}
void HttpClient::log(const std::string& msg,
HttpRequestArgsPtr args)
void HttpClient::log(const std::string& msg, HttpRequestArgsPtr args)
{
if (args->logger)
{
args->logger(msg);
}
}
}
} // namespace ix

View File

@ -5,13 +5,13 @@
*/
#include "IXHttpServer.h"
#include "IXNetSystem.h"
#include "IXSocketConnect.h"
#include "IXSocketFactory.h"
#include "IXNetSystem.h"
#include <fstream>
#include <iostream>
#include <sstream>
#include <fstream>
#include <vector>
namespace
@ -39,15 +39,13 @@ namespace
auto vec = res.second;
return std::make_pair(res.first, std::string(vec.begin(), vec.end()));
}
}
} // namespace
namespace ix
{
HttpServer::HttpServer(int port,
const std::string& host,
int backlog,
size_t maxConnections) : SocketServer(port, host, backlog, maxConnections),
_connectedClientsCount(0)
HttpServer::HttpServer(int port, const std::string& host, int backlog, size_t maxConnections)
: SocketServer(port, host, backlog, maxConnections)
, _connectedClientsCount(0)
{
setDefaultConnectionCallback();
}
@ -71,9 +69,7 @@ namespace ix
_onConnectionCallback = callback;
}
void HttpServer::handleConnection(
int fd,
std::shared_ptr<ConnectionState> connectionState)
void HttpServer::handleConnection(int fd, std::shared_ptr<ConnectionState> connectionState)
{
_connectedClientsCount++;
@ -109,8 +105,7 @@ namespace ix
{
setOnConnectionCallback(
[this](HttpRequestPtr request,
std::shared_ptr<ConnectionState> /*connectionState*/) -> HttpResponsePtr
{
std::shared_ptr<ConnectionState> /*connectionState*/) -> HttpResponsePtr {
std::string uri(request->uri);
if (uri.empty() || uri == "/")
{
@ -122,23 +117,16 @@ namespace ix
bool found = res.first;
if (!found)
{
return std::make_shared<HttpResponse>(404, "Not Found",
HttpErrorCode::Ok,
WebSocketHttpHeaders(),
std::string());
return std::make_shared<HttpResponse>(
404, "Not Found", HttpErrorCode::Ok, WebSocketHttpHeaders(), std::string());
}
std::string content = res.second;
// Log request
std::stringstream ss;
ss << request->method
<< " "
<< request->headers["User-Agent"]
<< " "
<< request->uri
<< " "
<< content.size();
ss << request->method << " " << request->headers["User-Agent"] << " "
<< request->uri << " " << content.size();
logInfo(ss.str());
WebSocketHttpHeaders headers;
@ -151,11 +139,8 @@ namespace ix
headers[it.first] = it.second;
}
return std::make_shared<HttpResponse>(200, "OK",
HttpErrorCode::Ok,
headers,
content);
}
);
}
return std::make_shared<HttpResponse>(
200, "OK", HttpErrorCode::Ok, headers, content);
});
}
} // namespace ix

View File

@ -77,8 +77,7 @@ namespace ix
tv.tv_sec = timeout / 1000;
tv.tv_usec = (timeout % 1000) * 1000;
int ret = select(maxfd + 1, &readfds, &writefds, &errorfds,
timeout != -1 ? &tv : NULL);
int ret = select(maxfd + 1, &readfds, &writefds, &errorfds, timeout != -1 ? &tv : NULL);
if (ret < 0)
{

View File

@ -42,5 +42,4 @@ namespace ix
{
return -1;
}
}
} // namespace ix

View File

@ -26,14 +26,13 @@
#include "IXSelectInterruptEventFd.h"
#include <sys/eventfd.h>
#include <unistd.h> // for write
#include <string.h> // for strerror
#include <fcntl.h>
#include <errno.h>
#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <sstream>
#include <string.h> // for strerror
#include <sys/eventfd.h>
#include <unistd.h> // for write
namespace ix
{
@ -113,4 +112,4 @@ namespace ix
{
return _eventfd;
}
}
} // namespace ix

View File

@ -22,4 +22,4 @@ namespace ix
return std::make_shared<SelectInterrupt>();
#endif
}
}
} // namespace ix

View File

@ -10,12 +10,12 @@
#include "IXSelectInterruptPipe.h"
#include <unistd.h> // for write
#include <string.h> // for strerror
#include <fcntl.h>
#include <errno.h>
#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <sstream>
#include <string.h> // for strerror
#include <unistd.h> // for write
namespace ix
{
@ -143,4 +143,4 @@ namespace ix
return _fildes[kPipeReadIndex];
}
}
} // namespace ix

View File

@ -5,21 +5,20 @@
*/
#include "IXSocket.h"
#include "IXSocketConnect.h"
#include "IXNetSystem.h"
#include "IXSelectInterrupt.h"
#include "IXSelectInterruptFactory.h"
#include "IXSocketConnect.h"
#include <algorithm>
#include <assert.h>
#include <fcntl.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <stdint.h>
#include <fcntl.h>
#include <sys/types.h>
#include <algorithm>
#ifdef min
#undef min
#endif
@ -32,9 +31,9 @@ namespace ix
const uint64_t Socket::kCloseRequest = 2;
constexpr size_t Socket::kChunkSize;
Socket::Socket(int fd) :
_sockfd(fd),
_selectInterrupt(createSelectInterrupt())
Socket::Socket(int fd)
: _sockfd(fd)
, _selectInterrupt(createSelectInterrupt())
{
;
}
@ -123,8 +122,7 @@ namespace ix
// getsockopt() puts the errno value for connect into optval so 0
// means no-error.
if (getsockopt(sockfd, SOL_SOCKET, SO_ERROR, &optval, &optlen) == -1 ||
optval != 0)
if (getsockopt(sockfd, SOL_SOCKET, SO_ERROR, &optval, &optlen) == -1 || optval != 0)
{
pollResult = PollResultType::Error;
@ -292,8 +290,7 @@ namespace ix
}
}
bool Socket::readByte(void* buffer,
const CancellationRequest& isCancellationRequested)
bool Socket::readByte(void* buffer, const CancellationRequest& isCancellationRequested)
{
while (true)
{
@ -369,9 +366,7 @@ namespace ix
if (ret > 0)
{
output.insert(output.end(),
_readBuffer.begin(),
_readBuffer.begin() + ret);
output.insert(output.end(), _readBuffer.begin(), _readBuffer.begin() + ret);
}
else if (ret <= 0 && !Socket::isWaitNeeded())
{
@ -388,7 +383,6 @@ namespace ix
}
}
return std::make_pair(true, std::string(output.begin(),
output.end()));
}
return std::make_pair(true, std::string(output.begin(), output.end()));
}
} // namespace ix

View File

@ -6,11 +6,13 @@
* Adapted from Satori SDK Apple SSL code.
*/
#include "IXSocketAppleSSL.h"
#include "IXSocketConnect.h"
#include "IXSocketConnect.h"
#include <errno.h>
#include <fcntl.h>
#include <netdb.h>
#include <netinet/tcp.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@ -18,20 +20,16 @@
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdint.h>
#include <errno.h>
#define socketerrno errno
#include <Security/SecureTransport.h>
namespace {
namespace
{
OSStatus read_from_socket(SSLConnectionRef connection, void* data, size_t* len)
{
int fd = (int) (long) connection;
if (fd < 0)
return errSSLInternal;
if (fd < 0) return errSSLInternal;
assert(data != nullptr);
assert(len != nullptr);
@ -56,18 +54,15 @@ OSStatus read_from_socket(SSLConnectionRef connection, void *data, size_t *len)
else
{
*len = 0;
switch (errno) {
case ENOENT:
return errSSLClosedGraceful;
switch (errno)
{
case ENOENT: return errSSLClosedGraceful;
case EAGAIN:
return errSSLWouldBlock;
case EAGAIN: return errSSLWouldBlock;
case ECONNRESET:
return errSSLClosedAbort;
case ECONNRESET: return errSSLClosedAbort;
default:
return errSecIO;
default: return errSecIO;
}
}
}
@ -75,8 +70,7 @@ OSStatus read_from_socket(SSLConnectionRef connection, void *data, size_t *len)
OSStatus write_to_socket(SSLConnectionRef connection, const void* data, size_t* len)
{
int fd = (int) (long) connection;
if (fd < 0)
return errSSLInternal;
if (fd < 0) return errSSLInternal;
assert(data != nullptr);
assert(len != nullptr);
@ -123,8 +117,8 @@ std::string getSSLErrorDescription(OSStatus status)
{
char localBuffer[128];
Boolean success;
success = CFStringGetCString(message, localBuffer, 128,
CFStringGetSystemEncoding());
success =
CFStringGetCString(message, localBuffer, 128, CFStringGetSystemEncoding());
if (success)
{
errMsg = localBuffer;
@ -141,9 +135,10 @@ std::string getSSLErrorDescription(OSStatus status)
namespace ix
{
SocketAppleSSL::SocketAppleSSL(const SocketTLSOptions& tlsOptions, int fd) : Socket(fd),
_sslContext(nullptr),
_tlsOptions(tlsOptions)
SocketAppleSSL::SocketAppleSSL(const SocketTLSOptions& tlsOptions, int fd)
: Socket(fd)
, _sslContext(nullptr)
, _tlsOptions(tlsOptions)
{
;
}
@ -173,10 +168,10 @@ namespace ix
SSLSetProtocolVersionMin(_sslContext, kTLSProtocol12);
SSLSetPeerDomainName(_sslContext, host.c_str(), host.size());
do {
do
{
status = SSLHandshake(_sslContext);
} while (errSSLWouldBlock == status ||
errSSLServerAuthCompleted == status);
} while (errSSLWouldBlock == status || errSSLServerAuthCompleted == status);
}
if (noErr != status)
@ -206,7 +201,8 @@ namespace ix
{
ssize_t ret = 0;
OSStatus status;
do {
do
{
size_t processed = 0;
std::lock_guard<std::mutex> lock(_mutex);
status = SSLWrite(_sslContext, buf, nbyte, &processed);
@ -215,8 +211,7 @@ namespace ix
nbyte -= processed;
} while (nbyte > 0 && errSSLWouldBlock == status);
if (ret == 0 && errSSLClosedAbort != status)
ret = -1;
if (ret == 0 && errSSLClosedAbort != status) ret = -1;
return ret;
}
@ -235,13 +230,11 @@ namespace ix
std::lock_guard<std::mutex> lock(_mutex);
status = SSLRead(_sslContext, buf, nbyte, &processed);
if (processed > 0)
return (ssize_t) processed;
if (processed > 0) return (ssize_t) processed;
// The connection was reset, inform the caller that this
// Socket should close
if (status == errSSLClosedGraceful ||
status == errSSLClosedNoNotify ||
if (status == errSSLClosedGraceful || status == errSSLClosedNoNotify ||
status == errSSLClosedAbort)
{
errno = ECONNRESET;
@ -257,4 +250,4 @@ namespace ix
return -1;
}
}
} // namespace ix

View File

@ -5,12 +5,12 @@
*/
#include "IXSocketConnect.h"
#include "IXDNSLookup.h"
#include "IXNetSystem.h"
#include "IXSocket.h"
#include <string.h>
#include <fcntl.h>
#include <string.h>
#include <sys/types.h>
// Android needs extra headers for TCP_NODELAY and IPPROTO_TCP
@ -23,8 +23,8 @@ namespace ix
{
//
// This function can be cancelled every 50 ms
// This is important so that we don't block the main UI thread when shutting down a connection which is
// already trying to reconnect, and can be blocked waiting for ::connect to respond.
// This is important so that we don't block the main UI thread when shutting down a connection
// which is already trying to reconnect, and can be blocked waiting for ::connect to respond.
//
int SocketConnect::connectToAddress(const struct addrinfo* address,
std::string& errMsg,
@ -32,9 +32,7 @@ namespace ix
{
errMsg = "no error";
int fd = socket(address->ai_family,
address->ai_socktype,
address->ai_protocol);
int fd = socket(address->ai_family, address->ai_socktype, address->ai_protocol);
if (fd < 0)
{
errMsg = "Cannot create a socket";
@ -74,8 +72,7 @@ namespace ix
else if (pollResult == PollResultType::Error)
{
Socket::closeSocket(fd);
errMsg = std::string("Connect error: ") +
strerror(Socket::getErrno());
errMsg = std::string("Connect error: ") + strerror(Socket::getErrno());
return -1;
}
else if (pollResult == PollResultType::ReadyForWrite)
@ -85,8 +82,7 @@ namespace ix
else
{
Socket::closeSocket(fd);
errMsg = std::string("Connect error: ") +
strerror(Socket::getErrno());
errMsg = std::string("Connect error: ") + strerror(Socket::getErrno());
return -1;
}
}
@ -149,8 +145,7 @@ namespace ix
// 3. (apple) prevent SIGPIPE from being emitted when the remote end disconnect
#ifdef SO_NOSIGPIPE
int value = 1;
setsockopt(sockfd, SOL_SOCKET, SO_NOSIGPIPE,
(void *)&value, sizeof(value));
setsockopt(sockfd, SOL_SOCKET, SO_NOSIGPIPE, (void*) &value, sizeof(value));
#endif
}
}
} // namespace ix

View File

@ -7,15 +7,16 @@
#pragma once
#include "IXSocketTLSOptions.h"
#include <memory>
#include <string>
#include "IXSocketTLSOptions.h"
namespace ix
{
class Socket;
std::shared_ptr<Socket> createSocket(bool tls, std::string& errorMsg, const SocketTLSOptions& tlsOptions);
std::shared_ptr<Socket> createSocket(bool tls,
std::string& errorMsg,
const SocketTLSOptions& tlsOptions);
std::shared_ptr<Socket> createSocket(int fd, std::string& errorMsg);
} // namespace ix

View File

@ -9,16 +9,16 @@
*/
#include "IXSocketMbedTLS.h"
#include "IXSocketConnect.h"
#include "IXNetSystem.h"
#include "IXSocket.h"
#include "IXSocketConnect.h"
#include <string.h>
namespace ix
{
SocketMbedTLS::SocketMbedTLS(const SocketTLSOptions& tlsOptions) :
_tlsOptions(tlsOptions)
SocketMbedTLS::SocketMbedTLS(const SocketTLSOptions& tlsOptions)
: _tlsOptions(tlsOptions)
{
;
}
@ -102,8 +102,7 @@ namespace ix
{
std::lock_guard<std::mutex> lock(_mutex);
res = mbedtls_ssl_handshake(&_ssl);
}
while (res == MBEDTLS_ERR_SSL_WANT_READ || res == MBEDTLS_ERR_SSL_WANT_WRITE);
} while (res == MBEDTLS_ERR_SSL_WANT_READ || res == MBEDTLS_ERR_SSL_WANT_WRITE);
if (res != 0)
{
@ -142,13 +141,18 @@ namespace ix
ssize_t res = mbedtls_ssl_write(&_ssl, (unsigned char*) buf, nbyte);
if (res > 0) {
if (res > 0)
{
nbyte -= res;
sent += res;
} else if (res == MBEDTLS_ERR_SSL_WANT_READ || res == MBEDTLS_ERR_SSL_WANT_WRITE) {
}
else if (res == MBEDTLS_ERR_SSL_WANT_READ || res == MBEDTLS_ERR_SSL_WANT_WRITE)
{
errno = EWOULDBLOCK;
return -1;
} else {
}
else
{
return -1;
}
}
@ -181,4 +185,4 @@ namespace ix
}
}
}
} // namespace ix

View File

@ -121,7 +121,9 @@ namespace ix
});
SSL_CTX_set_verify_depth(ctx, 4);
} else {
}
else
{
SSL_CTX_set_verify(ctx, SSL_VERIFY_NONE, nullptr);
}

View File

@ -13,12 +13,12 @@
#include "IXSocketSChannel.h"
#ifdef _WIN32
# include <basetsd.h>
# include <WinSock2.h>
# include <ws2def.h>
#include <WS2tcpip.h>
# include <schannel.h>
#include <WinSock2.h>
#include <basetsd.h>
#include <io.h>
#include <schannel.h>
#include <ws2def.h>
#define WIN32_LEAN_AND_MEAN
@ -26,14 +26,15 @@
#define UNICODE
#endif
#include <windows.h>
#include <winsock2.h>
#include <mstcpip.h>
#include <ws2tcpip.h>
#include <rpc.h>
#include <ntdsapi.h>
#include <rpc.h>
#include <stdio.h>
#include <tchar.h>
#include <winsock2.h>
#include <ws2tcpip.h>
#include <windows.h>
#define RECV_DATA_BUF_SIZE 256
@ -50,10 +51,6 @@
// has already been initialized
#else
#error("This file should only be built on Windows")
#endif
@ -67,12 +64,9 @@ namespace ix
SocketSChannel::~SocketSChannel()
{
}
bool SocketSChannel::connect(const std::string& host,
int port,
std::string& errMsg)
bool SocketSChannel::connect(const std::string& host, int port, std::string& errMsg)
{
return Socket::connect(host, port, errMsg, nullptr);
}
@ -103,4 +97,4 @@ namespace ix
return Socket::recv(buf, nbyte);
}
}
} // namespace ix

View File

@ -5,14 +5,14 @@
*/
#include "IXSocketServer.h"
#include "IXNetSystem.h"
#include "IXSocket.h"
#include "IXSocketConnect.h"
#include "IXNetSystem.h"
#include <assert.h>
#include <iostream>
#include <sstream>
#include <string.h>
#include <assert.h>
namespace ix
{
@ -24,17 +24,16 @@ namespace ix
SocketServer::SocketServer(int port,
const std::string& host,
int backlog,
size_t maxConnections) :
_port(port),
_host(host),
_backlog(backlog),
_maxConnections(maxConnections),
_serverFd(-1),
_stop(false),
_stopGc(false),
_connectionStateFactory(&ConnectionState::createConnectionState)
size_t maxConnections)
: _port(port)
, _host(host)
, _backlog(backlog)
, _maxConnections(maxConnections)
, _serverFd(-1)
, _stop(false)
, _stopGc(false)
, _connectionStateFactory(&ConnectionState::createConnectionState)
{
}
SocketServer::~SocketServer()
@ -62,21 +61,18 @@ namespace ix
if ((_serverFd = socket(AF_INET, SOCK_STREAM, 0)) < 0)
{
std::stringstream ss;
ss << "SocketServer::listen() error creating socket): "
<< strerror(Socket::getErrno());
ss << "SocketServer::listen() error creating socket): " << strerror(Socket::getErrno());
return std::make_pair(false, ss.str());
}
// Make that socket reusable. (allow restarting this server at will)
int enable = 1;
if (setsockopt(_serverFd, SOL_SOCKET, SO_REUSEADDR,
(char*) &enable, sizeof(enable)) < 0)
if (setsockopt(_serverFd, SOL_SOCKET, SO_REUSEADDR, (char*) &enable, sizeof(enable)) < 0)
{
std::stringstream ss;
ss << "SocketServer::listen() error calling setsockopt(SO_REUSEADDR) "
<< "at address " << _host << ":" << _port
<< " : " << strerror(Socket::getErrno());
<< "at address " << _host << ":" << _port << " : " << strerror(Socket::getErrno());
Socket::closeSocket(_serverFd);
return std::make_pair(false, ss.str());
@ -99,8 +95,7 @@ namespace ix
{
std::stringstream ss;
ss << "SocketServer::listen() error calling bind "
<< "at address " << _host << ":" << _port
<< " : " << strerror(Socket::getErrno());
<< "at address " << _host << ":" << _port << " : " << strerror(Socket::getErrno());
Socket::closeSocket(_serverFd);
return std::make_pair(false, ss.str());
@ -113,8 +108,7 @@ namespace ix
{
std::stringstream ss;
ss << "SocketServer::listen() error calling listen "
<< "at address " << _host << ":" << _port
<< " : " << strerror(Socket::getErrno());
<< "at address " << _host << ":" << _port << " : " << strerror(Socket::getErrno());
Socket::closeSocket(_serverFd);
return std::make_pair(false, ss.str());
@ -221,8 +215,7 @@ namespace ix
if (pollResult == PollResultType::Error)
{
std::stringstream ss;
ss << "SocketServer::run() error in select: "
<< strerror(Socket::getErrno());
ss << "SocketServer::run() error in select: " << strerror(Socket::getErrno());
logError(ss.str());
continue;
}
@ -245,8 +238,8 @@ namespace ix
// FIXME: that error should be propagated
int err = Socket::getErrno();
std::stringstream ss;
ss << "SocketServer::run() error accepting connection: "
<< err << ", " << strerror(err);
ss << "SocketServer::run() error accepting connection: " << err << ", "
<< strerror(err);
logError(ss.str());
}
continue;
@ -255,8 +248,7 @@ namespace ix
if (getConnectedClientsCount() >= _maxConnections)
{
std::stringstream ss;
ss << "SocketServer::run() reached max connections = "
<< _maxConnections << ". "
ss << "SocketServer::run() reached max connections = " << _maxConnections << ". "
<< "Not accepting connection";
logError(ss.str());
@ -277,10 +269,7 @@ namespace ix
std::lock_guard<std::mutex> lock(_connectionsThreadsMutex);
_connectionsThreads.push_back(std::make_pair(
connectionState,
std::thread(&SocketServer::handleConnection,
this,
clientFd,
connectionState)));
std::thread(&SocketServer::handleConnection, this, clientFd, connectionState)));
}
}
@ -308,5 +297,4 @@ namespace ix
std::this_thread::sleep_for(std::chrono::milliseconds(10));
}
}
}
} // namespace ix

View File

@ -4,13 +4,14 @@
* Copyright (c) 2017-2018 Machine Zone, Inc. All rights reserved.
*/
#include <assert.h>
#include "IXSocketTLSOptions.h"
#include <assert.h>
namespace ix
{
SocketTLSOptions::SocketTLSOptions() {
SocketTLSOptions::SocketTLSOptions()
{
#ifndef IXWEBSOCKET_USE_TLS
assert(false && "To use TLS features the library must be compiled with USE_TLS");
#endif

View File

@ -5,6 +5,7 @@
*/
#include "IXUrlParser.h"
#include "LUrlParser.h"
namespace ix
@ -64,4 +65,4 @@ namespace ix
return true;
}
}
} // namespace ix

View File

@ -5,8 +5,8 @@
*/
#include "IXUserAgent.h"
#include "IXWebSocketVersion.h"
#include "IXWebSocketVersion.h"
#include <sstream>
#include <zlib.h>
@ -80,4 +80,4 @@ namespace ix
return ss.str();
}
}
} // namespace ix

View File

@ -48,20 +48,31 @@ namespace ix
/// Lookup table for the UTF8 decode state machine
static uint8_t const utf8d[] = {
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, // 00..1f
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, // 20..3f
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, // 40..5f
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, // 60..7f
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,9,9,9,9,9,9,9,9,9,9,9,9,9,9,9,9, // 80..9f
7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, // a0..bf
8,8,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2, // c0..df
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 00..1f
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 20..3f
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 40..5f
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 60..7f
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, // 80..9f
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, // a0..bf
8, 8, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // c0..df
0xa, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x3, 0x3, // e0..ef
0xb, 0x6, 0x6, 0x6, 0x5, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, // f0..ff
0x0, 0x1, 0x2, 0x3, 0x5, 0x8, 0x7, 0x1, 0x1, 0x1, 0x4, 0x6, 0x1, 0x1, 0x1, 0x1, // s0..s0
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,1,1,1,1,1,0,1,0,1,1,1,1,1,1, // s1..s2
1,2,1,1,1,1,1,2,1,2,1,1,1,1,1,1,1,1,1,1,1,1,1,2,1,1,1,1,1,1,1,1, // s3..s4
1,2,1,1,1,1,1,1,1,2,1,1,1,1,1,1,1,1,1,1,1,1,1,3,1,3,1,1,1,1,1,1, // s5..s6
1,3,1,1,1,1,1,3,1,3,1,1,1,1,1,1,1,3,1,1,1,1,1,1,1,1,1,1,1,1,1,1, // s7..s8
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1, 1, // s1..s2
1, 2, 1, 1, 1, 1, 1, 2, 1, 2, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, // s3..s4
1, 2, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 3, 1, 3, 1, 1, 1, 1, 1, 1, // s5..s6
1, 3, 1, 1, 1, 1, 1, 3, 1, 3, 1, 1, 1, 1, 1, 1,
1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // s7..s8
};
/// Decode the next byte of a UTF8 sequence
@ -75,9 +86,7 @@ namespace ix
{
uint32_t type = utf8d[byte];
*codep = (*state != utf8_accept) ?
(byte & 0x3fu) | (*codep << 6) :
(0xff >> type) & (byte);
*codep = (*state != utf8_accept) ? (byte & 0x3fu) | (*codep << 6) : (0xff >> type) & (byte);
*state = utf8d[256 + *state * 16 + type];
return *state;
@ -88,7 +97,11 @@ namespace ix
{
public:
/// Construct and initialize the validator
Utf8Validator() : m_state(utf8_accept),m_codepoint(0) {}
Utf8Validator()
: m_state(utf8_accept)
, m_codepoint(0)
{
}
/// Advance the state of the validator with the next input byte
/**
@ -115,11 +128,8 @@ namespace ix
{
for (iterator_type it = begin; it != end; ++it)
{
unsigned int result = decodeNextByte(
&m_state,
&m_codepoint,
static_cast<uint8_t>(*it)
);
unsigned int result =
decodeNextByte(&m_state, &m_codepoint, static_cast<uint8_t>(*it));
if (result == utf8_reject)
{
@ -144,6 +154,7 @@ namespace ix
m_state = utf8_accept;
m_codepoint = 0;
}
private:
uint32_t m_state;
uint32_t m_codepoint;

View File

@ -5,13 +5,13 @@
*/
#include "IXWebSocket.h"
#include "IXSetThreadName.h"
#include "IXWebSocketHandshake.h"
#include "IXExponentialBackoff.h"
#include "IXUtf8Validator.h"
#include <cmath>
#include "IXExponentialBackoff.h"
#include "IXSetThreadName.h"
#include "IXUtf8Validator.h"
#include "IXWebSocketHandshake.h"
#include <cassert>
#include <cmath>
namespace ix
@ -23,26 +23,26 @@ namespace ix
const bool WebSocket::kDefaultEnablePong(true);
const uint32_t WebSocket::kDefaultMaxWaitBetweenReconnectionRetries(10 * 1000); // 10s
WebSocket::WebSocket() :
_onMessageCallback(OnMessageCallback()),
_stop(false),
_automaticReconnection(true),
_maxWaitBetweenReconnectionRetries(kDefaultMaxWaitBetweenReconnectionRetries),
_handshakeTimeoutSecs(kDefaultHandShakeTimeoutSecs),
_enablePong(kDefaultEnablePong),
_pingIntervalSecs(kDefaultPingIntervalSecs),
_pingTimeoutSecs(kDefaultPingTimeoutSecs)
WebSocket::WebSocket()
: _onMessageCallback(OnMessageCallback())
, _stop(false)
, _automaticReconnection(true)
, _maxWaitBetweenReconnectionRetries(kDefaultMaxWaitBetweenReconnectionRetries)
, _handshakeTimeoutSecs(kDefaultHandShakeTimeoutSecs)
, _enablePong(kDefaultEnablePong)
, _pingIntervalSecs(kDefaultPingIntervalSecs)
, _pingTimeoutSecs(kDefaultPingTimeoutSecs)
{
_ws.setOnCloseCallback(
[this](uint16_t code, const std::string& reason, size_t wireSize, bool remote)
{
[this](uint16_t code, const std::string& reason, size_t wireSize, bool remote) {
_onMessageCallback(
std::make_shared<WebSocketMessage>(
WebSocketMessageType::Close, "", wireSize,
WebSocketErrorInfo(), WebSocketOpenInfo(),
std::make_shared<WebSocketMessage>(WebSocketMessageType::Close,
"",
wireSize,
WebSocketErrorInfo(),
WebSocketOpenInfo(),
WebSocketCloseInfo(code, reason, remote)));
}
);
});
}
WebSocket::~WebSocket()
@ -67,7 +67,8 @@ namespace ix
return _url;
}
void WebSocket::setPerMessageDeflateOptions(const WebSocketPerMessageDeflateOptions& perMessageDeflateOptions)
void WebSocket::setPerMessageDeflateOptions(
const WebSocketPerMessageDeflateOptions& perMessageDeflateOptions)
{
std::lock_guard<std::mutex> lock(_configMutex);
_perMessageDeflateOptions = perMessageDeflateOptions;
@ -159,8 +160,7 @@ namespace ix
_thread = std::thread(&WebSocket::run, this);
}
void WebSocket::stop(uint16_t code,
const std::string& reason)
void WebSocket::stop(uint16_t code, const std::string& reason)
{
close(code, reason);
@ -192,8 +192,9 @@ namespace ix
}
_onMessageCallback(
std::make_shared<WebSocketMessage>(
WebSocketMessageType::Open, "", 0,
std::make_shared<WebSocketMessage>(WebSocketMessageType::Open,
"",
0,
WebSocketErrorInfo(),
WebSocketOpenInfo(status.uri, status.headers),
WebSocketCloseInfo()));
@ -218,8 +219,9 @@ namespace ix
}
_onMessageCallback(
std::make_shared<WebSocketMessage>(
WebSocketMessageType::Open, "", 0,
std::make_shared<WebSocketMessage>(WebSocketMessageType::Open,
"",
0,
WebSocketErrorInfo(),
WebSocketOpenInfo(status.uri, status.headers),
WebSocketCloseInfo()));
@ -236,8 +238,7 @@ namespace ix
return getReadyState() == ReadyState::Closing;
}
void WebSocket::close(uint16_t code,
const std::string& reason)
void WebSocket::close(uint16_t code, const std::string& reason)
{
_ws.close(code, reason);
}
@ -281,7 +282,8 @@ namespace ix
if (_automaticReconnection)
{
duration = millis(calculateRetryWaitMilliseconds(retries++, _maxWaitBetweenReconnectionRetries));
duration = millis(calculateRetryWaitMilliseconds(
retries++, _maxWaitBetweenReconnectionRetries));
connectErr.wait_time = duration.count();
connectErr.retries = retries;
@ -290,10 +292,11 @@ namespace ix
connectErr.reason = status.errorStr;
connectErr.http_status = status.http_status;
_onMessageCallback(
std::make_shared<WebSocketMessage>(
WebSocketMessageType::Error, "", 0,
connectErr, WebSocketOpenInfo(),
_onMessageCallback(std::make_shared<WebSocketMessage>(WebSocketMessageType::Error,
"",
0,
connectErr,
WebSocketOpenInfo(),
WebSocketCloseInfo()));
}
}
@ -330,8 +333,7 @@ namespace ix
[this](const std::string& msg,
size_t wireSize,
bool decompressionError,
WebSocketTransport::MessageKind messageKind)
{
WebSocketTransport::MessageKind messageKind) {
WebSocketMessageType webSocketMessageType;
switch (messageKind)
{
@ -339,22 +341,26 @@ namespace ix
case WebSocketTransport::MessageKind::MSG_BINARY:
{
webSocketMessageType = WebSocketMessageType::Message;
} break;
}
break;
case WebSocketTransport::MessageKind::PING:
{
webSocketMessageType = WebSocketMessageType::Ping;
} break;
}
break;
case WebSocketTransport::MessageKind::PONG:
{
webSocketMessageType = WebSocketMessageType::Pong;
} break;
}
break;
case WebSocketTransport::MessageKind::FRAGMENT:
{
webSocketMessageType = WebSocketMessageType::Fragment;
} break;
}
break;
}
WebSocketErrorInfo webSocketErrorInfo;
@ -362,11 +368,13 @@ namespace ix
bool binary = messageKind == WebSocketTransport::MessageKind::MSG_BINARY;
_onMessageCallback(
std::make_shared<WebSocketMessage>(
webSocketMessageType, msg, wireSize,
webSocketErrorInfo, WebSocketOpenInfo(),
WebSocketCloseInfo(), binary));
_onMessageCallback(std::make_shared<WebSocketMessage>(webSocketMessageType,
msg,
wireSize,
webSocketErrorInfo,
WebSocketOpenInfo(),
WebSocketCloseInfo(),
binary));
WebSocket::invokeTrafficTrackerCallback(msg.size(), true);
});
@ -453,17 +461,20 @@ namespace ix
case SendMessageKind::Text:
{
webSocketSendInfo = _ws.sendText(text, onProgressCallback);
} break;
}
break;
case SendMessageKind::Binary:
{
webSocketSendInfo = _ws.sendBinary(text, onProgressCallback);
} break;
}
break;
case SendMessageKind::Ping:
{
webSocketSendInfo = _ws.sendPing(text);
} break;
}
break;
}
WebSocket::invokeTrafficTrackerCallback(webSocketSendInfo.wireSize, false);
@ -514,4 +525,4 @@ namespace ix
{
return _ws.bufferedAmount();
}
}
} // namespace ix

View File

@ -22,10 +22,15 @@ namespace ix
const std::string WebSocketCloseConstants::kProtocolErrorMessage("Protocol error");
const std::string WebSocketCloseConstants::kNoStatusCodeErrorMessage("No status code");
const std::string WebSocketCloseConstants::kProtocolErrorReservedBitUsed("Reserved bit used");
const std::string WebSocketCloseConstants::kProtocolErrorPingPayloadOversized("Ping reason control frame with payload length > 125 octets");
const std::string WebSocketCloseConstants::kProtocolErrorCodeControlMessageFragmented("Control message fragmented");
const std::string WebSocketCloseConstants::kProtocolErrorCodeDataOpcodeOutOfSequence("Fragmentation: data message out of sequence");
const std::string WebSocketCloseConstants::kProtocolErrorCodeContinuationOpCodeOutOfSequence("Fragmentation: continuation opcode out of sequence");
const std::string WebSocketCloseConstants::kInvalidFramePayloadDataMessage("Invalid frame payload data");
const std::string WebSocketCloseConstants::kProtocolErrorPingPayloadOversized(
"Ping reason control frame with payload length > 125 octets");
const std::string WebSocketCloseConstants::kProtocolErrorCodeControlMessageFragmented(
"Control message fragmented");
const std::string WebSocketCloseConstants::kProtocolErrorCodeDataOpcodeOutOfSequence(
"Fragmentation: data message out of sequence");
const std::string WebSocketCloseConstants::kProtocolErrorCodeContinuationOpCodeOutOfSequence(
"Fragmentation: continuation opcode out of sequence");
const std::string WebSocketCloseConstants::kInvalidFramePayloadDataMessage(
"Invalid frame payload data");
const std::string WebSocketCloseConstants::kInvalidCloseCodeMessage("Invalid close code");
}
} // namespace ix

View File

@ -5,48 +5,43 @@
*/
#include "IXWebSocketHandshake.h"
#include "IXHttp.h"
#include "IXSocketConnect.h"
#include "IXUrlParser.h"
#include "IXHttp.h"
#include "IXUserAgent.h"
#include "libwshandshake.hpp"
#include <sstream>
#include <random>
#include <algorithm>
#include <random>
#include <sstream>
namespace ix
{
WebSocketHandshake::WebSocketHandshake(std::atomic<bool>& requestInitCancellation,
WebSocketHandshake::WebSocketHandshake(
std::atomic<bool>& requestInitCancellation,
std::shared_ptr<Socket> socket,
WebSocketPerMessageDeflate& perMessageDeflate,
WebSocketPerMessageDeflateOptions& perMessageDeflateOptions,
std::atomic<bool>& enablePerMessageDeflate) :
_requestInitCancellation(requestInitCancellation),
_socket(socket),
_perMessageDeflate(perMessageDeflate),
_perMessageDeflateOptions(perMessageDeflateOptions),
_enablePerMessageDeflate(enablePerMessageDeflate)
std::atomic<bool>& enablePerMessageDeflate)
: _requestInitCancellation(requestInitCancellation)
, _socket(socket)
, _perMessageDeflate(perMessageDeflate)
, _perMessageDeflateOptions(perMessageDeflateOptions)
, _enablePerMessageDeflate(enablePerMessageDeflate)
{
}
bool WebSocketHandshake::insensitiveStringCompare(const std::string& a, const std::string& b)
{
return std::equal(a.begin(), a.end(),
b.begin(), b.end(),
[](char a, char b)
{
return std::equal(a.begin(), a.end(), b.begin(), b.end(), [](char a, char b) {
return tolower(a) == tolower(b);
});
}
std::string WebSocketHandshake::genRandomString(const int len)
{
std::string alphanum =
"0123456789"
std::string alphanum = "0123456789"
"ABCDEFGH"
"abcdefgh";
@ -88,7 +83,8 @@ namespace ix
return WebSocketInitResult(false, code, reason);
}
WebSocketInitResult WebSocketHandshake::clientHandshake(const std::string& url,
WebSocketInitResult WebSocketHandshake::clientHandshake(
const std::string& url,
const WebSocketHttpHeaders& extraHeaders,
const std::string& host,
const std::string& path,
@ -105,9 +101,7 @@ namespace ix
if (!success)
{
std::stringstream ss;
ss << "Unable to connect to " << host
<< " on port " << port
<< ", error: " << errMsg;
ss << "Unable to connect to " << host << " on port " << port << ", error: " << errMsg;
return WebSocketInitResult(false, 0, ss.str());
}
@ -149,7 +143,8 @@ namespace ix
if (!_socket->writeBytes(ss.str(), isCancellationRequested))
{
return WebSocketInitResult(false, 0, std::string("Failed sending GET request to ") + url);
return WebSocketInitResult(
false, 0, std::string("Failed sending GET request to ") + url);
}
// Read HTTP status line
@ -159,8 +154,8 @@ namespace ix
if (!lineValid)
{
return WebSocketInitResult(false, 0,
std::string("Failed reading HTTP status line from ") + url);
return WebSocketInitResult(
false, 0, std::string("Failed reading HTTP status line from ") + url);
}
// Validate status
@ -173,8 +168,7 @@ namespace ix
{
std::stringstream ss;
ss << "Expecting HTTP/1.1, got " << httpVersion << ". "
<< "Rejecting connection to " << host << ":" << port
<< ", status: " << status
<< "Rejecting connection to " << host << ":" << port << ", status: " << status
<< ", HTTP Status line: " << line;
return WebSocketInitResult(false, status, ss.str());
}
@ -183,8 +177,7 @@ namespace ix
if (status != 101)
{
std::stringstream ss;
ss << "Got bad status connecting to " << host << ":" << port
<< ", status: " << status
ss << "Got bad status connecting to " << host << ":" << port << ", status: " << status
<< ", HTTP Status line: " << line;
return WebSocketInitResult(false, status, ss.str());
}
@ -280,7 +273,8 @@ namespace ix
if (httpVersion != "HTTP/1.1")
{
return sendErrorResponse(400, "Invalid HTTP version, need HTTP/1.1, got: " + httpVersion);
return sendErrorResponse(400,
"Invalid HTTP version, need HTTP/1.1, got: " + httpVersion);
}
// Retrieve and validate HTTP headers
@ -305,8 +299,10 @@ namespace ix
if (!insensitiveStringCompare(headers["upgrade"], "WebSocket"))
{
return sendErrorResponse(400, "Invalid Upgrade header, "
"need WebSocket, got " + headers["upgrade"]);
return sendErrorResponse(400,
"Invalid Upgrade header, "
"need WebSocket, got " +
headers["upgrade"]);
}
if (headers.find("sec-websocket-version") == headers.end())
@ -322,8 +318,10 @@ namespace ix
if (version != 13)
{
return sendErrorResponse(400, "Invalid Sec-WebSocket-Version, "
"need 13, got " + ss.str());
return sendErrorResponse(400,
"Invalid Sec-WebSocket-Version, "
"need 13, got " +
ss.str());
}
}
@ -358,9 +356,10 @@ namespace ix
if (!_socket->writeBytes(ss.str(), isCancellationRequested))
{
return WebSocketInitResult(false, 0, std::string("Failed sending response to ") + remote);
return WebSocketInitResult(
false, 0, std::string("Failed sending response to ") + remote);
}
return WebSocketInitResult(true, 200, "", headers, uri);
}
}
} // namespace ix

View File

@ -49,8 +49,7 @@ namespace ix
WebSocketPerMessageDeflateOptions& perMessageDeflateOptions,
std::atomic<bool>& enablePerMessageDeflate);
WebSocketInitResult clientHandshake(
const std::string& url,
WebSocketInitResult clientHandshake(const std::string& url,
const WebSocketHttpHeaders& extraHeaders,
const std::string& host,
const std::string& path,

View File

@ -5,13 +5,15 @@
*/
#include "IXWebSocketHttpHeaders.h"
#include "IXSocket.h"
#include <algorithm>
#include <locale>
namespace ix
{
bool CaseInsensitiveLess::NocaseCompare::operator()(const unsigned char & c1, const unsigned char & c2) const
bool CaseInsensitiveLess::NocaseCompare::operator()(const unsigned char& c1,
const unsigned char& c2) const
{
#ifdef _WIN32
return std::tolower(c1, std::locale()) < std::tolower(c2, std::locale());
@ -22,15 +24,15 @@ namespace ix
bool CaseInsensitiveLess::operator()(const std::string& s1, const std::string& s2) const
{
return std::lexicographical_compare
(s1.begin(), s1.end(), // source range
s2.begin(), s2.end(), // dest range
return std::lexicographical_compare(s1.begin(),
s1.end(), // source range
s2.begin(),
s2.end(), // dest range
NocaseCompare()); // comparison
}
std::pair<bool, WebSocketHttpHeaders> parseHttpHeaders(
std::shared_ptr<Socket> socket,
const CancellationRequest& isCancellationRequested)
std::shared_ptr<Socket> socket, const CancellationRequest& isCancellationRequested)
{
WebSocketHttpHeaders headers;
@ -41,9 +43,7 @@ namespace ix
{
int colon = 0;
for (i = 0;
i < 2 || (i < 1023 && line[i-2] != '\r' && line[i-1] != '\n');
++i)
for (i = 0; i < 2 || (i < 1023 && line[i - 2] != '\r' && line[i - 1] != '\n'); ++i)
{
if (!socket->readByte(line + i, isCancellationRequested))
{
@ -79,4 +79,4 @@ namespace ix
return std::make_pair(true, headers);
}
}
} // namespace ix

View File

@ -8,7 +8,6 @@
namespace ix
{
WebSocketMessageQueue::WebSocketMessageQueue(WebSocket* websocket)
{
bindWebsocket(websocket);
@ -40,8 +39,7 @@ namespace ix
// bind new
if (_websocket)
{
_websocket->setOnMessageCallback([this](const WebSocketMessagePtr& msg)
{
_websocket->setOnMessageCallback([this](const WebSocketMessagePtr& msg) {
std::lock_guard<std::mutex> lock(_messagesMutex);
_messages.emplace_back(std::move(msg));
});
@ -74,8 +72,7 @@ namespace ix
void WebSocketMessageQueue::poll(int count)
{
if (!_onMessageUserCallback)
return;
if (!_onMessageUserCallback) return;
WebSocketMessagePtr message;
@ -86,4 +83,4 @@ namespace ix
}
}
}
} // namespace ix

View File

@ -41,19 +41,21 @@
* - Added more documentation.
*
* Per message Deflate RFC: https://tools.ietf.org/html/rfc7692
* Chrome websocket -> https://github.com/chromium/chromium/tree/2ca8c5037021c9d2ecc00b787d58a31ed8fc8bcb/net/websockets
* Chrome websocket ->
* https://github.com/chromium/chromium/tree/2ca8c5037021c9d2ecc00b787d58a31ed8fc8bcb/net/websockets
*
*/
#include "IXWebSocketPerMessageDeflate.h"
#include "IXWebSocketPerMessageDeflateOptions.h"
#include "IXWebSocketPerMessageDeflateCodec.h"
#include "IXWebSocketPerMessageDeflateOptions.h"
namespace ix
{
WebSocketPerMessageDeflate::WebSocketPerMessageDeflate() :
_compressor(std::make_unique<WebSocketPerMessageDeflateCompressor>()),
_decompressor(std::make_unique<WebSocketPerMessageDeflateDecompressor>())
WebSocketPerMessageDeflate::WebSocketPerMessageDeflate()
: _compressor(std::make_unique<WebSocketPerMessageDeflateCompressor>())
, _decompressor(std::make_unique<WebSocketPerMessageDeflateDecompressor>())
{
;
}
@ -63,10 +65,10 @@ namespace ix
;
}
bool WebSocketPerMessageDeflate::init(const WebSocketPerMessageDeflateOptions& perMessageDeflateOptions)
bool WebSocketPerMessageDeflate::init(
const WebSocketPerMessageDeflateOptions& perMessageDeflateOptions)
{
bool clientNoContextTakeover =
perMessageDeflateOptions.getClientNoContextTakeover();
bool clientNoContextTakeover = perMessageDeflateOptions.getClientNoContextTakeover();
uint8_t deflateBits = perMessageDeflateOptions.getClientMaxWindowBits();
uint8_t inflateBits = perMessageDeflateOptions.getServerMaxWindowBits();
@ -75,16 +77,14 @@ namespace ix
_decompressor->init(inflateBits, clientNoContextTakeover);
}
bool WebSocketPerMessageDeflate::compress(const std::string& in,
std::string& out)
bool WebSocketPerMessageDeflate::compress(const std::string& in, std::string& out)
{
return _compressor->compress(in, out);
}
bool WebSocketPerMessageDeflate::decompress(const std::string& in,
std::string &out)
bool WebSocketPerMessageDeflate::decompress(const std::string& in, std::string& out)
{
return _decompressor->decompress(in, out);
}
}
} // namespace ix

View File

@ -5,8 +5,8 @@
*/
#include "IXWebSocketPerMessageDeflateCodec.h"
#include "IXWebSocketPerMessageDeflateOptions.h"
#include "IXWebSocketPerMessageDeflateOptions.h"
#include <cassert>
#include <string.h>
@ -18,7 +18,7 @@ namespace
const std::string kEmptyUncompressedBlock = std::string("\x00\x00\xff\xff", 4);
const int kBufferSize = 1 << 14;
}
} // namespace
namespace ix
{
@ -43,22 +43,18 @@ namespace ix
bool WebSocketPerMessageDeflateCompressor::init(uint8_t deflateBits,
bool clientNoContextTakeOver)
{
int ret = deflateInit2(
&_deflateState,
int ret = deflateInit2(&_deflateState,
Z_DEFAULT_COMPRESSION,
Z_DEFLATED,
-1 * deflateBits,
4, // memory level 1-9
Z_DEFAULT_STRATEGY
);
Z_DEFAULT_STRATEGY);
if (ret != Z_OK) return false;
_compressBuffer = std::make_unique<unsigned char[]>(_compressBufferSize);
_flush = (clientNoContextTakeOver)
? Z_FULL_FLUSH
: Z_SYNC_FLUSH;
_flush = (clientNoContextTakeOver) ? Z_FULL_FLUSH : Z_SYNC_FLUSH;
return true;
}
@ -70,8 +66,7 @@ namespace ix
return std::equal(ending.rbegin(), ending.rend(), value.rbegin());
}
bool WebSocketPerMessageDeflateCompressor::compress(const std::string& in,
std::string& out)
bool WebSocketPerMessageDeflateCompressor::compress(const std::string& in, std::string& out)
{
//
// 7.2.1. Compression
@ -146,24 +141,18 @@ namespace ix
bool WebSocketPerMessageDeflateDecompressor::init(uint8_t inflateBits,
bool clientNoContextTakeOver)
{
int ret = inflateInit2(
&_inflateState,
-1*inflateBits
);
int ret = inflateInit2(&_inflateState, -1 * inflateBits);
if (ret != Z_OK) return false;
_compressBuffer = std::make_unique<unsigned char[]>(_compressBufferSize);
_flush = (clientNoContextTakeOver)
? Z_FULL_FLUSH
: Z_SYNC_FLUSH;
_flush = (clientNoContextTakeOver) ? Z_FULL_FLUSH : Z_SYNC_FLUSH;
return true;
}
bool WebSocketPerMessageDeflateDecompressor::decompress(const std::string& in,
std::string& out)
bool WebSocketPerMessageDeflateDecompressor::decompress(const std::string& in, std::string& out)
{
//
// 7.2.2. Decompression
@ -193,13 +182,10 @@ namespace ix
return false; // zlib error
}
out.append(
reinterpret_cast<char *>(_compressBuffer.get()),
_compressBufferSize - _inflateState.avail_out
);
out.append(reinterpret_cast<char*>(_compressBuffer.get()),
_compressBufferSize - _inflateState.avail_out);
} while (_inflateState.avail_out == 0);
return true;
}
}
} // namespace ix

View File

@ -6,9 +6,9 @@
#include "IXWebSocketPerMessageDeflateOptions.h"
#include <sstream>
#include <algorithm>
#include <cctype>
#include <sstream>
namespace ix
{
@ -48,7 +48,8 @@ namespace ix
//
// Server response could look like that:
//
// Sec-WebSocket-Extensions: permessage-deflate; client_no_context_takeover; server_no_context_takeover
// Sec-WebSocket-Extensions: permessage-deflate; client_no_context_takeover;
// server_no_context_takeover
//
WebSocketPerMessageDeflateOptions::WebSocketPerMessageDeflateOptions(std::string extension)
{
@ -92,8 +93,7 @@ namespace ix
// Sanitize values to be in the proper range [8, 15] in
// case a server would give us bogus values
_serverMaxWindowBits =
std::min(maxServerMaxWindowBits,
std::max(x, minServerMaxWindowBits));
std::min(maxServerMaxWindowBits, std::max(x, minServerMaxWindowBits));
}
if (startsWith(token, "client_max_window_bits="))
@ -107,8 +107,7 @@ namespace ix
// Sanitize values to be in the proper range [8, 15] in
// case a server would give us bogus values
_clientMaxWindowBits =
std::min(maxClientMaxWindowBits,
std::max(x, minClientMaxWindowBits));
std::min(maxClientMaxWindowBits, std::max(x, minClientMaxWindowBits));
sanitizeClientMaxWindowBits();
}
@ -175,11 +174,10 @@ namespace ix
std::string WebSocketPerMessageDeflateOptions::removeSpaces(const std::string& str)
{
std::string out(str);
out.erase(std::remove_if(out.begin(),
out.end(),
[](unsigned char x){ return std::isspace(x); }),
out.erase(
std::remove_if(out.begin(), out.end(), [](unsigned char x) { return std::isspace(x); }),
out.end());
return out;
}
}
} // namespace ix

View File

@ -5,13 +5,13 @@
*/
#include "IXWebSocketServer.h"
#include "IXWebSocketTransport.h"
#include "IXWebSocket.h"
#include "IXSocketConnect.h"
#include "IXNetSystem.h"
#include <sstream>
#include "IXNetSystem.h"
#include "IXSocketConnect.h"
#include "IXWebSocket.h"
#include "IXWebSocketTransport.h"
#include <future>
#include <sstream>
#include <string.h>
namespace ix
@ -23,11 +23,11 @@ namespace ix
const std::string& host,
int backlog,
size_t maxConnections,
int handshakeTimeoutSecs) : SocketServer(port, host, backlog, maxConnections),
_handshakeTimeoutSecs(handshakeTimeoutSecs),
_enablePong(kDefaultEnablePong)
int handshakeTimeoutSecs)
: SocketServer(port, host, backlog, maxConnections)
, _handshakeTimeoutSecs(handshakeTimeoutSecs)
, _enablePong(kDefaultEnablePong)
{
}
WebSocketServer::~WebSocketServer()
@ -63,9 +63,7 @@ namespace ix
_onConnectionCallback = callback;
}
void WebSocketServer::handleConnection(
int fd,
std::shared_ptr<ConnectionState> connectionState)
void WebSocketServer::handleConnection(int fd, std::shared_ptr<ConnectionState> connectionState)
{
auto webSocket = std::make_shared<WebSocket>();
_onConnectionCallback(webSocket, connectionState);
@ -93,10 +91,8 @@ namespace ix
else
{
std::stringstream ss;
ss << "WebSocketServer::handleConnection() HTTP status: "
<< status.http_status
<< " error: "
<< status.errorStr;
ss << "WebSocketServer::handleConnection() HTTP status: " << status.http_status
<< " error: " << status.errorStr;
logError(ss.str());
}
@ -126,4 +122,4 @@ namespace ix
std::lock_guard<std::mutex> lock(_clientsMutex);
return _clients.size();
}
}
} // namespace ix

View File

@ -32,24 +32,23 @@
// Adapted from https://github.com/dhbaird/easywsclient
//
#include "IXSocketTLSOptions.h"
#include "IXWebSocketTransport.h"
#include "IXSocketFactory.h"
#include "IXSocketTLSOptions.h"
#include "IXUrlParser.h"
#include "IXUtf8Validator.h"
#include "IXWebSocketHandshake.h"
#include "IXWebSocketHttpHeaders.h"
#include "IXUrlParser.h"
#include "IXSocketFactory.h"
#include "IXUtf8Validator.h"
#include <string.h>
#include <stdlib.h>
#include <cstdlib>
#include <vector>
#include <string>
#include <cstdarg>
#include <sstream>
#include <chrono>
#include <cstdarg>
#include <cstdlib>
#include <sstream>
#include <stdlib.h>
#include <string.h>
#include <string>
#include <thread>
#include <vector>
namespace
@ -65,7 +64,7 @@ namespace
return a;
}
}
} // namespace
namespace ix
{
@ -76,24 +75,24 @@ namespace ix
const int WebSocketTransport::kClosingMaximumWaitingDelayInMs(300);
constexpr size_t WebSocketTransport::kChunkSize;
WebSocketTransport::WebSocketTransport() :
_useMask(true),
_compressedMessage(false),
_readyState(ReadyState::CLOSED),
_closeCode(WebSocketCloseConstants::kInternalErrorCode),
_closeReason(WebSocketCloseConstants::kInternalErrorMessage),
_closeWireSize(0),
_closeRemote(false),
_enablePerMessageDeflate(false),
_requestInitCancellation(false),
_closingTimePoint(std::chrono::steady_clock::now()),
_enablePong(kDefaultEnablePong),
_pingIntervalSecs(kDefaultPingIntervalSecs),
_pingTimeoutSecs(kDefaultPingTimeoutSecs),
_pingIntervalOrTimeoutGCDSecs(-1),
_nextGCDTimePoint(std::chrono::steady_clock::now()),
_lastSendPingTimePoint(std::chrono::steady_clock::now()),
_lastReceivePongTimePoint(std::chrono::steady_clock::now())
WebSocketTransport::WebSocketTransport()
: _useMask(true)
, _compressedMessage(false)
, _readyState(ReadyState::CLOSED)
, _closeCode(WebSocketCloseConstants::kInternalErrorCode)
, _closeReason(WebSocketCloseConstants::kInternalErrorMessage)
, _closeWireSize(0)
, _closeRemote(false)
, _enablePerMessageDeflate(false)
, _requestInitCancellation(false)
, _closingTimePoint(std::chrono::steady_clock::now())
, _enablePong(kDefaultEnablePong)
, _pingIntervalSecs(kDefaultPingIntervalSecs)
, _pingTimeoutSecs(kDefaultPingTimeoutSecs)
, _pingIntervalOrTimeoutGCDSecs(-1)
, _nextGCDTimePoint(std::chrono::steady_clock::now())
, _lastSendPingTimePoint(std::chrono::steady_clock::now())
, _lastReceivePongTimePoint(std::chrono::steady_clock::now())
{
_readbuf.resize(kChunkSize);
}
@ -103,7 +102,8 @@ namespace ix
;
}
void WebSocketTransport::configure(const WebSocketPerMessageDeflateOptions& perMessageDeflateOptions,
void WebSocketTransport::configure(
const WebSocketPerMessageDeflateOptions& perMessageDeflateOptions,
const SocketTLSOptions& socketTLSOptions,
bool enablePong,
int pingIntervalSecs,
@ -118,8 +118,8 @@ namespace ix
if (pingIntervalSecs > 0 && pingTimeoutSecs > 0)
{
_pingIntervalOrTimeoutGCDSecs = greatestCommonDivisor(pingIntervalSecs,
pingTimeoutSecs);
_pingIntervalOrTimeoutGCDSecs =
greatestCommonDivisor(pingIntervalSecs, pingTimeoutSecs);
}
else if (_pingTimeoutSecs > 0)
{
@ -132,8 +132,7 @@ namespace ix
}
// Client
WebSocketInitResult WebSocketTransport::connectToUrl(
const std::string& url,
WebSocketInitResult WebSocketTransport::connectToUrl(const std::string& url,
const WebSocketHttpHeaders& headers,
int timeoutSecs)
{
@ -144,8 +143,7 @@ namespace ix
if (!UrlParser::parse(url, protocol, host, path, query, port))
{
return WebSocketInitResult(false, 0,
std::string("Could not parse URL ") + url);
return WebSocketInitResult(false, 0, std::string("Could not parse URL ") + url);
}
std::string errorMsg;
@ -163,8 +161,8 @@ namespace ix
_perMessageDeflateOptions,
_enablePerMessageDeflate);
auto result = webSocketHandshake.clientHandshake(url, headers, host, path,
port, timeoutSecs);
auto result =
webSocketHandshake.clientHandshake(url, headers, host, path, port, timeoutSecs);
if (result.success)
{
setReadyState(ReadyState::OPEN);
@ -247,15 +245,15 @@ namespace ix
if (_pingIntervalOrTimeoutGCDSecs > 0)
{
_nextGCDTimePoint = std::chrono::steady_clock::now() + std::chrono::seconds(_pingIntervalOrTimeoutGCDSecs);
_nextGCDTimePoint = std::chrono::steady_clock::now() +
std::chrono::seconds(_pingIntervalOrTimeoutGCDSecs);
}
}
// Only consider send PING time points for that computation.
bool WebSocketTransport::pingIntervalExceeded()
{
if (_pingIntervalSecs <= 0)
return false;
if (_pingIntervalSecs <= 0) return false;
std::lock_guard<std::mutex> lock(_lastSendPingTimePointMutex);
auto now = std::chrono::steady_clock::now();
@ -264,8 +262,7 @@ namespace ix
bool WebSocketTransport::pingTimeoutExceeded()
{
if (_pingTimeoutSecs <= 0)
return false;
if (_pingTimeoutSecs <= 0) return false;
std::lock_guard<std::mutex> lock(_lastReceivePongTimePointMutex);
auto now = std::chrono::steady_clock::now();
@ -302,7 +299,8 @@ namespace ix
// No timeout if state is not OPEN, otherwise computed
// pingIntervalOrTimeoutGCD (equals to -1 if no ping and no ping timeout are set)
int lastingTimeoutDelayInMs = (_readyState != ReadyState::OPEN) ? 0 : _pingIntervalOrTimeoutGCDSecs;
int lastingTimeoutDelayInMs =
(_readyState != ReadyState::OPEN) ? 0 : _pingIntervalOrTimeoutGCDSecs;
if (_pingIntervalOrTimeoutGCDSecs > 0)
{
@ -317,7 +315,10 @@ namespace ix
}
else
{
lastingTimeoutDelayInMs = (int)std::chrono::duration_cast<std::chrono::milliseconds>(_nextGCDTimePoint - now).count();
lastingTimeoutDelayInMs =
(int) std::chrono::duration_cast<std::chrono::milliseconds>(_nextGCDTimePoint -
now)
.count();
}
}
@ -373,8 +374,9 @@ namespace ix
}
else if (ret <= 0)
{
// if there are received data pending to be processed, then delay the abnormal closure
// to after dispatch (other close code/reason could be read from the buffer)
// if there are received data pending to be processed, then delay the abnormal
// closure to after dispatch (other close code/reason could be read from the
// buffer)
closeSocket();
@ -382,9 +384,7 @@ namespace ix
}
else
{
_rxbuf.insert(_rxbuf.end(),
_readbuf.begin(),
_readbuf.begin() + ret);
_rxbuf.insert(_rxbuf.end(), _readbuf.begin(), _readbuf.begin() + ret);
}
}
}
@ -482,7 +482,8 @@ namespace ix
ws.opcode = (wsheader_type::opcode_type)(data[0] & 0x0f);
ws.mask = (data[1] & 0x80) == 0x80;
ws.N0 = (data[1] & 0x7f);
ws.header_size = 2 + (ws.N0 == 126? 2 : 0) + (ws.N0 == 127? 8 : 0) + (ws.mask? 4 : 0);
ws.header_size =
2 + (ws.N0 == 126 ? 2 : 0) + (ws.N0 == 127 ? 8 : 0) + (ws.mask ? 4 : 0);
if (_rxbuf.size() < ws.header_size) break; /* Need: ws.header_size - _rxbuf.size() */
if ((ws.rsv1 && !_enablePerMessageDeflate) || ws.rsv2 || ws.rsv3)
@ -551,11 +552,9 @@ namespace ix
return; /* Need: ws.header_size+ws.N - _rxbuf.size() */
}
if (!ws.fin && (
ws.opcode == wsheader_type::PING
|| ws.opcode == wsheader_type::PONG
|| ws.opcode == wsheader_type::CLOSE
)){
if (!ws.fin && (ws.opcode == wsheader_type::PING || ws.opcode == wsheader_type::PONG ||
ws.opcode == wsheader_type::CLOSE))
{
// Control messages should not be fragmented
close(WebSocketCloseConstants::kProtocolErrorCode,
WebSocketCloseConstants::kProtocolErrorCodeControlMessageFragmented);
@ -567,16 +566,13 @@ namespace ix
_rxbuf.begin() + ws.header_size + (size_t) ws.N);
// We got a whole message, now do something with it:
if (
ws.opcode == wsheader_type::TEXT_FRAME
|| ws.opcode == wsheader_type::BINARY_FRAME
|| ws.opcode == wsheader_type::CONTINUATION
) {
if (ws.opcode == wsheader_type::TEXT_FRAME ||
ws.opcode == wsheader_type::BINARY_FRAME ||
ws.opcode == wsheader_type::CONTINUATION)
{
if (ws.opcode != wsheader_type::CONTINUATION)
{
_fragmentedMessageKind =
(ws.opcode == wsheader_type::TEXT_FRAME)
_fragmentedMessageKind = (ws.opcode == wsheader_type::TEXT_FRAME)
? MessageKind::MSG_TEXT
: MessageKind::MSG_BINARY;
@ -592,7 +588,8 @@ namespace ix
else if (_chunks.empty())
{
// Continuation message need to follow a non-fin TEXT or BINARY message
close(WebSocketCloseConstants::kProtocolErrorCode,
close(
WebSocketCloseConstants::kProtocolErrorCode,
WebSocketCloseConstants::kProtocolErrorCodeContinuationOpCodeOutOfSequence);
}
@ -601,10 +598,8 @@ namespace ix
//
if (ws.fin && _chunks.empty())
{
emitMessage(_fragmentedMessageKind,
frameData,
_compressedMessage,
onMessageCallback);
emitMessage(
_fragmentedMessageKind, frameData, _compressedMessage, onMessageCallback);
_compressedMessage = false;
}
@ -621,8 +616,10 @@ namespace ix
if (ws.fin)
{
emitMessage(_fragmentedMessageKind, getMergedChunks(),
_compressedMessage, onMessageCallback);
emitMessage(_fragmentedMessageKind,
getMergedChunks(),
_compressedMessage,
onMessageCallback);
_chunks.clear();
_compressedMessage = false;
@ -690,13 +687,11 @@ namespace ix
// Full list of status code and status range is defined in the dedicated
// RFC section at https://tools.ietf.org/html/rfc6455#page-45
//
if (code < 1000 || code == 1004 || code == 1006 ||
(code > 1013 && code < 3000))
if (code < 1000 || code == 1004 || code == 1006 || (code > 1013 && code < 3000))
{
// build up an error message containing the bad error code
std::stringstream ss;
ss << WebSocketCloseConstants::kInvalidCloseCodeMessage
<< ": " << code;
ss << WebSocketCloseConstants::kInvalidCloseCodeMessage << ": " << code;
reason = ss.str();
code = WebSocketCloseConstants::kProtocolErrorCode;
@ -722,8 +717,8 @@ namespace ix
}
else
{
// we got the CLOSE frame answer from our close, so we can close the connection if
// the code/reason are the same
// we got the CLOSE frame answer from our close, so we can close the connection
// if the code/reason are the same
bool identicalReason;
{
std::lock_guard<std::mutex> lock(_closeDataMutex);
@ -746,8 +741,7 @@ namespace ix
}
// Erase the message that has been processed from the input/read buffer
_rxbuf.erase(_rxbuf.begin(),
_rxbuf.begin() + ws.header_size + (size_t) ws.N);
_rxbuf.erase(_rxbuf.begin(), _rxbuf.begin() + ws.header_size + (size_t) ws.N);
}
// if an abnormal closure was raised in poll, and nothing else triggered a CLOSED state in
@ -756,7 +750,8 @@ namespace ix
{
_rxbuf.clear();
// if we previously closed the connection (CLOSING state), then set state to CLOSED (code/reason were set before)
// if we previously closed the connection (CLOSING state), then set state to CLOSED
// (code/reason were set before)
if (_readyState == ReadyState::CLOSING)
{
closeSocket();
@ -767,7 +762,8 @@ namespace ix
{
closeSocketAndSwitchToClosedState(WebSocketCloseConstants::kAbnormalCloseCode,
WebSocketCloseConstants::kAbnormalCloseMessage,
0, false);
0,
false);
}
}
}
@ -832,13 +828,11 @@ namespace ix
{
auto now = std::chrono::system_clock::now();
auto seconds =
std::chrono::duration_cast<std::chrono::seconds>(
now.time_since_epoch()).count();
std::chrono::duration_cast<std::chrono::seconds>(now.time_since_epoch()).count();
return static_cast<unsigned>(seconds);
}
WebSocketSendInfo WebSocketTransport::sendData(
wsheader_type::opcode_type type,
WebSocketSendInfo WebSocketTransport::sendData(wsheader_type::opcode_type type,
const std::string& message,
bool compress,
const OnProgressCallback& onProgressCallback)
@ -950,10 +944,9 @@ namespace ix
masking_key[3] = (x) &0xff;
std::vector<uint8_t> header;
header.assign(2 +
(message_size >= 126 ? 2 : 0) +
(message_size >= 65536 ? 6 : 0) +
(_useMask ? 4 : 0), 0);
header.assign(2 + (message_size >= 126 ? 2 : 0) + (message_size >= 65536 ? 6 : 0) +
(_useMask ? 4 : 0),
0);
header[0] = type;
// The fin bit indicate that this is the last fragment. Fin is French for end.
@ -1017,8 +1010,7 @@ namespace ix
}
// _txbuf will keep growing until it can be transmitted over the socket:
appendToSendBuffer(header, message_begin, message_end,
message_size, masking_key);
appendToSendBuffer(header, message_begin, message_end, message_size, masking_key);
// Now actually send this data
sendOnSocket();
@ -1038,22 +1030,20 @@ namespace ix
return info;
}
WebSocketSendInfo WebSocketTransport::sendBinary(
const std::string& message,
WebSocketSendInfo WebSocketTransport::sendBinary(const std::string& message,
const OnProgressCallback& onProgressCallback)
{
return sendData(wsheader_type::BINARY_FRAME, message,
_enablePerMessageDeflate, onProgressCallback);
return sendData(
wsheader_type::BINARY_FRAME, message, _enablePerMessageDeflate, onProgressCallback);
}
WebSocketSendInfo WebSocketTransport::sendText(
const std::string& message,
WebSocketSendInfo WebSocketTransport::sendText(const std::string& message,
const OnProgressCallback& onProgressCallback)
{
return sendData(wsheader_type::TEXT_FRAME, message,
_enablePerMessageDeflate, onProgressCallback);
return sendData(
wsheader_type::TEXT_FRAME, message, _enablePerMessageDeflate, onProgressCallback);
}
ssize_t WebSocketTransport::send()
@ -1116,8 +1106,10 @@ namespace ix
_socket->close();
}
void WebSocketTransport::closeSocketAndSwitchToClosedState(
uint16_t code, const std::string& reason, size_t closeWireSize, bool remote)
void WebSocketTransport::closeSocketAndSwitchToClosedState(uint16_t code,
const std::string& reason,
size_t closeWireSize,
bool remote)
{
closeSocket();
@ -1133,8 +1125,10 @@ namespace ix
_requestInitCancellation = false;
}
void WebSocketTransport::close(
uint16_t code, const std::string& reason, size_t closeWireSize, bool remote)
void WebSocketTransport::close(uint16_t code,
const std::string& reason,
size_t closeWireSize,
bool remote)
{
_requestInitCancellation = true;

View File

@ -25,7 +25,6 @@
#include <memory>
#include <mutex>
#include <string>
#include <vector>
namespace ix

View File

@ -44,13 +44,22 @@ static bool IsSchemeValid( const std::string& SchemeName )
bool LUrlParser::clParseURL::GetPort(int* OutPort) const
{
if ( !IsValid() ) { return false; }
if (!IsValid())
{
return false;
}
int Port = atoi(m_Port.c_str());
if ( Port <= 0 || Port > 65535 ) { return false; }
if (Port <= 0 || Port > 65535)
{
return false;
}
if ( OutPort ) { *OutPort = Port; }
if (OutPort)
{
*OutPort = Port;
}
return true;
}
@ -65,7 +74,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
/*
* <scheme>:<scheme-specific-part>
* <scheme> := [a-z\+\-\.]+
* For resiliency, programs interpreting URLs should treat upper case letters as equivalent to lower case in scheme names
* For resiliency, programs interpreting URLs should treat upper case letters as equivalent to
*lower case in scheme names
*/
// try to read scheme
@ -86,7 +96,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
}
// scheme should be lowercase
std::transform( Result.m_Scheme.begin(), Result.m_Scheme.end(), Result.m_Scheme.begin(), ::tolower );
std::transform(
Result.m_Scheme.begin(), Result.m_Scheme.end(), Result.m_Scheme.begin(), ::tolower);
// skip ':'
CurrentString = LocalString + 1;
@ -130,7 +141,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
if (bHasUserName)
{
// read user name
while ( *LocalString && *LocalString != ':' && *LocalString != '@' ) LocalString++;
while (*LocalString && *LocalString != ':' && *LocalString != '@')
LocalString++;
Result.m_UserName = std::string(CurrentString, LocalString - CurrentString);
@ -145,7 +157,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
// read password
LocalString = CurrentString;
while ( *LocalString && *LocalString != '@' ) LocalString++;
while (*LocalString && *LocalString != '@')
LocalString++;
Result.m_Password = std::string(CurrentString, LocalString - CurrentString);
@ -195,7 +208,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
// read port number
LocalString = CurrentString;
while ( *LocalString && *LocalString != '/' ) LocalString++;
while (*LocalString && *LocalString != '/')
LocalString++;
Result.m_Port = std::string(CurrentString, LocalString - CurrentString);
@ -221,7 +235,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
// parse the path
LocalString = CurrentString;
while ( *LocalString && *LocalString != '#' && *LocalString != '?' ) LocalString++;
while (*LocalString && *LocalString != '#' && *LocalString != '?')
LocalString++;
Result.m_Path = std::string(CurrentString, LocalString - CurrentString);
@ -236,7 +251,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
// read query
LocalString = CurrentString;
while ( *LocalString && *LocalString != '#' ) LocalString++;
while (*LocalString && *LocalString != '#')
LocalString++;
Result.m_Query = std::string(CurrentString, LocalString - CurrentString);
@ -252,7 +268,8 @@ LUrlParser::clParseURL LUrlParser::clParseURL::ParseURL( const std::string& URL
// read fragment
LocalString = CurrentString;
while ( *LocalString ) LocalString++;
while (*LocalString)
LocalString++;
Result.m_Fragment = std::string(CurrentString, LocalString - CurrentString);
}

View File

@ -62,7 +62,10 @@ namespace LUrlParser
}
/// return 'true' if the parsing was successful
bool IsValid() const { return m_ErrorCode == LUrlParserError_Ok; }
bool IsValid() const
{
return m_ErrorCode == LUrlParserError_Ok;
}
/// helper to convert the port number to int, return 'true' if the port is valid (within the
/// 0..65535 range)

View File

@ -17,4 +17,4 @@ namespace ix
//
pthread_setname_np(name.substr(0, 63).c_str());
}
}
} // namespace ix

View File

@ -15,7 +15,6 @@ namespace ix
// See prctl and PR_SET_NAME property in
// http://man7.org/linux/man-pages/man2/prctl.2.html
//
pthread_setname_np(pthread_self(),
name.substr(0, 15).c_str());
}
pthread_setname_np(pthread_self(), name.substr(0, 15).c_str());
}
} // namespace ix

View File

@ -4,6 +4,7 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include "../IXSetThreadName.h"
#include <Windows.h>
namespace ix
@ -30,7 +31,8 @@ namespace ix
__try
{
RaiseException(MS_VC_EXCEPTION, 0, sizeof(info) / sizeof(ULONG_PTR), (ULONG_PTR*)& info);
RaiseException(
MS_VC_EXCEPTION, 0, sizeof(info) / sizeof(ULONG_PTR), (ULONG_PTR*) &info);
}
__except (EXCEPTION_EXECUTE_HANDLER)
{
@ -41,4 +43,4 @@ namespace ix
{
SetThreadName(-1, name.c_str());
}
}
} // namespace ix

View File

@ -4,14 +4,13 @@
* Copyright (c) 2017 Machine Zone. All rights reserved.
*/
#include <iostream>
#include "IXSnakeServer.h"
#include "IXTest.h"
#include "catch.hpp"
#include <chrono>
#include <iostream>
#include <ixcobra/IXCobraConnection.h>
#include <ixcrypto/IXUuid.h>
#include "IXTest.h"
#include "IXSnakeServer.h"
#include "catch.hpp"
using namespace ix;
@ -22,9 +21,7 @@ namespace
void setupTrafficTrackerCallback()
{
ix::CobraConnection::setTrafficTrackerCallback(
[](size_t size, bool incoming)
{
ix::CobraConnection::setTrafficTrackerCallback([](size_t size, bool incoming) {
if (incoming)
{
incomingBytes += size;
@ -33,8 +30,7 @@ namespace
{
outgoingBytes += size;
}
}
);
});
}
class SatoriChat
@ -77,12 +73,12 @@ namespace
SatoriChat::SatoriChat(const std::string& user,
const std::string& session,
const std::string& endpoint) :
_user(user),
_session(session),
_endpoint(endpoint),
_stop(false),
_connectedAndSubscribed(false)
const std::string& endpoint)
: _user(user)
, _session(session)
, _endpoint(endpoint)
, _stop(false)
, _connectedAndSubscribed(false)
{
}
@ -127,9 +123,7 @@ namespace
void SatoriChat::subscribe(const std::string& channel)
{
std::string filter;
_conn.subscribe(channel, filter,
[this](const Json::Value& msg)
{
_conn.subscribe(channel, filter, [this](const Json::Value& msg) {
std::cout << msg.toStyledString() << std::endl;
if (!msg.isObject()) return;
if (!msg.isMember("user")) return;
@ -150,10 +144,7 @@ namespace
_receivedQueue.push(msg);
std::stringstream ss;
ss << std::endl
<< msg_user << " > " << msg_text
<< std::endl
<< _user << " > ";
ss << std::endl << msg_user << " > " << msg_text << std::endl << _user << " > ";
log(ss.str());
});
}
@ -189,18 +180,15 @@ namespace
std::string role = "_sub";
std::string secret = "66B1dA3ED5fA074EB5AE84Dd8CE3b5ba";
_conn.configure(appkey, _endpoint, role, secret,
ix::WebSocketPerMessageDeflateOptions(true));
_conn.configure(
appkey, _endpoint, role, secret, ix::WebSocketPerMessageDeflateOptions(true));
_conn.connect();
_conn.setEventCallback(
[this, channel]
(ix::CobraConnectionEventType eventType,
_conn.setEventCallback([this, channel](ix::CobraConnectionEventType eventType,
const std::string& errMsg,
const ix::WebSocketHttpHeaders& /*headers*/,
const std::string& subscriptionId,
CobraConnection::MsgId msgId)
{
CobraConnection::MsgId msgId) {
if (eventType == ix::CobraConnection_EventType_Open)
{
log("Subscriber connected: " + _user);
@ -231,8 +219,7 @@ namespace
{
Logger() << "Subscriber: published message acked: " << msgId;
}
}
);
});
while (!_stop)
{
@ -261,19 +248,15 @@ namespace
ix::msleep(50);
_conn.disconnect();
_conn.setEventCallback([]
(ix::CobraConnectionEventType /*eventType*/,
_conn.setEventCallback([](ix::CobraConnectionEventType /*eventType*/,
const std::string& /*errMsg*/,
const ix::WebSocketHttpHeaders& /*headers*/,
const std::string& /*subscriptionId*/,
CobraConnection::MsgId /*msgId*/)
{
;
});
CobraConnection::MsgId /*msgId*/) { ; });
snakeServer.stop();
}
}
} // namespace
TEST_CASE("Cobra_chat", "[cobra_chat]")
{

View File

@ -3,14 +3,13 @@
* Copyright (c) 2018 Machine Zone. All rights reserved.
*/
#include <iostream>
#include <set>
#include <ixcrypto/IXUuid.h>
#include <ixcobra/IXCobraMetricsPublisher.h>
#include "IXTest.h"
#include "IXSnakeServer.h"
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <ixcobra/IXCobraMetricsPublisher.h>
#include <ixcrypto/IXUuid.h>
#include <set>
using namespace ix;
@ -45,18 +44,18 @@ namespace
gMessageCount = 0;
ix::CobraConnection conn;
conn.configure(APPKEY, endpoint, SUBSCRIBER_ROLE, SUBSCRIBER_SECRET,
conn.configure(APPKEY,
endpoint,
SUBSCRIBER_ROLE,
SUBSCRIBER_SECRET,
ix::WebSocketPerMessageDeflateOptions(true));
conn.connect();
conn.setEventCallback(
[&conn]
(ix::CobraConnectionEventType eventType,
conn.setEventCallback([&conn](ix::CobraConnectionEventType eventType,
const std::string& errMsg,
const ix::WebSocketHttpHeaders& /*headers*/,
const std::string& subscriptionId,
CobraConnection::MsgId msgId)
{
CobraConnection::MsgId msgId) {
if (eventType == ix::CobraConnection_EventType_Open)
{
Logger() << "Subscriber connected:";
@ -69,9 +68,7 @@ namespace
{
log("Subscriber authenticated");
std::string filter;
conn.subscribe(CHANNEL, filter,
[](const Json::Value& msg)
{
conn.subscribe(CHANNEL, filter, [](const Json::Value& msg) {
log(msg.toStyledString());
std::string id = msg["id"].asString();
@ -107,8 +104,7 @@ namespace
{
Logger() << "Subscriber: published message acked: " << msgId;
}
}
);
});
while (!gStop)
{
@ -121,7 +117,7 @@ namespace
gUniqueMessageIdsCount = gIds.size();
}
}
} // namespace
TEST_CASE("Cobra_Metrics_Publisher", "[cobra]")
{
@ -158,8 +154,8 @@ TEST_CASE("Cobra_Metrics_Publisher", "[cobra]")
ix::CobraMetricsPublisher cobraMetricsPublisher;
bool perMessageDeflate = true;
cobraMetricsPublisher.configure(APPKEY, endpoint, CHANNEL,
PUBLISHER_ROLE, PUBLISHER_SECRET, perMessageDeflate);
cobraMetricsPublisher.configure(
APPKEY, endpoint, CHANNEL, PUBLISHER_ROLE, PUBLISHER_SECRET, perMessageDeflate);
cobraMetricsPublisher.setSession(uuid4());
cobraMetricsPublisher.enable(true); // disabled by default, needs to be enabled to be active

View File

@ -4,11 +4,10 @@
* Copyright (c) 2018 Machine Zone. All rights reserved.
*/
#include "catch.hpp"
#include "IXTest.h"
#include <ixwebsocket/IXDNSLookup.h>
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXDNSLookup.h>
using namespace ix;
@ -32,7 +31,11 @@ TEST_CASE("dns", "[net]")
auto dnsLookup = std::make_shared<DNSLookup>("wwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwww", 80);
std::string errMsg;
struct addrinfo* res = dnsLookup->resolve(errMsg, [] { return false; });
struct addrinfo* res = dnsLookup->resolve(errMsg,
[]
{
return false;
});
std::cerr << "Error message: " << errMsg << std::endl;
REQUIRE(res == nullptr);
}
@ -43,7 +46,11 @@ TEST_CASE("dns", "[net]")
std::string errMsg;
// The callback returning true means we are requesting cancellation
struct addrinfo* res = dnsLookup->resolve(errMsg, [] { return true; });
struct addrinfo* res = dnsLookup->resolve(errMsg,
[]
{
return true;
});
std::cerr << "Error message: " << errMsg << std::endl;
REQUIRE(res == nullptr);
}

View File

@ -5,11 +5,11 @@
*/
#include "IXGetFreePort.h"
#include <ixwebsocket/IXNetSystem.h>
#include <ixwebsocket/IXSocket.h>
#include <string>
#include <random>
#include <string>
namespace ix
{
@ -30,8 +30,7 @@ namespace ix
}
int enable = 1;
if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR,
(char*) &enable, sizeof(enable)) < 0)
if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, (char*) &enable, sizeof(enable)) < 0)
{
return getAnyFreePortRandom();
}

View File

@ -4,11 +4,10 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXHttpClient.h>
#include "catch.hpp"
using namespace ix;
TEST_CASE("http client", "[http]")
@ -28,14 +27,10 @@ TEST_CASE("http client", "[http]")
args->maxRedirects = 10;
args->verbose = true;
args->compress = true;
args->logger = [](const std::string& msg)
{
std::cout << msg;
};
args->onProgressCallback = [](int current, int total) -> bool
{
std::cerr << "\r" << "Downloaded "
<< current << " bytes out of " << total;
args->logger = [](const std::string& msg) { std::cout << msg; };
args->onProgressCallback = [](int current, int total) -> bool {
std::cerr << "\r"
<< "Downloaded " << current << " bytes out of " << total;
return true;
};
@ -70,14 +65,10 @@ TEST_CASE("http client", "[http]")
args->maxRedirects = 10;
args->verbose = true;
args->compress = true;
args->logger = [](const std::string& msg)
{
std::cout << msg;
};
args->onProgressCallback = [](int current, int total) -> bool
{
std::cerr << "\r" << "Downloaded "
<< current << " bytes out of " << total;
args->logger = [](const std::string& msg) { std::cout << msg; };
args->onProgressCallback = [](int current, int total) -> bool {
std::cerr << "\r"
<< "Downloaded " << current << " bytes out of " << total;
return true;
};
@ -113,23 +104,18 @@ TEST_CASE("http client", "[http]")
args->maxRedirects = 10;
args->verbose = true;
args->compress = true;
args->logger = [](const std::string& msg)
{
std::cout << msg;
};
args->onProgressCallback = [](int current, int total) -> bool
{
std::cerr << "\r" << "Downloaded "
<< current << " bytes out of " << total;
args->logger = [](const std::string& msg) { std::cout << msg; };
args->onProgressCallback = [](int current, int total) -> bool {
std::cerr << "\r"
<< "Downloaded " << current << " bytes out of " << total;
return true;
};
std::atomic<bool> requestCompleted(false);
std::atomic<int> statusCode(0);
httpClient.performRequest(args, [&requestCompleted, &statusCode]
(const HttpResponsePtr& response)
{
httpClient.performRequest(
args, [&requestCompleted, &statusCode](const HttpResponsePtr& response) {
std::cerr << "Upload size: " << response->uploadSize << std::endl;
std::cerr << "Download size: " << response->downloadSize << std::endl;
std::cerr << "Status: " << response->statusCode << std::endl;
@ -138,8 +124,7 @@ TEST_CASE("http client", "[http]")
// In case of failure, print response->errorMsg
statusCode = response->statusCode;
requestCompleted = true;
}
);
});
int wait = 0;
while (wait < 5000)
@ -171,14 +156,10 @@ TEST_CASE("http client", "[http]")
args->maxRedirects = 10;
args->verbose = true;
args->compress = true;
args->logger = [](const std::string& msg)
{
std::cout << msg;
};
args->onProgressCallback = [](int current, int total) -> bool
{
std::cerr << "\r" << "Downloaded "
<< current << " bytes out of " << total;
args->logger = [](const std::string& msg) { std::cout << msg; };
args->onProgressCallback = [](int current, int total) -> bool {
std::cerr << "\r"
<< "Downloaded " << current << " bytes out of " << total;
return true;
};
@ -189,9 +170,10 @@ TEST_CASE("http client", "[http]")
for (int i = 0; i < 3; ++i)
{
httpClient.performRequest(args, [i, &requestCompleted, &statusCode0, &statusCode1, &statusCode2]
(const HttpResponsePtr& response)
{
httpClient.performRequest(
args,
[i, &requestCompleted, &statusCode0, &statusCode1, &statusCode2](
const HttpResponsePtr& response) {
std::cerr << "Upload size: " << response->uploadSize << std::endl;
std::cerr << "Download size: " << response->downloadSize << std::endl;
std::cerr << "Status: " << response->statusCode << std::endl;
@ -211,8 +193,7 @@ TEST_CASE("http client", "[http]")
statusCode2 = response->statusCode;
requestCompleted = true;
}
}
);
});
}
int wait = 0;

View File

@ -4,12 +4,11 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "IXGetFreePort.h"
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXHttpClient.h>
#include <ixwebsocket/IXHttpServer.h>
#include "IXGetFreePort.h"
#include "catch.hpp"
using namespace ix;
@ -39,14 +38,10 @@ TEST_CASE("http server", "[httpd]")
args->maxRedirects = 10;
args->verbose = true;
args->compress = true;
args->logger = [](const std::string& msg)
{
std::cout << msg;
};
args->onProgressCallback = [](int current, int total) -> bool
{
std::cerr << "\r" << "Downloaded "
<< current << " bytes out of " << total;
args->logger = [](const std::string& msg) { std::cout << msg; };
args->onProgressCallback = [](int current, int total) -> bool {
std::cerr << "\r"
<< "Downloaded " << current << " bytes out of " << total;
return true;
};

View File

@ -4,15 +4,13 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXHttp.h>
#include "catch.hpp"
#include <string.h>
namespace ix
{
TEST_CASE("http", "[http]")
{
SECTION("Normal case")
@ -52,4 +50,4 @@ TEST_CASE("http", "[http]")
}
}
}
} // namespace ix

View File

@ -4,11 +4,10 @@
* Copyright (c) 2018 Machine Zone. All rights reserved.
*/
#include "catch.hpp"
#include "IXTest.h"
#include <ixwebsocket/IXSocketConnect.h>
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXSocketConnect.h>
using namespace ix;

View File

@ -4,13 +4,12 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include <iostream>
#include <ixwebsocket/IXSocketFactory.h>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXCancellationRequest.h>
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXCancellationRequest.h>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXSocketFactory.h>
#include <string.h>
using namespace ix;
@ -33,8 +32,7 @@ namespace ix
Logger() << "errMsg: " << errMsg;
REQUIRE(success);
Logger() << "Sending request: " << request
<< "to " << host << ":" << port;
Logger() << "Sending request: " << request << "to " << host << ":" << port;
REQUIRE(socket->writeBytes(request, isCancellationRequested));
auto lineResult = socket->readLine(isCancellationRequested);
@ -49,11 +47,12 @@ namespace ix
REQUIRE(sscanf(line.c_str(), "HTTP/1.1 %d", &status) == 1);
REQUIRE(status == expectedStatus);
}
}
} // namespace ix
TEST_CASE("socket", "[socket]")
{
SECTION("Connect to a local websocket server over a free port. Send GET request without header. Should return 400")
SECTION("Connect to a local websocket server over a free port. Send GET request without "
"header. Should return 400")
{
// Start a server first which we'll hit with our socket code
int port = getFreePort();
@ -78,7 +77,8 @@ TEST_CASE("socket", "[socket]")
}
#if defined(IXWEBSOCKET_USE_TLS)
SECTION("Connect to google HTTPS server over port 443. Send GET request without header. Should return 200")
SECTION("Connect to google HTTPS server over port 443. Send GET request without header. Should "
"return 200")
{
std::string errMsg;
bool tls = true;

View File

@ -5,19 +5,19 @@
*/
#include "IXTest.h"
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXNetSystem.h>
#include <chrono>
#include <thread>
#include <mutex>
#include <string>
#include <fstream>
#include <iostream>
#include <stdlib.h>
#include <stack>
#include <iomanip>
#include <iostream>
#include <ixwebsocket/IXNetSystem.h>
#include <ixwebsocket/IXWebSocket.h>
#include <mutex>
#include <random>
#include <stack>
#include <stdlib.h>
#include <string>
#include <thread>
namespace ix
@ -29,9 +29,7 @@ namespace ix
void setupWebSocketTrafficTrackerCallback()
{
ix::WebSocket::setTrafficTrackerCallback(
[](size_t size, bool incoming)
{
ix::WebSocket::setTrafficTrackerCallback([](size_t size, bool incoming) {
if (incoming)
{
incomingBytes += size;
@ -40,8 +38,7 @@ namespace ix
{
outgoingBytes += size;
}
}
);
});
}
void reportWebSocketTraffic()
@ -61,8 +58,7 @@ namespace ix
{
auto now = std::chrono::system_clock::now();
auto seconds =
std::chrono::duration_cast<std::chrono::seconds>(
now.time_since_epoch()).count();
std::chrono::duration_cast<std::chrono::seconds>(now.time_since_epoch()).count();
return std::to_string(seconds);
}
@ -72,17 +68,14 @@ namespace ix
Logger() << msg;
}
void hexDump(const std::string& prefix,
const std::string& s)
void hexDump(const std::string& prefix, const std::string& s)
{
std::ostringstream ss;
bool upper_case = false;
for (std::string::size_type i = 0; i < s.length(); ++i)
{
ss << std::hex
<< std::setfill('0')
<< std::setw(2)
ss << std::hex << std::setfill('0') << std::setw(2)
<< (upper_case ? std::uppercase : std::nouppercase) << (int) s[i];
}
@ -91,13 +84,10 @@ namespace ix
bool startWebSocketEchoServer(ix::WebSocketServer& server)
{
server.setOnConnectionCallback(
[&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
server.setOnConnectionCallback([&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback(
[webSocket, connectionState, &server](const ix::WebSocketMessagePtr& msg)
{
[webSocket, connectionState, &server](const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
Logger() << "New connection";
@ -122,10 +112,8 @@ namespace ix
}
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -190,4 +178,4 @@ namespace ix
return appConfig;
}
}
} // namespace ix

View File

@ -6,10 +6,10 @@
#pragma once
#include "IXAppConfig.h"
#include "IXGetFreePort.h"
#include <iostream>
#include <ixwebsocket/IXWebSocketServer.h>
#include "IXAppConfig.h"
#include <mutex>
#include <spdlog/spdlog.h>
#include <sstream>

View File

@ -4,6 +4,7 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "catch.hpp"
#include <ixwebsocket/IXCancellationRequest.h>
#include <ixwebsocket/IXConnectionState.h>
#include <ixwebsocket/IXDNSLookup.h>
@ -39,8 +40,6 @@
#include <ixwebsocket/LUrlParser.h>
#include <ixwebsocket/libwshandshake.hpp>
#include "catch.hpp"
using namespace ix;
TEST_CASE("unity build", "[unity_build]")

View File

@ -4,18 +4,16 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include <iostream>
#include <ixwebsocket/IXUrlParser.h>
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXUrlParser.h>
#include <string.h>
using namespace ix;
namespace ix
{
TEST_CASE("urlParser", "[urlParser]")
{
SECTION("http://google.com")
@ -88,7 +86,12 @@ TEST_CASE("urlParser", "[urlParser]")
SECTION("real test")
{
std::string url = "ws://127.0.0.1:7350/ws?token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE1NTcxNzAwNzIsInVpZCI6ImMwZmZjOGE1LTk4OTktNDAwYi1hNGU5LTJjNWM3NjFmNWQxZiIsInVzbiI6InN2YmhOdlNJSmEifQ.5L8BUbpTA4XAHlSrdwhIVlrlIpRtjExepim7Yh5eEO4&status=true&format=protobuf";
std::string url =
"ws://127.0.0.1:7350/"
"ws?token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9."
"eyJleHAiOjE1NTcxNzAwNzIsInVpZCI6ImMwZmZjOGE1LTk4OTktNDAwYi1hNGU5LTJjNWM3NjFmNWQxZi"
"IsInVzbiI6InN2YmhOdlNJSmEifQ.5L8BUbpTA4XAHlSrdwhIVlrlIpRtjExepim7Yh5eEO4&status="
"true&format=protobuf";
std::string protocol, host, path, query;
int port;
bool res;
@ -98,11 +101,18 @@ TEST_CASE("urlParser", "[urlParser]")
REQUIRE(res);
REQUIRE(protocol == "ws");
REQUIRE(host == "127.0.0.1");
REQUIRE(path == "/ws?token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE1NTcxNzAwNzIsInVpZCI6ImMwZmZjOGE1LTk4OTktNDAwYi1hNGU5LTJjNWM3NjFmNWQxZiIsInVzbiI6InN2YmhOdlNJSmEifQ.5L8BUbpTA4XAHlSrdwhIVlrlIpRtjExepim7Yh5eEO4&status=true&format=protobuf");
REQUIRE(query == "token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJleHAiOjE1NTcxNzAwNzIsInVpZCI6ImMwZmZjOGE1LTk4OTktNDAwYi1hNGU5LTJjNWM3NjFmNWQxZiIsInVzbiI6InN2YmhOdlNJSmEifQ.5L8BUbpTA4XAHlSrdwhIVlrlIpRtjExepim7Yh5eEO4&status=true&format=protobuf");
REQUIRE(path ==
"/ws?token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9."
"eyJleHAiOjE1NTcxNzAwNzIsInVpZCI6ImMwZmZjOGE1LTk4OTktNDAwYi1hNGU5LTJjNWM3NjFmNW"
"QxZiIsInVzbiI6InN2YmhOdlNJSmEifQ.5L8BUbpTA4XAHlSrdwhIVlrlIpRtjExepim7Yh5eEO4&"
"status=true&format=protobuf");
REQUIRE(query ==
"token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9."
"eyJleHAiOjE1NTcxNzAwNzIsInVpZCI6ImMwZmZjOGE1LTk4OTktNDAwYi1hNGU5LTJjNWM3NjFmNW"
"QxZiIsInVzbiI6InN2YmhOdlNJSmEifQ.5L8BUbpTA4XAHlSrdwhIVlrlIpRtjExepim7Yh5eEO4&"
"status=true&format=protobuf");
REQUIRE(port == 7350);
}
}
}
} // namespace ix

View File

@ -9,17 +9,15 @@
// websocket_chat_server/broacast-server.js
//
#include "IXTest.h"
#include "catch.hpp"
#include "msgpack11.hpp"
#include <iostream>
#include <sstream>
#include <vector>
#include <mutex>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include "msgpack11.hpp"
#include "IXTest.h"
#include "catch.hpp"
#include <mutex>
#include <sstream>
#include <vector>
using msgpack11::MsgPack;
using namespace ix;
@ -29,9 +27,7 @@ namespace
class WebSocketChat
{
public:
WebSocketChat(const std::string& user,
const std::string& session,
int port);
WebSocketChat(const std::string& user, const std::string& session, int port);
void subscribe(const std::string& channel);
void start();
@ -57,12 +53,10 @@ namespace
mutable std::mutex _mutex;
};
WebSocketChat::WebSocketChat(const std::string& user,
const std::string& session,
int port) :
_user(user),
_session(session),
_port(port)
WebSocketChat::WebSocketChat(const std::string& user, const std::string& session, int port)
: _user(user)
, _session(session)
, _port(port)
{
;
}
@ -100,10 +94,7 @@ namespace
std::string url;
{
std::stringstream ss;
ss << "ws://127.0.0.1:"
<< _port
<< "/"
<< _user;
ss << "ws://127.0.0.1:" << _port << "/" << _user;
url = ss.str();
}
@ -113,22 +104,16 @@ namespace
std::stringstream ss;
log(std::string("Connecting to url: ") + url);
_webSocket.setOnMessageCallback(
[this](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const ix::WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
ss << "cmd_websocket_chat: user "
<< _user
<< " Connected !";
ss << "cmd_websocket_chat: user " << _user << " Connected !";
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Close)
{
ss << "cmd_websocket_chat: user "
<< _user
<< " disconnected !";
ss << "cmd_websocket_chat: user " << _user << " disconnected !";
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Message)
@ -148,10 +133,7 @@ namespace
payload = "<message too large>";
}
ss << std::endl
<< result.first << " > " << payload
<< std::endl
<< _user << " > ";
ss << std::endl << result.first << " > " << payload << std::endl << _user << " > ";
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Error)
@ -211,13 +193,10 @@ namespace
bool startServer(ix::WebSocketServer& server)
{
server.setOnConnectionCallback(
[&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
server.setOnConnectionCallback([&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback(
[webSocket, connectionState, &server](const ix::WebSocketMessagePtr& msg)
{
[webSocket, connectionState, &server](const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
Logger() << "New connection";
@ -243,10 +222,8 @@ namespace
}
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -258,7 +235,7 @@ namespace
server.start();
return true;
}
}
} // namespace
TEST_CASE("Websocket_chat", "[websocket_chat]")
{
@ -305,8 +282,7 @@ TEST_CASE("Websocket_chat", "[websocket_chat]")
// Wait until all messages are received. 10s timeout
int attempts = 0;
while (chatA.getReceivedMessagesCount() != 3 ||
chatB.getReceivedMessagesCount() != 3)
while (chatA.getReceivedMessagesCount() != 3 || chatB.getReceivedMessagesCount() != 3)
{
REQUIRE(attempts++ < 10);
ix::msleep(1000);

View File

@ -4,15 +4,13 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <sstream>
#include <queue>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include "IXTest.h"
#include "catch.hpp"
#include <queue>
#include <sstream>
using namespace ix;
@ -102,9 +100,7 @@ namespace
std::string url;
{
std::stringstream ss;
ss << "ws://localhost:"
<< _port
<< "/";
ss << "ws://localhost:" << _port << "/";
url = ss.str();
}
@ -115,9 +111,7 @@ namespace
std::stringstream ss;
log(std::string("Connecting to url: ") + url);
_webSocket.setOnMessageCallback(
[this](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const ix::WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -126,10 +120,7 @@ namespace
else if (msg->type == ix::WebSocketMessageType::Close)
{
std::stringstream ss;
ss << "client disconnected("
<< msg->closeInfo.code
<< ","
<< msg->closeInfo.reason
ss << "client disconnected(" << msg->closeInfo.code << "," << msg->closeInfo.reason
<< ")";
log(ss.str());
@ -178,12 +169,15 @@ namespace
{
// A dev/null server
server.setOnConnectionCallback(
[&receivedCloseCode, &receivedCloseReason, &receivedCloseRemote, &mutexWrite](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
webSocket->setOnMessageCallback(
[webSocket, connectionState, &receivedCloseCode, &receivedCloseReason, &receivedCloseRemote, &mutexWrite](const ix::WebSocketMessagePtr& msg)
{
[&receivedCloseCode, &receivedCloseReason, &receivedCloseRemote, &mutexWrite](
std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback([webSocket,
connectionState,
&receivedCloseCode,
&receivedCloseReason,
&receivedCloseRemote,
&mutexWrite](const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
Logger() << "New server connection";
@ -198,11 +192,8 @@ namespace
else if (msg->type == ix::WebSocketMessageType::Close)
{
std::stringstream ss;
ss << "Server closed connection("
<< msg->closeInfo.code
<< ","
<< msg->closeInfo.reason
<< ")";
ss << "Server closed connection(" << msg->closeInfo.code << ","
<< msg->closeInfo.reason << ")";
log(ss.str());
std::lock_guard<std::mutex> lck(mutexWrite);
@ -211,10 +202,8 @@ namespace
receivedCloseReason = std::string(msg->closeInfo.reason);
receivedCloseRemote = msg->closeInfo.remote;
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -226,7 +215,7 @@ namespace
server.start();
return true;
}
}
} // namespace
TEST_CASE("Websocket_client_close_default", "[close]")
{
@ -242,7 +231,11 @@ TEST_CASE("Websocket_client_close_default", "[close]")
std::string serverReceivedCloseReason("");
std::mutex mutexWrite;
REQUIRE(startServer(server, serverReceivedCloseCode, serverReceivedCloseReason, serverReceivedCloseRemote, mutexWrite));
REQUIRE(startServer(server,
serverReceivedCloseCode,
serverReceivedCloseReason,
serverReceivedCloseRemote,
mutexWrite));
std::string session = ix::generateSessionId();
WebSocketClient webSocketClient(port);
@ -301,7 +294,11 @@ TEST_CASE("Websocket_client_close_params_given", "[close]")
std::string serverReceivedCloseReason("");
std::mutex mutexWrite;
REQUIRE(startServer(server, serverReceivedCloseCode, serverReceivedCloseReason, serverReceivedCloseRemote, mutexWrite));
REQUIRE(startServer(server,
serverReceivedCloseCode,
serverReceivedCloseReason,
serverReceivedCloseRemote,
mutexWrite));
std::string session = ix::generateSessionId();
WebSocketClient webSocketClient(port);
@ -359,7 +356,11 @@ TEST_CASE("Websocket_server_close", "[close]")
std::string serverReceivedCloseReason("");
std::mutex mutexWrite;
REQUIRE(startServer(server, serverReceivedCloseCode, serverReceivedCloseReason, serverReceivedCloseRemote, mutexWrite));
REQUIRE(startServer(server,
serverReceivedCloseCode,
serverReceivedCloseReason,
serverReceivedCloseRemote,
mutexWrite));
std::string session = ix::generateSessionId();
WebSocketClient webSocketClient(port);
@ -417,7 +418,11 @@ TEST_CASE("Websocket_server_close_immediatly", "[close]")
std::string serverReceivedCloseReason("");
std::mutex mutexWrite;
REQUIRE(startServer(server, serverReceivedCloseCode, serverReceivedCloseReason, serverReceivedCloseRemote, mutexWrite));
REQUIRE(startServer(server,
serverReceivedCloseCode,
serverReceivedCloseReason,
serverReceivedCloseRemote,
mutexWrite));
std::string session = ix::generateSessionId();
WebSocketClient webSocketClient(port);

View File

@ -4,12 +4,11 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include <ixwebsocket/IXWebSocketMessageQueue.h>
#include "IXTest.h"
#include "catch.hpp"
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketMessageQueue.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include <thread>
using namespace ix;
@ -18,13 +17,10 @@ namespace
{
bool startServer(ix::WebSocketServer& server)
{
server.setOnConnectionCallback(
[&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
server.setOnConnectionCallback([&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback(
[connectionState, &server](const WebSocketMessagePtr& msg)
{
[connectionState, &server](const WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
Logger() << "New connection";
@ -50,10 +46,8 @@ namespace
client->send(msg->str);
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -73,8 +67,7 @@ namespace
{
msgQ.bindWebsocket(&ws);
msgQ.setOnMessageCallback([this](const WebSocketMessagePtr& msg)
{
msgQ.setOnMessageCallback([this](const WebSocketMessagePtr& msg) {
REQUIRE(mainThreadId == std::this_thread::get_id());
std::stringstream ss;
@ -153,7 +146,10 @@ namespace
}
}
bool isSucceeded() const { return succeeded; }
bool isSucceeded() const
{
return succeeded;
}
private:
WebSocket ws;
@ -163,7 +159,7 @@ namespace
std::thread::id mainThreadId;
bool succeeded = false;
};
}
} // namespace
TEST_CASE("Websocket_message_queue", "[websocket_message_q]")
{

View File

@ -4,15 +4,13 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <sstream>
#include <queue>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include "IXTest.h"
#include "catch.hpp"
#include <queue>
#include <sstream>
using namespace ix;
@ -35,8 +33,8 @@ namespace
};
WebSocketClient::WebSocketClient(int port, bool useHeartBeatMethod)
: _port(port),
_useHeartBeatMethod(useHeartBeatMethod)
: _port(port)
, _useHeartBeatMethod(useHeartBeatMethod)
{
;
}
@ -56,9 +54,7 @@ namespace
std::string url;
{
std::stringstream ss;
ss << "ws://127.0.0.1:"
<< _port
<< "/";
ss << "ws://127.0.0.1:" << _port << "/";
url = ss.str();
}
@ -79,14 +75,12 @@ namespace
std::stringstream ss;
log(std::string("Connecting to url: ") + url);
_webSocket.setOnMessageCallback(
[](ix::WebSocketMessageType messageType,
_webSocket.setOnMessageCallback([](ix::WebSocketMessageType messageType,
const std::string& str,
size_t wireSize,
const ix::WebSocketErrorInfo& error,
const ix::WebSocketOpenInfo& openInfo,
const ix::WebSocketCloseInfo& closeInfo)
{
const ix::WebSocketCloseInfo& closeInfo) {
std::stringstream ss;
if (messageType == ix::WebSocketMessageType::Open)
{
@ -135,16 +129,15 @@ namespace
// A dev/null server
server.setOnConnectionCallback(
[&server, &receivedPingMessages](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback(
[webSocket, connectionState, &server, &receivedPingMessages](ix::WebSocketMessageType messageType,
[webSocket, connectionState, &server, &receivedPingMessages](
ix::WebSocketMessageType messageType,
const std::string& str,
size_t wireSize,
const ix::WebSocketErrorInfo& error,
const ix::WebSocketOpenInfo& openInfo,
const ix::WebSocketCloseInfo& closeInfo)
{
const ix::WebSocketCloseInfo& closeInfo) {
if (messageType == ix::WebSocketMessageType::Open)
{
Logger() << "New server connection";
@ -173,10 +166,8 @@ namespace
client->sendText("reply");
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -188,7 +179,7 @@ namespace
server.start();
return true;
}
}
} // namespace
TEST_CASE("Websocket_ping_no_data_sent_setPingInterval", "[setPingInterval]")
{
@ -282,7 +273,8 @@ TEST_CASE("Websocket_ping_data_sent_setPingInterval", "[setPingInterval]")
TEST_CASE("Websocket_ping_data_sent_setPingInterval_half_full", "[setPingInterval]")
{
SECTION("Make sure that ping messages are sent, even if other messages are sent continuously during a given time")
SECTION("Make sure that ping messages are sent, even if other messages are sent continuously "
"during a given time")
{
ix::setupWebSocketTrafficTrackerCallback();
@ -335,7 +327,8 @@ TEST_CASE("Websocket_ping_data_sent_setPingInterval_half_full", "[setPingInterva
TEST_CASE("Websocket_ping_data_sent_setPingInterval_full", "[setPingInterval]")
{
SECTION("Make sure that ping messages are sent, even if other messages are sent continuously for longer than ping interval")
SECTION("Make sure that ping messages are sent, even if other messages are sent continuously "
"for longer than ping interval")
{
ix::setupWebSocketTrafficTrackerCallback();

View File

@ -4,15 +4,13 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <sstream>
#include <queue>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include "IXTest.h"
#include "catch.hpp"
#include <queue>
#include <sstream>
using namespace ix;
@ -41,11 +39,11 @@ namespace
};
WebSocketClient::WebSocketClient(int port, int pingInterval, int pingTimeout)
: _port(port),
_receivedPongMessages(0),
_closedDueToPingTimeout(false),
_pingInterval(pingInterval),
_pingTimeout(pingTimeout)
: _port(port)
, _receivedPongMessages(0)
, _closedDueToPingTimeout(false)
, _pingInterval(pingInterval)
, _pingTimeout(pingTimeout)
{
;
}
@ -70,9 +68,7 @@ namespace
std::string url;
{
std::stringstream ss;
ss << "ws://127.0.0.1:"
<< _port
<< "/";
ss << "ws://127.0.0.1:" << _port << "/";
url = ss.str();
}
@ -88,19 +84,16 @@ namespace
std::stringstream ss;
log(std::string("Connecting to url: ") + url);
_webSocket.setOnMessageCallback(
[this](ix::WebSocketMessageType messageType,
_webSocket.setOnMessageCallback([this](ix::WebSocketMessageType messageType,
const std::string& str,
size_t wireSize,
const ix::WebSocketErrorInfo& error,
const ix::WebSocketOpenInfo& openInfo,
const ix::WebSocketCloseInfo& closeInfo)
{
const ix::WebSocketCloseInfo& closeInfo) {
std::stringstream ss;
if (messageType == ix::WebSocketMessageType::Open)
{
log("client connected");
}
else if (messageType == ix::WebSocketMessageType::Close)
{
@ -110,7 +103,6 @@ namespace
{
_closedDueToPingTimeout = true;
}
}
else if (messageType == ix::WebSocketMessageType::Error)
{
@ -159,21 +151,22 @@ namespace
return _closedDueToPingTimeout;
}
bool startServer(ix::WebSocketServer& server, std::atomic<int>& receivedPingMessages, bool enablePong)
bool startServer(ix::WebSocketServer& server,
std::atomic<int>& receivedPingMessages,
bool enablePong)
{
// A dev/null server
server.setOnConnectionCallback(
[&server, &receivedPingMessages](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback(
[webSocket, connectionState, &server, &receivedPingMessages](ix::WebSocketMessageType messageType,
[webSocket, connectionState, &server, &receivedPingMessages](
ix::WebSocketMessageType messageType,
const std::string& str,
size_t wireSize,
const ix::WebSocketErrorInfo& error,
const ix::WebSocketOpenInfo& openInfo,
const ix::WebSocketCloseInfo& closeInfo)
{
const ix::WebSocketCloseInfo& closeInfo) {
if (messageType == ix::WebSocketMessageType::Open)
{
Logger() << "New server connection";
@ -194,10 +187,8 @@ namespace
log("Server received a ping");
receivedPingMessages++;
}
}
);
}
);
});
});
if (!enablePong)
{
@ -215,7 +206,7 @@ namespace
server.start();
return true;
}
}
} // namespace
TEST_CASE("Websocket_ping_timeout_not_checked", "[setPingTimeout]")
{

View File

@ -4,15 +4,13 @@
* Copyright (c) 2019 Machine Zone. All rights reserved.
*/
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXSocketFactory.h>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXWebSocketServer.h>
#include <ixwebsocket/IXSocketFactory.h>
#include "IXTest.h"
#include "catch.hpp"
using namespace ix;
@ -28,23 +26,18 @@ namespace ix
}
};
bool startServer(ix::WebSocketServer& server,
std::string& connectionId)
{
auto factory = []() -> std::shared_ptr<ConnectionState>
bool startServer(ix::WebSocketServer& server, std::string& connectionId)
{
auto factory = []() -> std::shared_ptr<ConnectionState> {
return std::make_shared<ConnectionStateCustom>();
};
server.setConnectionStateFactory(factory);
server.setOnConnectionCallback(
[&server, &connectionId](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
webSocket->setOnMessageCallback(
[webSocket, connectionState,
&connectionId, &server](const ix::WebSocketMessagePtr& msg)
{
server.setOnConnectionCallback([&server, &connectionId](
std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback([webSocket, connectionState, &connectionId, &server](
const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
Logger() << "New connection";
@ -73,10 +66,8 @@ namespace ix
}
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -88,7 +79,7 @@ namespace ix
server.start();
return true;
}
}
} // namespace ix
TEST_CASE("Websocket_server", "[websocket_server]")
{
@ -103,10 +94,7 @@ TEST_CASE("Websocket_server", "[websocket_server]")
bool tls = false;
std::shared_ptr<Socket> socket = createSocket(tls, errMsg);
std::string host("127.0.0.1");
auto isCancellationRequested = []() -> bool
{
return false;
};
auto isCancellationRequested = []() -> bool { return false; };
bool success = socket->connect(host, port, errMsg, isCancellationRequested);
REQUIRE(success);
@ -139,10 +127,7 @@ TEST_CASE("Websocket_server", "[websocket_server]")
bool tls = false;
std::shared_ptr<Socket> socket = createSocket(tls, errMsg);
std::string host("127.0.0.1");
auto isCancellationRequested = []() -> bool
{
return false;
};
auto isCancellationRequested = []() -> bool { return false; };
bool success = socket->connect(host, port, errMsg, isCancellationRequested);
REQUIRE(success);
@ -178,10 +163,7 @@ TEST_CASE("Websocket_server", "[websocket_server]")
bool tls = false;
std::shared_ptr<Socket> socket = createSocket(tls, errMsg);
std::string host("127.0.0.1");
auto isCancellationRequested = []() -> bool
{
return false;
};
auto isCancellationRequested = []() -> bool { return false; };
bool success = socket->connect(host, port, errMsg, isCancellationRequested);
REQUIRE(success);

View File

@ -4,13 +4,12 @@
* Copyright (c) 2017 Machine Zone. All rights reserved.
*/
#include <iostream>
#include <sstream>
#include <set>
#include <ixwebsocket/IXWebSocket.h>
#include "IXTest.h"
#include "catch.hpp"
#include <iostream>
#include <ixwebsocket/IXWebSocket.h>
#include <set>
#include <sstream>
using namespace ix;
@ -19,7 +18,7 @@ namespace
const std::string WEBSOCKET_DOT_ORG_URL("wss://echo.websocket.org");
const std::string GOOGLE_URL("wss://google.com");
const std::string UNKNOWN_URL("wss://asdcasdcaasdcasdcasdcasdcasdcasdcasassdd.com");
}
} // namespace
namespace
{
@ -51,9 +50,7 @@ namespace
std::stringstream ss;
log(std::string("Connecting to url: ") + url);
_webSocket.setOnMessageCallback(
[](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([](const ix::WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -100,11 +97,12 @@ namespace
// Start the connection
_webSocket.start();
}
}
} // namespace
//
// We try to connect to different servers, and make sure there are no crashes.
// FIXME: We could do more checks (make sure that we were not able to connect to unknown servers, etc...)
// FIXME: We could do more checks (make sure that we were not able to connect to unknown servers,
// etc...)
//
TEST_CASE("websocket_connections", "[websocket]")
{
@ -121,7 +119,8 @@ TEST_CASE("websocket_connections", "[websocket]")
test.stop();
}
SECTION("Try to connect and disconnect with different timing, not enough time to succesfully connect")
SECTION("Try to connect and disconnect with different timing, not enough time to succesfully "
"connect")
{
IXWebSocketTestConnectionDisconnection test;
log(std::string("50 Runs"));
@ -141,7 +140,8 @@ TEST_CASE("websocket_connections", "[websocket]")
// This test breaks on travis CI - Ubuntu Xenial + gcc + tsan
// We should fix this.
SECTION("Try to connect and disconnect with different timing, from not enough time to successfull connect")
SECTION("Try to connect and disconnect with different timing, from not enough time to "
"successfull connect")
{
IXWebSocketTestConnectionDisconnection test;
log(std::string("20 Runs"));

View File

@ -6,20 +6,15 @@
#define CATCH_CONFIG_RUNNER
#include "catch.hpp"
#include <spdlog/spdlog.h>
#include <ixwebsocket/IXNetSystem.h>
#include <ixcore/utils/IXCoreLogger.h>
#include <ixwebsocket/IXNetSystem.h>
#include <spdlog/spdlog.h>
int main(int argc, char* argv[])
{
ix::initNetSystem();
ix::IXCoreLogger::LogFunc logFunc = [](const char* msg)
{
spdlog::info(msg);
};
ix::IXCoreLogger::LogFunc logFunc = [](const char* msg) { spdlog::info(msg); };
ix::IXCoreLogger::setLogFunction(logFunc);
int result = Catch::Session().run(argc, argv);

View File

@ -5,14 +5,14 @@
*/
#include "IXRedisClient.h"
#include <ixwebsocket/IXSocketFactory.h>
#include <ixwebsocket/IXSocket.h>
#include <iostream>
#include <sstream>
#include <iomanip>
#include <vector>
#include <cstring>
#include <iomanip>
#include <iostream>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXSocketFactory.h>
#include <sstream>
#include <vector>
namespace ix
{
@ -31,8 +31,7 @@ namespace ix
return _socket->connect(hostname, port, errMsg, nullptr);
}
bool RedisClient::auth(const std::string& password,
std::string& response)
bool RedisClient::auth(const std::string& password, std::string& response)
{
response.clear();
@ -246,4 +245,4 @@ namespace ix
{
_stop = true;
}
}
} // namespace ix

View File

@ -6,9 +6,9 @@
#pragma once
#include <atomic>
#include <functional>
#include <memory>
#include <atomic>
namespace ix
{
@ -20,7 +20,10 @@ namespace ix
using OnRedisSubscribeResponseCallback = std::function<void(const std::string&)>;
using OnRedisSubscribeCallback = std::function<void(const std::string&)>;
RedisClient() : _stop(false) {}
RedisClient()
: _stop(false)
{
}
~RedisClient() = default;
bool connect(const std::string& hostname, int port);

View File

@ -8,17 +8,16 @@
#include <chrono>
#include <iostream>
#include <spdlog/spdlog.h>
#include <ixwebsocket/IXWebSocketHttpHeaders.h>
#include <spdlog/spdlog.h>
namespace ix
{
SentryClient::SentryClient(const std::string& dsn) :
_dsn(dsn),
_validDsn(false),
_luaFrameRegex("\t([^/]+):([0-9]+): in function '([^/]+)'")
SentryClient::SentryClient(const std::string& dsn)
: _dsn(dsn)
, _validDsn(false)
, _luaFrameRegex("\t([^/]+):([0-9]+): in function '([^/]+)'")
{
const std::regex dsnRegex("(http[s]?)://([^:]+):([^@]+)@([^/]+)/([0-9]+)");
std::smatch group;
@ -168,8 +167,7 @@ namespace ix
return _jsonWriter.write(payload);
}
std::pair<HttpResponsePtr, std::string> SentryClient::send(const Json::Value& msg,
bool verbose)
std::pair<HttpResponsePtr, std::string> SentryClient::send(const Json::Value& msg, bool verbose)
{
auto args = _httpClient.createRequest();
args->extraHeaders["X-Sentry-Auth"] = SentryClient::computeAuthHeader();
@ -177,10 +175,7 @@ namespace ix
args->transferTimeout = 5 * 60;
args->followRedirects = true;
args->verbose = verbose;
args->logger = [](const std::string& msg)
{
spdlog::info("request logger: {}", msg);
};
args->logger = [](const std::string& msg) { spdlog::info("request logger: {}", msg); };
std::string body = computePayload(msg);
HttpResponsePtr response = _httpClient.post(_url, body, args);

View File

@ -4,24 +4,20 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include "IXSnakeProtocol.h"
#include "IXAppConfig.h"
#include "IXSnakeProtocol.h"
#include <iostream>
#include <ixcrypto/IXUuid.h>
namespace snake
{
bool isAppKeyValid(
const AppConfig& appConfig,
std::string appkey)
bool isAppKeyValid(const AppConfig& appConfig, std::string appkey)
{
return appConfig.apps.count(appkey) != 0;
}
std::string getRoleSecret(
const AppConfig& appConfig,
std::string appkey,
std::string role)
std::string getRoleSecret(const AppConfig& appConfig, std::string appkey, std::string role)
{
if (!isAppKeyValid(appConfig, appkey))
{
@ -49,4 +45,4 @@ namespace snake
std::cout << "redis password: " << appConfig.redisPassword << std::endl;
std::cout << "redis port: " << appConfig.redisPort << std::endl;
}
}
} // namespace snake

View File

@ -16,16 +16,37 @@ namespace snake
class SnakeConnectionState : public ix::ConnectionState
{
public:
std::string getNonce() { return _nonce; }
void setNonce(const std::string& nonce) { _nonce = nonce; }
std::string getNonce()
{
return _nonce;
}
void setNonce(const std::string& nonce)
{
_nonce = nonce;
}
std::string appkey() { return _appkey; }
void setAppkey(const std::string& appkey) { _appkey = appkey; }
std::string appkey()
{
return _appkey;
}
void setAppkey(const std::string& appkey)
{
_appkey = appkey;
}
std::string role() { return _role; }
void setRole(const std::string& role) { _role = role; }
std::string role()
{
return _role;
}
void setRole(const std::string& role)
{
_role = role;
}
ix::RedisClient& redisClient() { return _redisClient; }
ix::RedisClient& redisClient()
{
return _redisClient;
}
std::future<void> fut;

View File

@ -6,20 +6,17 @@
#include "IXSnakeProtocol.h"
#include <ixwebsocket/IXWebSocket.h>
#include <ixcrypto/IXHMac.h>
#include "IXSnakeConnectionState.h"
#include "IXAppConfig.h"
#include "IXSnakeConnectionState.h"
#include "nlohmann/json.hpp"
#include <sstream>
#include <iostream>
#include <ixcrypto/IXHMac.h>
#include <ixwebsocket/IXWebSocket.h>
#include <sstream>
namespace snake
{
void handleError(
const std::string& action,
void handleError(const std::string& action,
std::shared_ptr<ix::WebSocket> ws,
nlohmann::json pdu,
const std::string& errMsg)
@ -28,17 +25,11 @@ namespace snake
actionError += "/error";
nlohmann::json response = {
{"action", actionError},
{"id", pdu.value("id", 1)},
{"body", {
{"reason", errMsg}
}}
};
{"action", actionError}, {"id", pdu.value("id", 1)}, {"body", {{"reason", errMsg}}}};
ws->sendText(response.dump());
}
void handleHandshake(
std::shared_ptr<SnakeConnectionState> state,
void handleHandshake(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const nlohmann::json& pdu)
{
@ -50,13 +41,10 @@ namespace snake
nlohmann::json response = {
{"action", "auth/handshake/ok"},
{"id", pdu.value("id", 1)},
{"body", {
{"data", {
{"nonce", state->getNonce()},
{"connection_id", state->getId()}
}},
}}
};
{"body",
{
{"data", {{"nonce", state->getNonce()}, {"connection_id", state->getId()}}},
}}};
auto serializedResponse = response.dump();
std::cout << "response = " << serializedResponse << std::endl;
@ -64,8 +52,7 @@ namespace snake
ws->sendText(serializedResponse);
}
void handleAuth(
std::shared_ptr<SnakeConnectionState> state,
void handleAuth(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const AppConfig& appConfig,
const nlohmann::json& pdu)
@ -78,11 +65,7 @@ namespace snake
nlohmann::json response = {
{"action", "auth/authenticate/error"},
{"id", pdu.value("id", 1)},
{"body", {
{"error", "authentication_failed"},
{"reason", "invalid secret"}
}}
};
{"body", {{"error", "authentication_failed"}, {"reason", "invalid secret"}}}};
ws->sendText(response.dump());
return;
}
@ -102,26 +85,18 @@ namespace snake
nlohmann::json response = {
{"action", "auth/authenticate/error"},
{"id", pdu.value("id", 1)},
{"body", {
{"error", "authentication_failed"},
{"reason", "invalid hash"}
}}
};
{"body", {{"error", "authentication_failed"}, {"reason", "invalid hash"}}}};
ws->sendText(response.dump());
return;
}
nlohmann::json response = {
{"action", "auth/authenticate/ok"},
{"id", pdu.value("id", 1)},
{"body", {}}
};
{"action", "auth/authenticate/ok"}, {"id", pdu.value("id", 1)}, {"body", {}}};
ws->sendText(response.dump());
}
void handlePublish(
std::shared_ptr<SnakeConnectionState> state,
void handlePublish(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const nlohmann::json& pdu)
{
@ -150,9 +125,7 @@ namespace snake
for (auto&& channel : channels)
{
std::stringstream ss;
ss << state->appkey()
<< "::"
<< channel;
ss << state->appkey() << "::" << channel;
std::string errMsg;
if (!state->redisClient().publish(ss.str(), pdu.dump(), errMsg))
@ -165,10 +138,7 @@ namespace snake
}
nlohmann::json response = {
{"action", "rtm/publish/ok"},
{"id", pdu.value("id", 1)},
{"body", {}}
};
{"action", "rtm/publish/ok"}, {"id", pdu.value("id", 1)}, {"body", {}}};
ws->sendText(response.dump());
}
@ -176,8 +146,7 @@ namespace snake
//
// FIXME: this is not cancellable. We should be able to cancel the redis subscription
//
void handleRedisSubscription(
std::shared_ptr<SnakeConnectionState> state,
void handleRedisSubscription(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const AppConfig& appConfig,
const nlohmann::json& pdu)
@ -186,9 +155,7 @@ namespace snake
std::string subscriptionId = channel;
std::stringstream ss;
ss << state->appkey()
<< "::"
<< channel;
ss << state->appkey() << "::" << channel;
std::string appChannel(ss.str());
@ -224,8 +191,7 @@ namespace snake
}
int id = 0;
auto callback = [ws, &id, &subscriptionId](const std::string& messageStr)
{
auto callback = [ws, &id, &subscriptionId](const std::string& messageStr) {
auto msg = nlohmann::json::parse(messageStr);
msg = msg["body"]["message"];
@ -233,27 +199,18 @@ namespace snake
nlohmann::json response = {
{"action", "rtm/subscription/data"},
{"id", id++},
{"body", {
{"subscription_id", subscriptionId},
{"messages", {msg}}
}}
};
{"body", {{"subscription_id", subscriptionId}, {"messages", {msg}}}}};
ws->sendText(response.dump());
};
auto responseCallback = [ws, pdu, &subscriptionId](const std::string& redisResponse)
{
auto responseCallback = [ws, pdu, &subscriptionId](const std::string& redisResponse) {
std::cout << "Redis subscribe response: " << redisResponse << std::endl;
// Success
nlohmann::json response = {
{"action", "rtm/subscribe/ok"},
nlohmann::json response = {{"action", "rtm/subscribe/ok"},
{"id", pdu.value("id", 1)},
{"body", {
{"subscription_id", subscriptionId}
}}
};
{"body", {{"subscription_id", subscriptionId}}}};
ws->sendText(response.dump());
};
@ -267,22 +224,16 @@ namespace snake
}
}
void handleSubscribe(
std::shared_ptr<SnakeConnectionState> state,
void handleSubscribe(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const AppConfig& appConfig,
const nlohmann::json& pdu)
{
state->fut = std::async(std::launch::async,
handleRedisSubscription,
state,
ws,
appConfig,
pdu);
state->fut =
std::async(std::launch::async, handleRedisSubscription, state, ws, appConfig, pdu);
}
void handleUnSubscribe(
std::shared_ptr<SnakeConnectionState> state,
void handleUnSubscribe(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const nlohmann::json& pdu)
{
@ -292,18 +243,13 @@ namespace snake
state->redisClient().stop();
nlohmann::json response = {
{"action", "rtm/unsubscribe/ok"},
nlohmann::json response = {{"action", "rtm/unsubscribe/ok"},
{"id", pdu.value("id", 1)},
{"body", {
{"subscription_id", subscriptionId}
}}
};
{"body", {{"subscription_id", subscriptionId}}}};
ws->sendText(response.dump());
}
void processCobraMessage(
std::shared_ptr<SnakeConnectionState> state,
void processCobraMessage(std::shared_ptr<SnakeConnectionState> state,
std::shared_ptr<ix::WebSocket> ws,
const AppConfig& appConfig,
const std::string& str)
@ -339,4 +285,4 @@ namespace snake
std::cerr << "Unhandled action: " << action << std::endl;
}
}
}
} // namespace snake

View File

@ -5,18 +5,18 @@
*/
#include "IXSnakeServer.h"
#include "IXSnakeProtocol.h"
#include "IXSnakeConnectionState.h"
#include "IXAppConfig.h"
#include "IXAppConfig.h"
#include "IXSnakeConnectionState.h"
#include "IXSnakeProtocol.h"
#include <iostream>
#include <sstream>
namespace snake
{
SnakeServer::SnakeServer(const AppConfig& appConfig) :
_appConfig(appConfig),
_server(appConfig.port, appConfig.hostname)
SnakeServer::SnakeServer(const AppConfig& appConfig)
: _appConfig(appConfig)
, _server(appConfig.port, appConfig.hostname)
{
;
}
@ -45,21 +45,18 @@ namespace snake
{
std::cout << "Listening on " << _appConfig.hostname << ":" << _appConfig.port << std::endl;
auto factory = []() -> std::shared_ptr<ix::ConnectionState>
{
auto factory = []() -> std::shared_ptr<ix::ConnectionState> {
return std::make_shared<SnakeConnectionState>();
};
_server.setConnectionStateFactory(factory);
_server.setOnConnectionCallback(
[this](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ix::ConnectionState> connectionState)
{
std::shared_ptr<ix::ConnectionState> connectionState) {
auto state = std::dynamic_pointer_cast<SnakeConnectionState>(connectionState);
webSocket->setOnMessageCallback(
[this, webSocket, state](const ix::WebSocketMessagePtr& msg)
{
[this, webSocket, state](const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
std::cerr << "New connection" << std::endl;
@ -84,8 +81,8 @@ namespace snake
else if (msg->type == ix::WebSocketMessageType::Close)
{
std::cerr << "Closed connection"
<< " code " << msg->closeInfo.code
<< " reason " << msg->closeInfo.reason << std::endl;
<< " code " << msg->closeInfo.code << " reason "
<< msg->closeInfo.reason << std::endl;
}
else if (msg->type == ix::WebSocketMessageType::Error)
{
@ -105,10 +102,8 @@ namespace snake
std::cerr << "Received " << msg->wireSize << " bytes" << std::endl;
processCobraMessage(state, webSocket, _appConfig, msg->str);
}
}
);
}
);
});
});
auto res = _server.listen();
if (!res.first)
@ -133,4 +128,4 @@ namespace snake
{
_server.stop();
}
}
} // namespace snake

108
ws/ws.cpp
View File

@ -9,27 +9,22 @@
//
#include "ws.h"
#include <string>
#include <sstream>
#include <iostream>
#include <fstream>
#include <cli11/CLI11.hpp>
#include <spdlog/spdlog.h>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXNetSystem.h>
#include <fstream>
#include <iostream>
#include <ixcore/utils/IXCoreLogger.h>
#include <ixwebsocket/IXNetSystem.h>
#include <ixwebsocket/IXSocket.h>
#include <spdlog/spdlog.h>
#include <sstream>
#include <string>
int main(int argc, char** argv)
{
ix::initNetSystem();
ix::IXCoreLogger::LogFunc logFunc = [](const char* msg)
{
spdlog::info(msg);
};
ix::IXCoreLogger::LogFunc logFunc = [](const char* msg) { spdlog::info(msg); };
ix::IXCoreLogger::setLogFunction(logFunc);
// Display command.
@ -94,12 +89,15 @@ int main(int argc, char** argv)
CLI::App* sendApp = app.add_subcommand("send", "Send a file");
sendApp->add_option("url", url, "Connection url")->required();
sendApp->add_option("path", path, "Path to the file to send")
->required()->check(CLI::ExistingPath);
->required()
->check(CLI::ExistingPath);
sendApp->add_option("--pidfile", pidfile, "Pid file");
CLI::App* receiveApp = app.add_subcommand("receive", "Receive a file");
receiveApp->add_option("url", url, "Connection url")->required();
receiveApp->add_option("--delay", delayMs, "Delay (ms) to wait after receiving a fragment"
receiveApp->add_option("--delay",
delayMs,
"Delay (ms) to wait after receiving a fragment"
" to artificially slow down the receiver");
receiveApp->add_option("--pidfile", pidfile, "Pid file");
@ -114,7 +112,9 @@ int main(int argc, char** argv)
connectApp->add_flag("-d", disableAutomaticReconnection, "Disable Automatic Reconnection");
connectApp->add_flag("-x", disablePerMessageDeflate, "Disable per message deflate");
connectApp->add_flag("-b", binaryMode, "Send in binary mode");
connectApp->add_option("--max_wait", maxWaitBetweenReconnectionRetries, "Max Wait Time between reconnection retries");
connectApp->add_option("--max_wait",
maxWaitBetweenReconnectionRetries,
"Max Wait Time between reconnection retries");
CLI::App* chatApp = app.add_subcommand("chat", "Group chat");
chatApp->add_option("url", url, "Connection url")->required();
@ -181,9 +181,11 @@ int main(int argc, char** argv)
cobraPublish->add_option("channel", channel, "Channel")->required();
cobraPublish->add_option("--pidfile", pidfile, "Pid file");
cobraPublish->add_option("path", path, "Path to the file to send")
->required()->check(CLI::ExistingPath);
->required()
->check(CLI::ExistingPath);
CLI::App* cobraMetricsPublish = app.add_subcommand("cobra_metrics_publish", "Cobra metrics publisher");
CLI::App* cobraMetricsPublish =
app.add_subcommand("cobra_metrics_publish", "Cobra metrics publisher");
cobraMetricsPublish->add_option("--appkey", appkey, "Appkey");
cobraMetricsPublish->add_option("--endpoint", endpoint, "Endpoint");
cobraMetricsPublish->add_option("--rolename", rolename, "Role name");
@ -191,7 +193,8 @@ int main(int argc, char** argv)
cobraMetricsPublish->add_option("channel", channel, "Channel")->required();
cobraMetricsPublish->add_option("--pidfile", pidfile, "Pid file");
cobraMetricsPublish->add_option("path", path, "Path to the file to send")
->required()->check(CLI::ExistingPath);
->required()
->check(CLI::ExistingPath);
cobraMetricsPublish->add_flag("--stress", stress, "Stress mode");
CLI::App* cobra2statsd = app.add_subcommand("cobra_to_statsd", "Cobra to statsd");
@ -269,8 +272,11 @@ int main(int argc, char** argv)
}
else if (app.got_subcommand("connect"))
{
ret = ix::ws_connect_main(url, headers, disableAutomaticReconnection,
disablePerMessageDeflate, binaryMode,
ret = ix::ws_connect_main(url,
headers,
disableAutomaticReconnection,
disablePerMessageDeflate,
binaryMode,
maxWaitBetweenReconnectionRetries);
}
else if (app.got_subcommand("chat"))
@ -291,15 +297,22 @@ int main(int argc, char** argv)
}
else if (app.got_subcommand("curl"))
{
ret = ix::ws_http_client_main(url, headers, data, headersOnly,
connectTimeOut, transferTimeout,
followRedirects, maxRedirects, verbose,
save, output, compress);
ret = ix::ws_http_client_main(url,
headers,
data,
headersOnly,
connectTimeOut,
transferTimeout,
followRedirects,
maxRedirects,
verbose,
save,
output,
compress);
}
else if (app.got_subcommand("redis_publish"))
{
ret = ix::ws_redis_publish_main(hostname, redisPort, password,
channel, message, count);
ret = ix::ws_redis_publish_main(hostname, redisPort, password, channel, message, count);
}
else if (app.got_subcommand("redis_subscribe"))
{
@ -307,42 +320,41 @@ int main(int argc, char** argv)
}
else if (app.got_subcommand("cobra_subscribe"))
{
ret = ix::ws_cobra_subscribe_main(appkey, endpoint,
rolename, rolesecret,
channel, filter, quiet);
ret = ix::ws_cobra_subscribe_main(
appkey, endpoint, rolename, rolesecret, channel, filter, quiet);
}
else if (app.got_subcommand("cobra_publish"))
{
ret = ix::ws_cobra_publish_main(appkey, endpoint,
rolename, rolesecret,
channel, path);
ret = ix::ws_cobra_publish_main(appkey, endpoint, rolename, rolesecret, channel, path);
}
else if (app.got_subcommand("cobra_metrics_publish"))
{
ret = ix::ws_cobra_metrics_publish_main(appkey, endpoint,
rolename, rolesecret,
channel, path, stress);
ret = ix::ws_cobra_metrics_publish_main(
appkey, endpoint, rolename, rolesecret, channel, path, stress);
}
else if (app.got_subcommand("cobra_to_statsd"))
{
ret = ix::ws_cobra_to_statsd_main(appkey, endpoint,
rolename, rolesecret,
channel, filter, hostname, statsdPort,
prefix, fields, verbose);
ret = ix::ws_cobra_to_statsd_main(appkey,
endpoint,
rolename,
rolesecret,
channel,
filter,
hostname,
statsdPort,
prefix,
fields,
verbose);
}
else if (app.got_subcommand("cobra_to_sentry"))
{
ret = ix::ws_cobra_to_sentry_main(appkey, endpoint,
rolename, rolesecret,
channel, filter, dsn,
verbose, strict, jobs);
ret = ix::ws_cobra_to_sentry_main(
appkey, endpoint, rolename, rolesecret, channel, filter, dsn, verbose, strict, jobs);
}
else if (app.got_subcommand("snake"))
{
ret = ix::ws_snake_main(port, hostname,
redisHosts, redisPort,
redisPassword, verbose,
appsConfigPath);
ret = ix::ws_snake_main(
port, hostname, redisHosts, redisPort, redisPassword, verbose, appsConfigPath);
}
else if (app.got_subcommand("httpd"))
{

View File

@ -21,7 +21,8 @@
//
//
// 2 Run the test server (using docker)
// docker run -it --rm -v "${PWD}/config:/config" -v "${PWD}/reports:/reports" -p 9001:9001 --name fuzzingserver crossbario/autobahn-testsuite
// docker run -it --rm -v "${PWD}/config:/config" -v "${PWD}/reports:/reports" -p 9001:9001 --name
// fuzzingserver crossbario/autobahn-testsuite
//
// 3. Run this command
// ws autobahn -q --url ws://localhost:9001
@ -29,15 +30,14 @@
// 4. A HTML report will be generated, you can inspect it to see if you are compliant or not
//
#include <iostream>
#include <sstream>
#include <atomic>
#include <mutex>
#include <condition_variable>
#include <ixwebsocket/IXWebSocket.h>
#include <iostream>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXWebSocket.h>
#include <mutex>
#include <spdlog/spdlog.h>
#include <sstream>
namespace
@ -53,7 +53,7 @@ namespace
return str.substr(0, n) + "...";
}
}
}
} // namespace
namespace ix
{
@ -75,9 +75,9 @@ namespace ix
std::condition_variable _condition;
};
AutobahnTestCase::AutobahnTestCase(const std::string& url, bool quiet) :
_url(url),
_quiet(quiet)
AutobahnTestCase::AutobahnTestCase(const std::string& url, bool quiet)
: _url(url)
, _quiet(quiet)
{
_webSocket.disableAutomaticReconnection();
@ -102,9 +102,7 @@ namespace ix
std::stringstream ss;
log(std::string("Connecting to url: ") + _url);
_webSocket.setOnMessageCallback(
[this](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const ix::WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -128,9 +126,7 @@ namespace ix
{
ss << "Received " << msg->wireSize << " bytes" << std::endl;
ss << "autobahn: received message: "
<< truncate(msg->str, 40)
<< std::endl;
ss << "autobahn: received message: " << truncate(msg->str, 40) << std::endl;
_webSocket.send(msg->str, msg->binary);
}
@ -184,9 +180,7 @@ namespace ix
std::atomic<bool> success(true);
std::condition_variable condition;
webSocket.setOnMessageCallback(
[&condition, &success](const ix::WebSocketMessagePtr& msg)
{
webSocket.setOnMessageCallback([&condition, &success](const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Close)
{
std::cerr << "Report generated" << std::endl;
@ -203,8 +197,7 @@ namespace ix
success = false;
}
}
);
});
webSocket.start();
std::mutex mutex;
@ -231,9 +224,7 @@ namespace ix
int count = -1;
std::condition_variable condition;
webSocket.setOnMessageCallback(
[&condition, &count](const ix::WebSocketMessagePtr& msg)
{
webSocket.setOnMessageCallback([&condition, &count](const ix::WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Close)
{
condition.notify_one();
@ -256,8 +247,7 @@ namespace ix
ss << msg->str;
ss >> count;
}
}
);
});
webSocket.start();
std::mutex mutex;
@ -296,10 +286,7 @@ namespace ix
int caseNumber = i;
std::stringstream ss;
ss << url
<< "/runCase?case="
<< caseNumber
<< "&agent=ixwebsocket";
ss << url << "/runCase?case=" << caseNumber << "&agent=ixwebsocket";
std::string url(ss.str());
@ -309,4 +296,4 @@ namespace ix
return generateReport(url) ? 0 : 1;
}
}
} // namespace ix

View File

@ -5,8 +5,8 @@
*/
#include <iostream>
#include <sstream>
#include <ixwebsocket/IXWebSocketServer.h>
#include <sstream>
namespace ix
{
@ -16,13 +16,10 @@ namespace ix
ix::WebSocketServer server(port, hostname);
server.setOnConnectionCallback(
[&server](std::shared_ptr<WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
webSocket->setOnMessageCallback(
[webSocket, connectionState, &server](const WebSocketMessagePtr& msg)
{
server.setOnConnectionCallback([&server](std::shared_ptr<WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback([webSocket, connectionState, &server](
const WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
std::cerr << "New connection" << std::endl;
@ -37,8 +34,8 @@ namespace ix
else if (msg->type == ix::WebSocketMessageType::Close)
{
std::cerr << "Closed connection"
<< " code " << msg->closeInfo.code
<< " reason " << msg->closeInfo.reason << std::endl;
<< " code " << msg->closeInfo.code << " reason "
<< msg->closeInfo.reason << std::endl;
}
else if (msg->type == ix::WebSocketMessageType::Error)
{
@ -61,19 +58,16 @@ namespace ix
{
if (client != webSocket)
{
client->send(msg->str,
msg->binary,
[](int current, int total) -> bool
{
std::cerr << "Step " << current
<< " out of " << total << std::endl;
client->send(msg->str, msg->binary, [](int current, int total) -> bool {
std::cerr << "Step " << current << " out of " << total << std::endl;
return true;
});
do
{
size_t bufferedAmount = client->bufferedAmount();
std::cerr << bufferedAmount << " bytes left to be sent" << std::endl;
std::cerr << bufferedAmount << " bytes left to be sent"
<< std::endl;
std::chrono::duration<double, std::milli> duration(10);
std::this_thread::sleep_for(duration);
@ -81,10 +75,8 @@ namespace ix
}
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -98,4 +90,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -9,13 +9,12 @@
// Broadcast server can be ran with `ws broadcast_server`
//
#include <iostream>
#include <sstream>
#include <queue>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXSocket.h>
#include "nlohmann/json.hpp"
#include <iostream>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXWebSocket.h>
#include <queue>
#include <sstream>
// for convenience
using json = nlohmann::json;
@ -25,8 +24,7 @@ namespace ix
class WebSocketChat
{
public:
WebSocketChat(const std::string& url,
const std::string& user);
WebSocketChat(const std::string& url, const std::string& user);
void subscribe(const std::string& channel);
void start();
@ -48,10 +46,9 @@ namespace ix
void log(const std::string& msg);
};
WebSocketChat::WebSocketChat(const std::string& url,
const std::string& user) :
_url(url),
_user(user)
WebSocketChat::WebSocketChat(const std::string& url, const std::string& user)
: _url(url)
, _user(user)
{
;
}
@ -83,9 +80,7 @@ namespace ix
std::stringstream ss;
log(std::string("Connecting to url: ") + _url);
_webSocket.setOnMessageCallback(
[this](const WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -97,18 +92,13 @@ namespace ix
std::cout << it.first << ": " << it.second << std::endl;
}
ss << "ws chat: user "
<< _user
<< " Connected !";
ss << "ws chat: user " << _user << " Connected !";
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Close)
{
ss << "ws chat: user "
<< _user
<< " disconnected !"
<< " code " << msg->closeInfo.code
<< " reason " << msg->closeInfo.reason;
ss << "ws chat: user " << _user << " disconnected !"
<< " code " << msg->closeInfo.code << " reason " << msg->closeInfo.reason;
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Message)
@ -122,8 +112,8 @@ namespace ix
_receivedQueue.push(result.second);
ss << std::endl
<< result.first << "(" << msg->wireSize << " bytes)" << " > " << result.second
<< std::endl
<< result.first << "(" << msg->wireSize << " bytes)"
<< " > " << result.second << std::endl
<< _user << " > ";
log(ss.str());
}
@ -170,8 +160,7 @@ namespace ix
_webSocket.sendText(encodeMessage(text));
}
int ws_chat_main(const std::string& url,
const std::string& user)
int ws_chat_main(const std::string& url, const std::string& user)
{
std::cout << "Type Ctrl-D to exit prompt..." << std::endl;
WebSocketChat webSocketChat(url, user);
@ -196,4 +185,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,15 +4,15 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <fstream>
#include <sstream>
#include <chrono>
#include <thread>
#include <atomic>
#include <jsoncpp/json/json.h>
#include <chrono>
#include <fstream>
#include <iostream>
#include <ixcobra/IXCobraMetricsPublisher.h>
#include <jsoncpp/json/json.h>
#include <spdlog/spdlog.h>
#include <sstream>
#include <thread>
namespace ix
{
@ -27,25 +27,23 @@ namespace ix
std::atomic<int> sentMessages(0);
std::atomic<int> ackedMessages(0);
CobraConnection::setPublishTrackerCallback(
[&sentMessages, &ackedMessages](bool sent, bool acked)
{
[&sentMessages, &ackedMessages](bool sent, bool acked) {
if (sent) sentMessages++;
if (acked) ackedMessages++;
}
);
});
CobraMetricsPublisher cobraMetricsPublisher;
cobraMetricsPublisher.enable(true);
bool enablePerMessageDeflate = true;
cobraMetricsPublisher.configure(appkey, endpoint, channel,
rolename, rolesecret, enablePerMessageDeflate);
cobraMetricsPublisher.configure(
appkey, endpoint, channel, rolename, rolesecret, enablePerMessageDeflate);
while (!cobraMetricsPublisher.isAuthenticated()) ;
while (!cobraMetricsPublisher.isAuthenticated())
;
std::ifstream f(path);
std::string str((std::istreambuf_iterator<char>(f)),
std::istreambuf_iterator<char>());
std::string str((std::istreambuf_iterator<char>(f)), std::istreambuf_iterator<char>());
Json::Value data;
Json::Reader reader;
@ -70,7 +68,8 @@ namespace ix
cobraMetricsPublisher.resume();
// FIXME: investigate why without this check we trigger a lock
while (!cobraMetricsPublisher.isAuthenticated()) ;
while (!cobraMetricsPublisher.isAuthenticated())
;
}
}
@ -83,5 +82,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,17 +4,17 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <fstream>
#include <sstream>
#include <chrono>
#include <thread>
#include <atomic>
#include <mutex>
#include <chrono>
#include <condition_variable>
#include <jsoncpp/json/json.h>
#include <fstream>
#include <iostream>
#include <ixcobra/IXCobraMetricsPublisher.h>
#include <jsoncpp/json/json.h>
#include <mutex>
#include <spdlog/spdlog.h>
#include <sstream>
#include <thread>
namespace ix
{
@ -26,8 +26,7 @@ namespace ix
const std::string& path)
{
std::ifstream f(path);
std::string str((std::istreambuf_iterator<char>(f)),
std::istreambuf_iterator<char>());
std::string str((std::istreambuf_iterator<char>(f)), std::istreambuf_iterator<char>());
Json::Value data;
Json::Reader reader;
@ -38,9 +37,8 @@ namespace ix
}
ix::CobraConnection conn;
conn.configure(appkey, endpoint,
rolename, rolesecret,
ix::WebSocketPerMessageDeflateOptions(true));
conn.configure(
appkey, endpoint, rolename, rolesecret, ix::WebSocketPerMessageDeflateOptions(true));
conn.connect();
// Display incoming messages
@ -48,14 +46,12 @@ namespace ix
std::atomic<bool> messageAcked(false);
std::condition_variable condition;
conn.setEventCallback(
[&conn, &channel, &data, &authenticated, &messageAcked, &condition]
(ix::CobraConnectionEventType eventType,
conn.setEventCallback([&conn, &channel, &data, &authenticated, &messageAcked, &condition](
ix::CobraConnectionEventType eventType,
const std::string& errMsg,
const ix::WebSocketHttpHeaders& headers,
const std::string& subscriptionId,
CobraConnection::MsgId msgId)
{
CobraConnection::MsgId msgId) {
if (eventType == ix::CobraConnection_EventType_Open)
{
spdlog::info("Publisher connected");
@ -95,12 +91,13 @@ namespace ix
messageAcked = true;
condition.notify_one();
}
}
);
});
while (!authenticated) ;
while (!messageAcked) ;
while (!authenticated)
;
while (!messageAcked)
;
return 0;
}
}
} // namespace ix

View File

@ -4,14 +4,13 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <sstream>
#include <chrono>
#include <thread>
#include <atomic>
#include <chrono>
#include <iostream>
#include <ixcobra/IXCobraConnection.h>
#include <spdlog/spdlog.h>
#include <sstream>
#include <thread>
namespace ix
{
@ -24,9 +23,8 @@ namespace ix
bool quiet)
{
ix::CobraConnection conn;
conn.configure(appkey, endpoint,
rolename, rolesecret,
ix::WebSocketPerMessageDeflateOptions(true));
conn.configure(
appkey, endpoint, rolename, rolesecret, ix::WebSocketPerMessageDeflateOptions(true));
conn.connect();
Json::FastWriter jsonWriter;
@ -35,13 +33,11 @@ namespace ix
std::atomic<int> msgPerSeconds(0);
std::atomic<int> msgCount(0);
auto timer = [&msgPerSeconds, &msgCount]
{
auto timer = [&msgPerSeconds, &msgCount] {
while (true)
{
std::cout << "#messages " << msgCount << " "
<< "msg/s " << msgPerSeconds
<< std::endl;
<< "msg/s " << msgPerSeconds << std::endl;
msgPerSeconds = 0;
auto duration = std::chrono::seconds(1);
@ -52,13 +48,12 @@ namespace ix
std::thread t(timer);
conn.setEventCallback(
[&conn, &channel, &jsonWriter, &filter, &msgCount, &msgPerSeconds, &quiet]
(ix::CobraConnectionEventType eventType,
[&conn, &channel, &jsonWriter, &filter, &msgCount, &msgPerSeconds, &quiet](
ix::CobraConnectionEventType eventType,
const std::string& errMsg,
const ix::WebSocketHttpHeaders& headers,
const std::string& subscriptionId,
CobraConnection::MsgId msgId)
{
CobraConnection::MsgId msgId) {
if (eventType == ix::CobraConnection_EventType_Open)
{
spdlog::info("Subscriber connected");
@ -71,10 +66,10 @@ namespace ix
else if (eventType == ix::CobraConnection_EventType_Authenticated)
{
spdlog::info("Subscriber authenticated");
conn.subscribe(channel, filter,
[&jsonWriter, &quiet,
&msgPerSeconds, &msgCount](const Json::Value& msg)
{
conn.subscribe(
channel,
filter,
[&jsonWriter, &quiet, &msgPerSeconds, &msgCount](const Json::Value& msg) {
if (!quiet)
{
std::cout << jsonWriter.write(msg) << std::endl;
@ -100,8 +95,7 @@ namespace ix
{
spdlog::error("Published message hacked: {}", msgId);
}
}
);
});
while (true)
{
@ -111,4 +105,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,19 +4,18 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <sstream>
#include <chrono>
#include <thread>
#include <atomic>
#include <vector>
#include <queue>
#include <mutex>
#include <condition_variable>
#include <ixcobra/IXCobraConnection.h>
#include <spdlog/spdlog.h>
#include "IXSentryClient.h"
#include <atomic>
#include <chrono>
#include <condition_variable>
#include <iostream>
#include <ixcobra/IXCobraConnection.h>
#include <mutex>
#include <queue>
#include <spdlog/spdlog.h>
#include <sstream>
#include <thread>
#include <vector>
namespace ix
{
@ -32,9 +31,8 @@ namespace ix
int jobs)
{
ix::CobraConnection conn;
conn.configure(appkey, endpoint,
rolename, rolesecret,
ix::WebSocketPerMessageDeflateOptions(true));
conn.configure(
appkey, endpoint, rolename, rolesecret, ix::WebSocketPerMessageDeflateOptions(true));
conn.connect();
Json::FastWriter jsonWriter;
@ -48,10 +46,15 @@ namespace ix
std::condition_variable progressCondition;
std::queue<Json::Value> queue;
auto sentrySender = [&condition, &progressCondition, &conditionVariableMutex,
&queue, verbose, &errorSending, &sentCount,
&stop, &dsn]
{
auto sentrySender = [&condition,
&progressCondition,
&conditionVariableMutex,
&queue,
verbose,
&errorSending,
&sentCount,
&stop,
&dsn] {
SentryClient sentryClient(dsn);
while (true)
@ -94,17 +97,21 @@ namespace ix
pool.push_back(std::thread(sentrySender));
}
conn.setEventCallback(
[&conn, &channel, &filter, &jsonWriter,
verbose, &receivedCount, &sentCount,
&condition, &conditionVariableMutex,
&progressCondition, &queue]
(ix::CobraConnectionEventType eventType,
conn.setEventCallback([&conn,
&channel,
&filter,
&jsonWriter,
verbose,
&receivedCount,
&sentCount,
&condition,
&conditionVariableMutex,
&progressCondition,
&queue](ix::CobraConnectionEventType eventType,
const std::string& errMsg,
const ix::WebSocketHttpHeaders& headers,
const std::string& subscriptionId,
CobraConnection::MsgId msgId)
{
CobraConnection::MsgId msgId) {
if (eventType == ix::CobraConnection_EventType_Open)
{
spdlog::info("Subscriber connected");
@ -121,13 +128,16 @@ namespace ix
else if (eventType == ix::CobraConnection_EventType_Authenticated)
{
std::cerr << "Subscriber authenticated" << std::endl;
conn.subscribe(channel, filter,
[&jsonWriter, verbose,
&sentCount, &receivedCount,
&condition, &conditionVariableMutex,
&progressCondition, &queue]
(const Json::Value& msg)
{
conn.subscribe(channel,
filter,
[&jsonWriter,
verbose,
&sentCount,
&receivedCount,
&condition,
&conditionVariableMutex,
&progressCondition,
&queue](const Json::Value& msg) {
if (verbose)
{
spdlog::info(jsonWriter.write(msg));
@ -136,8 +146,7 @@ namespace ix
// If we cannot send to sentry fast enough, drop the message
const uint64_t scaleFactor = 2;
if (sentCount != 0 &&
receivedCount != 0 &&
if (sentCount != 0 && receivedCount != 0 &&
(sentCount * scaleFactor < receivedCount))
{
spdlog::warn("message dropped: sending is backlogged !");
@ -174,8 +183,7 @@ namespace ix
{
spdlog::error("Published message hacked: {}", msgId);
}
}
);
});
std::mutex progressConditionVariableMutex;
while (true)
@ -200,4 +208,4 @@ namespace ix
return (strict && errorSending) ? 1 : 0;
}
}
} // namespace ix

View File

@ -4,15 +4,14 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <sstream>
#include <chrono>
#include <thread>
#include <atomic>
#include <vector>
#include <chrono>
#include <iostream>
#include <ixcobra/IXCobraConnection.h>
#include <spdlog/spdlog.h>
#include <sstream>
#include <thread>
#include <vector>
#ifndef _WIN32
#include <statsd_client.h>
@ -41,8 +40,7 @@ namespace ix
// Extract an attribute from a Json Value.
// extractAttr("foo.bar", {"foo": {"bar": "baz"}}) => baz
//
std::string extractAttr(const std::string& attr,
const Json::Value& jsonValue)
std::string extractAttr(const std::string& attr, const Json::Value& jsonValue)
{
// Split by .
std::string token;
@ -71,9 +69,8 @@ namespace ix
bool verbose)
{
ix::CobraConnection conn;
conn.configure(appkey, endpoint,
rolename, rolesecret,
ix::WebSocketPerMessageDeflateOptions(true));
conn.configure(
appkey, endpoint, rolename, rolesecret, ix::WebSocketPerMessageDeflateOptions(true));
conn.connect();
auto tokens = parseFields(fields);
@ -90,14 +87,19 @@ namespace ix
Json::FastWriter jsonWriter;
uint64_t msgCount = 0;
conn.setEventCallback(
[&conn, &channel, &filter, &jsonWriter, &statsdClient, verbose, &tokens, &prefix, &msgCount]
(ix::CobraConnectionEventType eventType,
conn.setEventCallback([&conn,
&channel,
&filter,
&jsonWriter,
&statsdClient,
verbose,
&tokens,
&prefix,
&msgCount](ix::CobraConnectionEventType eventType,
const std::string& errMsg,
const ix::WebSocketHttpHeaders& headers,
const std::string& subscriptionId,
CobraConnection::MsgId msgId)
{
CobraConnection::MsgId msgId) {
if (eventType == ix::CobraConnection_EventType_Open)
{
spdlog::info("Subscriber connected");
@ -114,11 +116,10 @@ namespace ix
else if (eventType == ix::CobraConnection_EventType_Authenticated)
{
spdlog::info("Subscriber authenticated");
conn.subscribe(channel, filter,
[&jsonWriter, &statsdClient,
verbose, &tokens, &prefix, &msgCount]
(const Json::Value& msg)
{
conn.subscribe(channel,
filter,
[&jsonWriter, &statsdClient, verbose, &tokens, &prefix, &msgCount](
const Json::Value& msg) {
if (verbose)
{
spdlog::info(jsonWriter.write(msg));
@ -154,8 +155,7 @@ namespace ix
{
spdlog::error("Published message hacked: {}", msgId);
}
}
);
});
while (true)
{
@ -165,4 +165,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,12 +4,11 @@
* Copyright (c) 2017-2018 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <sstream>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXSocket.h>
#include "linenoise.hpp"
#include <iostream>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXWebSocket.h>
#include <sstream>
namespace ix
@ -46,10 +45,10 @@ namespace ix
bool disableAutomaticReconnection,
bool disablePerMessageDeflate,
bool binaryMode,
uint32_t maxWaitBetweenReconnectionRetries) :
_url(url),
_disablePerMessageDeflate(disablePerMessageDeflate),
_binaryMode(binaryMode)
uint32_t maxWaitBetweenReconnectionRetries)
: _url(url)
, _disablePerMessageDeflate(disablePerMessageDeflate)
, _binaryMode(binaryMode)
{
if (disableAutomaticReconnection)
{
@ -114,9 +113,7 @@ namespace ix
std::stringstream ss;
log(std::string("Connecting to url: ") + _url);
_webSocket.setOnMessageCallback(
[this](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const ix::WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -139,8 +136,7 @@ namespace ix
{
std::cerr << "Received " << msg->wireSize << " bytes" << std::endl;
ss << "ws_connect: received message: "
<< msg->str;
ss << "ws_connect: received message: " << msg->str;
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Error)
@ -237,5 +233,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -5,8 +5,8 @@
*/
#include <iostream>
#include <sstream>
#include <ixwebsocket/IXWebSocketServer.h>
#include <sstream>
namespace ix
{
@ -18,11 +18,9 @@ namespace ix
server.setOnConnectionCallback(
[greetings](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback(
[webSocket, connectionState, greetings](const WebSocketMessagePtr& msg)
{
[webSocket, connectionState, greetings](const WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
std::cerr << "New connection" << std::endl;
@ -42,8 +40,8 @@ namespace ix
else if (msg->type == ix::WebSocketMessageType::Close)
{
std::cerr << "Closed connection"
<< " code " << msg->closeInfo.code
<< " reason " << msg->closeInfo.reason << std::endl;
<< " code " << msg->closeInfo.code << " reason "
<< msg->closeInfo.reason << std::endl;
}
else if (msg->type == ix::WebSocketMessageType::Error)
{
@ -56,15 +54,11 @@ namespace ix
}
else if (msg->type == ix::WebSocketMessageType::Message)
{
std::cerr << "Received "
<< msg->wireSize << " bytes"
<< std::endl;
std::cerr << "Received " << msg->wireSize << " bytes" << std::endl;
webSocket->send(msg->str, msg->binary);
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -78,4 +72,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,11 +4,11 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <sstream>
#include <fstream>
#include <iostream>
#include <ixwebsocket/IXHttpClient.h>
#include <ixwebsocket/IXWebSocketHttpHeaders.h>
#include <sstream>
namespace ix
{
@ -104,14 +104,10 @@ namespace ix
args->maxRedirects = maxRedirects;
args->verbose = verbose;
args->compress = compress;
args->logger = [](const std::string& msg)
{
std::cout << msg;
};
args->onProgressCallback = [](int current, int total) -> bool
{
std::cerr << "\r" << "Downloaded "
<< current << " bytes out of " << total;
args->logger = [](const std::string& msg) { std::cout << msg; };
args->onProgressCallback = [](int current, int total) -> bool {
std::cerr << "\r"
<< "Downloaded " << current << " bytes out of " << total;
return true;
};
@ -173,11 +169,12 @@ namespace ix
{
std::cerr << "Binary output can mess up your terminal." << std::endl;
std::cerr << "Use the -O flag to save the file to disk." << std::endl;
std::cerr << "You can also use the --output option to specify a filename." << std::endl;
std::cerr << "You can also use the --output option to specify a filename."
<< std::endl;
}
}
}
return 0;
}
}
} // namespace ix

View File

@ -4,12 +4,12 @@
* Copyright (c) 2018 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <vector>
#include <fstream>
#include <sstream>
#include <iostream>
#include <ixwebsocket/IXHttpServer.h>
#include <spdlog/spdlog.h>
#include <sstream>
#include <vector>
namespace ix
{
@ -31,4 +31,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -5,9 +5,9 @@
*/
#include <iostream>
#include <sstream>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXWebSocket.h>
#include <sstream>
namespace ix
{
@ -30,8 +30,8 @@ namespace ix
void log(const std::string& msg);
};
WebSocketPingPong::WebSocketPingPong(const std::string& url) :
_url(url)
WebSocketPingPong::WebSocketPingPong(const std::string& url)
: _url(url)
{
;
}
@ -53,9 +53,7 @@ namespace ix
std::stringstream ss;
log(std::string("Connecting to url: ") + _url);
_webSocket.setOnMessageCallback(
[this](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const ix::WebSocketMessagePtr& msg) {
std::cerr << "Received " << msg->wireSize << " bytes" << std::endl;
std::stringstream ss;
@ -73,27 +71,23 @@ namespace ix
else if (msg->type == ix::WebSocketMessageType::Close)
{
ss << "ping_pong: disconnected:"
<< " code " << msg->closeInfo.code
<< " reason " << msg->closeInfo.reason
<< " code " << msg->closeInfo.code << " reason " << msg->closeInfo.reason
<< msg->str;
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Message)
{
ss << "ping_pong: received message: "
<< msg->str;
ss << "ping_pong: received message: " << msg->str;
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Ping)
{
ss << "ping_pong: received ping message: "
<< msg->str;
ss << "ping_pong: received ping message: " << msg->str;
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Pong)
{
ss << "ping_pong: received pong message: "
<< msg->str;
ss << "ping_pong: received pong message: " << msg->str;
log(ss.str());
}
else if (msg->type == ix::WebSocketMessageType::Error)
@ -118,7 +112,8 @@ namespace ix
{
if (!_webSocket.ping(text).success)
{
std::cerr << "Failed to send ping message. Message too long (> 125 bytes) or endpoint is disconnected"
std::cerr << "Failed to send ping message. Message too long (> 125 bytes) or endpoint "
"is disconnected"
<< std::endl;
}
}
@ -160,4 +155,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,19 +4,19 @@
* Copyright (c) 2017-2018 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <fstream>
#include <sstream>
#include <vector>
#include <condition_variable>
#include <mutex>
#include <chrono>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXSocket.h>
#include <ixcrypto/IXUuid.h>
#include <condition_variable>
#include <fstream>
#include <iostream>
#include <ixcrypto/IXBase64.h>
#include <ixcrypto/IXHash.h>
#include <ixcrypto/IXUuid.h>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXWebSocket.h>
#include <msgpack11/msgpack11.hpp>
#include <mutex>
#include <sstream>
#include <vector>
using msgpack11::MsgPack;
@ -25,9 +25,7 @@ namespace ix
class WebSocketReceiver
{
public:
WebSocketReceiver(const std::string& _url,
bool enablePerMessageDeflate,
int delayMs);
WebSocketReceiver(const std::string& _url, bool enablePerMessageDeflate, int delayMs);
void subscribe(const std::string& channel);
void start();
@ -55,11 +53,11 @@ namespace ix
WebSocketReceiver::WebSocketReceiver(const std::string& url,
bool enablePerMessageDeflate,
int delayMs) :
_url(url),
_enablePerMessageDeflate(enablePerMessageDeflate),
_delayMs(delayMs),
_receivedFragmentCounter(0)
int delayMs)
: _url(url)
, _enablePerMessageDeflate(enablePerMessageDeflate)
, _delayMs(delayMs)
, _receivedFragmentCounter(0)
{
;
}
@ -107,8 +105,7 @@ namespace ix
}
}
void WebSocketReceiver::handleError(const std::string& errMsg,
const std::string& id)
void WebSocketReceiver::handleError(const std::string& errMsg, const std::string& id)
{
std::map<MsgPack, MsgPack> pdu;
pdu["kind"] = "error";
@ -182,9 +179,7 @@ namespace ix
std::stringstream ss;
log(std::string("Connecting to url: ") + _url);
_webSocket.setOnMessageCallback(
[this](const ix::WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const ix::WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -243,9 +238,7 @@ namespace ix
_webSocket.start();
}
void wsReceive(const std::string& url,
bool enablePerMessageDeflate,
int delayMs)
void wsReceive(const std::string& url, bool enablePerMessageDeflate, int delayMs)
{
WebSocketReceiver webSocketReceiver(url, enablePerMessageDeflate, delayMs);
webSocketReceiver.start();
@ -261,11 +254,9 @@ namespace ix
webSocketReceiver.stop();
}
int ws_receive_main(const std::string& url,
bool enablePerMessageDeflate,
int delayMs)
int ws_receive_main(const std::string& url, bool enablePerMessageDeflate, int delayMs)
{
wsReceive(url, enablePerMessageDeflate, delayMs);
return 0;
}
}
} // namespace ix

View File

@ -4,9 +4,9 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include "IXRedisClient.h"
#include <iostream>
#include <sstream>
#include "IXRedisClient.h"
namespace ix
{
@ -41,8 +41,7 @@ namespace ix
{
if (!redisClient.publish(channel, message, errMsg))
{
std::cerr << "Error publishing to channel " << channel
<< "error: " << errMsg
std::cerr << "Error publishing to channel " << channel << "error: " << errMsg
<< std::endl;
return 1;
}
@ -50,4 +49,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,12 +4,12 @@
* Copyright (c) 2019 Machine Zone, Inc. All rights reserved.
*/
#include "IXRedisClient.h"
#include <atomic>
#include <chrono>
#include <iostream>
#include <sstream>
#include <chrono>
#include <thread>
#include <atomic>
#include "IXRedisClient.h"
namespace ix
{
@ -41,9 +41,7 @@ namespace ix
std::atomic<int> msgPerSeconds(0);
std::atomic<int> msgCount(0);
auto callback = [&msgPerSeconds, &msgCount, verbose]
(const std::string& message)
{
auto callback = [&msgPerSeconds, &msgCount, verbose](const std::string& message) {
if (verbose)
{
std::cout << "received: " << message << std::endl;
@ -53,18 +51,15 @@ namespace ix
msgCount++;
};
auto responseCallback = [](const std::string& redisResponse)
{
auto responseCallback = [](const std::string& redisResponse) {
std::cout << "Redis subscribe response: " << redisResponse << std::endl;
};
auto timer = [&msgPerSeconds, &msgCount]
{
auto timer = [&msgPerSeconds, &msgCount] {
while (true)
{
std::cout << "#messages " << msgCount << " "
<< "msg/s " << msgPerSeconds
<< std::endl;
<< "msg/s " << msgPerSeconds << std::endl;
msgPerSeconds = 0;
auto duration = std::chrono::seconds(1);
@ -83,4 +78,4 @@ namespace ix
return 0;
}
}
} // namespace ix

View File

@ -4,19 +4,19 @@
* Copyright (c) 2017-2018 Machine Zone, Inc. All rights reserved.
*/
#include <iostream>
#include <fstream>
#include <sstream>
#include <vector>
#include <condition_variable>
#include <mutex>
#include <chrono>
#include <ixwebsocket/IXWebSocket.h>
#include <ixwebsocket/IXSocket.h>
#include <ixcrypto/IXUuid.h>
#include <condition_variable>
#include <fstream>
#include <iostream>
#include <ixcrypto/IXBase64.h>
#include <ixcrypto/IXHash.h>
#include <ixcrypto/IXUuid.h>
#include <ixwebsocket/IXSocket.h>
#include <ixwebsocket/IXWebSocket.h>
#include <msgpack11/msgpack11.hpp>
#include <mutex>
#include <sstream>
#include <vector>
using msgpack11::MsgPack;
@ -25,8 +25,7 @@ namespace ix
class WebSocketSender
{
public:
WebSocketSender(const std::string& _url,
bool enablePerMessageDeflate);
WebSocketSender(const std::string& _url, bool enablePerMessageDeflate);
void subscribe(const std::string& channel);
void start();
@ -49,10 +48,9 @@ namespace ix
void log(const std::string& msg);
};
WebSocketSender::WebSocketSender(const std::string& url,
bool enablePerMessageDeflate) :
_url(url),
_enablePerMessageDeflate(enablePerMessageDeflate)
WebSocketSender::WebSocketSender(const std::string& url, bool enablePerMessageDeflate)
: _url(url)
, _enablePerMessageDeflate(enablePerMessageDeflate)
{
;
}
@ -111,9 +109,7 @@ namespace ix
std::stringstream ss;
log(std::string("Connecting to url: ") + _url);
_webSocket.setOnMessageCallback(
[this](const WebSocketMessagePtr& msg)
{
_webSocket.setOnMessageCallback([this](const WebSocketMessagePtr& msg) {
std::stringstream ss;
if (msg->type == ix::WebSocketMessageType::Open)
{
@ -177,10 +173,10 @@ namespace ix
class Bench
{
public:
Bench(const std::string& description) :
_description(description),
_start(std::chrono::system_clock::now()),
_reported(false)
Bench(const std::string& description)
: _description(description)
, _start(std::chrono::system_clock::now())
, _reported(false)
{
;
}
@ -199,8 +195,7 @@ namespace ix
auto milliseconds = std::chrono::duration_cast<std::chrono::milliseconds>(now - _start);
_ms = milliseconds.count();
std::cout << _description << " completed in "
<< _ms << "ms" << std::endl;
std::cout << _description << " completed in " << _ms << "ms" << std::endl;
_reported = true;
}
@ -217,8 +212,7 @@ namespace ix
bool _reported;
};
void WebSocketSender::sendMessage(const std::string& filename,
bool throttle)
void WebSocketSender::sendMessage(const std::string& filename, bool throttle)
{
std::vector<uint8_t> content;
{
@ -239,9 +233,7 @@ namespace ix
MsgPack msg(pdu);
Bench bench("Sending file through websocket");
_webSocket.sendBinary(msg.dump(),
[throttle](int current, int total) -> bool
{
_webSocket.sendBinary(msg.dump(), [throttle](int current, int total) -> bool {
std::cout << "ws_send: Step " << current << " out of " << total << std::endl;
if (throttle)
@ -256,8 +248,7 @@ namespace ix
do
{
size_t bufferedAmount = _webSocket.bufferedAmount();
std::cout << "ws_send: " << bufferedAmount
<< " bytes left to be sent" << std::endl;
std::cout << "ws_send: " << bufferedAmount << " bytes left to be sent" << std::endl;
std::chrono::duration<double, std::milli> duration(10);
std::this_thread::sleep_for(duration);
@ -289,8 +280,7 @@ namespace ix
webSocketSender.stop();
}
int ws_send_main(const std::string& url,
const std::string& path)
int ws_send_main(const std::string& url, const std::string& path)
{
bool throttle = false;
bool enablePerMessageDeflate = false;
@ -298,4 +288,4 @@ namespace ix
wsSend(url, path, enablePerMessageDeflate, throttle);
return 0;
}
}
} // namespace ix

View File

@ -5,10 +5,9 @@
*/
#include "IXSnakeServer.h"
#include <fstream>
#include <iostream>
#include <sstream>
#include <fstream>
namespace
{
@ -34,7 +33,7 @@ namespace
auto vec = load(path);
return std::string(vec.begin(), vec.end());
}
}
} // namespace
namespace ix
{
@ -80,4 +79,4 @@ namespace ix
return 0; // should never reach this
}
}
} // namespace ix

View File

@ -5,8 +5,8 @@
*/
#include <iostream>
#include <sstream>
#include <ixwebsocket/IXWebSocketServer.h>
#include <sstream>
namespace ix
{
@ -16,13 +16,10 @@ namespace ix
ix::WebSocketServer server(port, hostname);
server.setOnConnectionCallback(
[&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState)
{
webSocket->setOnMessageCallback(
[webSocket, connectionState, &server](const WebSocketMessagePtr& msg)
{
server.setOnConnectionCallback([&server](std::shared_ptr<ix::WebSocket> webSocket,
std::shared_ptr<ConnectionState> connectionState) {
webSocket->setOnMessageCallback([webSocket, connectionState, &server](
const WebSocketMessagePtr& msg) {
if (msg->type == ix::WebSocketMessageType::Open)
{
std::cerr << "New connection" << std::endl;
@ -37,8 +34,8 @@ namespace ix
else if (msg->type == ix::WebSocketMessageType::Close)
{
std::cerr << "Closed connection"
<< " code " << msg->closeInfo.code
<< " reason " << msg->closeInfo.reason << std::endl;
<< " code " << msg->closeInfo.code << " reason "
<< msg->closeInfo.reason << std::endl;
}
else if (msg->type == ix::WebSocketMessageType::Error)
{
@ -51,8 +48,7 @@ namespace ix
}
else if (msg->type == ix::WebSocketMessageType::Fragment)
{
std::cerr << "Received message fragment "
<< std::endl;
std::cerr << "Received message fragment " << std::endl;
}
else if (msg->type == ix::WebSocketMessageType::Message)
{
@ -61,12 +57,9 @@ namespace ix
{
if (client != webSocket)
{
client->send(msg->str,
msg->binary,
[](int current, int total) -> bool
{
std::cerr << "ws_transfer: Step " << current
<< " out of " << total << std::endl;
client->send(msg->str, msg->binary, [](int current, int total) -> bool {
std::cerr << "ws_transfer: Step " << current << " out of " << total
<< std::endl;
return true;
});
@ -82,10 +75,8 @@ namespace ix
}
}
}
}
);
}
);
});
});
auto res = server.listen();
if (!res.first)
@ -99,4 +90,4 @@ namespace ix
return 0;
}
}
} // namespace ix