jsocketpp 1.0
A cross-platform C++20 socket library.
Loading...
Searching...
No Matches

TCP client connection abstraction (Java-like interface). More...

#include <Socket.hpp>

Public Member Functions

 Socket ()=delete
 Default constructor (deleted) for Socket class.
 Socket (std::string_view host, Port port, std::optional< std::size_t > recvBufferSize=std::nullopt, std::optional< std::size_t > sendBufferSize=std::nullopt, std::optional< std::size_t > internalBufferSize=std::nullopt)
 Creates a new Socket object configured to connect to the specified host and port.
 Socket (const Socket &rhs)=delete
 Copy constructor (deleted) for Socket class.
 Socket (Socket &&rhs) noexcept
 Move constructor that transfers ownership of socket resources.
Socketoperator= (const Socket &rhs)=delete
 Copy assignment operator (deleted) for Socket class.
Socketoperator= (Socket &&rhs) noexcept
 Move assignment operator that transfers socket ownership safely.
 ~Socket () noexcept
 Destructs the Socket object, closing connections and freeing resources.
std::string getRemoteSocketAddress (bool convertIPv4Mapped=true) const
 Get the remote peer's address and port as a formatted string.
void connect (int timeoutMillis=-1) const
 Establishes a TCP connection to the remote host with optional timeout control.
template<typename T>
read ()
 Reads a fixed-size trivially copyable value of type T from the socket.
std::string readExact (std::size_t n) const
 Read exactly n bytes from the socket into a string.
std::string readUntil (char delimiter, std::size_t maxLen=8192, bool includeDelimiter=true) const
 Reads data from the socket until a specified delimiter character.
std::string readLine (const std::size_t maxLen=8192, const bool includeDelimiter=true) const
 Reads a line terminated by '
' from the socket.
std::string readAtMost (std::size_t n) const
 Reads up to n bytes from the socket into a string.
std::size_t readInto (void *buffer, const std::size_t len) const
 Reads available data from the socket into the provided buffer.
std::size_t readIntoExact (void *buffer, const std::size_t len) const
 Reads exactly len bytes into the given buffer (looped recv).
std::string readAtMostWithTimeout (std::size_t n, int timeoutMillis) const
 Performs a best-effort read up to n bytes, with a maximum timeout.
template<typename T>
std::string readPrefixed ()
 Reads a length-prefixed payload using a fixed-size prefix type.
template<typename T>
std::string readPrefixed (const std::size_t maxPayloadLen)
 Reads a length-prefixed message with an upper bound check.
std::string readAvailable () const
 Reads all bytes currently available on the socket without blocking.
std::size_t readIntoAvailable (void *buffer, std::size_t bufferSize) const
 Reads all currently available bytes into the provided buffer without blocking.
std::size_t readv (std::span< BufferView > buffers) const
 Performs a vectorized read into multiple buffers using a single system call.
std::size_t readvAll (std::span< BufferView > buffers) const
 Reads exactly the full contents of all provided buffers.
std::size_t readvAllWithTotalTimeout (std::span< BufferView > buffers, int timeoutMillis) const
 Reads exactly the full contents of all buffers within a timeout.
std::size_t readvAtMostWithTimeout (std::span< BufferView > buffers, int timeoutMillis) const
 Attempts a single vectorized read into multiple buffers with a timeout.
std::string peek (std::size_t n) const
 Peeks at incoming data without consuming it.
void discard (std::size_t n, std::size_t chunkSize=1024) const
 Discards exactly n bytes from the socket by reading and discarding them.
void close ()
 Closes the socket connection and releases associated resources.
void shutdown (ShutdownMode how) const
 Shutdown specific communication aspects of the socket.
size_t write (std::string_view message) const
 Writes data to the socket, handling partial writes.
size_t writeAll (std::string_view message) const
 Writes the entire contents of a message to the socket, handling partial writes.
template<typename T>
std::size_t writePrefixed (const std::string &payload)
 Writes a length-prefixed payload using a fixed-size prefix type.
template<typename T>
std::size_t writePrefixed (const void *data, std::size_t len) const
 Writes a binary payload prefixed with its length using a fixed-size integer type.
std::size_t writev (std::span< const std::string_view > buffers) const
 Writes multiple buffers in a single system call using scatter/gather I/O.
std::size_t writevAll (std::span< const std::string_view > buffers) const
 Writes all buffers fully using vectorized I/O with automatic retry on partial sends.
std::size_t writeAtMostWithTimeout (std::string_view data, int timeoutMillis) const
 Performs a best-effort write with a total timeout.
std::size_t writeFrom (const void *data, std::size_t len) const
 Writes up to len bytes from a raw memory buffer in a single send call.
std::size_t writeFromAll (const void *data, std::size_t len) const
 Writes all bytes from a raw memory buffer, retrying until complete.
std::size_t writeWithTotalTimeout (std::string_view data, int timeoutMillis) const
 Writes the full payload with a total timeout across all retries.
std::size_t writevWithTotalTimeout (std::span< const std::string_view > buffers, int timeoutMillis) const
 Writes all buffers fully within a total timeout using vectorized I/O.
std::size_t writevFrom (std::span< const BufferView > buffers) const
 Writes multiple raw memory regions using vectorized I/O.
std::size_t writevFromAll (std::span< BufferView > buffers) const
 Writes all raw memory regions fully using scatter/gather I/O.
std::size_t writevFromWithTotalTimeout (std::span< BufferView > buffers, int timeoutMillis) const
 Writes all raw memory buffers fully within a timeout using scatter I/O.
void setReceiveBufferSize (std::size_t size)
 Sets the socket's receive buffer size (SO_RCVBUF).
void setSendBufferSize (std::size_t size)
 Sets the socket's send buffer size (SO_SNDBUF).
int getReceiveBufferSize () const
 Get the socket's receive buffer size (SO_RCVBUF).
int getSendBufferSize () const
 Get the socket's send buffer size (SO_SNDBUF).
void setInternalBufferSize (std::size_t newLen)
 Sets the size of the internal read buffer used for string operations.
bool isValid () const noexcept
 Check if the socket is valid and open for communication.
void setNonBlocking (bool nonBlocking) const
 Set the socket to non-blocking or blocking mode.
bool getNonBlocking () const
 Check if the socket is currently in non-blocking mode.
void setSoTimeout (int millis, bool forRead=true, bool forWrite=true)
 Set timeout for socket send and/or receive operations.
bool waitReady (bool forWrite, int timeoutMillis) const
 Wait for the socket to be ready for reading or writing.
bool isConnected () const
 Check if the socket is still connected (TCP only).
void enableNoDelay (bool enable)
 Enable or disable TCP_NODELAY (Nagle's algorithm) on the socket.
void enableKeepAlive (bool enable)
 Enable or disable SO_KEEPALIVE on the socket.
void setOption (int level, int optName, int value)
 Set a socket option at the specified level.
int getOption (int level, int optName) const
 Get the current value of a socket option at the specified level.
template<>
std::string read ()
 Template specialization to read a string from the socket.

Static Public Member Functions

static std::string addressToString (const sockaddr_storage &addr)
 Convert an address and port to a string using getnameinfo.
static void stringToAddress (const std::string &str, sockaddr_storage &addr)
 Convert a string (ip:port) to sockaddr_storage.

Protected Member Functions

 Socket (SOCKET client, const sockaddr_storage &addr, socklen_t len, std::size_t recvBufferSize, std::size_t sendBufferSize, std::size_t internalBufferSize)
 Protected constructor used internally to create Socket objects for accepted client connections.
std::size_t readIntoInternal (void *buffer, std::size_t len, bool exact=false) const
 Reads data from the socket into a user-supplied buffer.
void cleanupAndThrow (int errorCode)
 Cleans up client socket resources and throws a SocketException.

Private Attributes

SOCKET _sockFd = INVALID_SOCKET
 Underlying socket file descriptor.
sockaddr_storage _remoteAddr
 (portability)
socklen_t _remoteAddrLen = 0
 Length of remote address (for recvfrom/recvmsg)
addrinfo * _cliAddrInfo = nullptr
 Address info for connection (from getaddrinfo)
addrinfo * _selectedAddrInfo = nullptr
 Selected address info for connection.
std::vector< char > _internalBuffer
 Internal buffer for read operations, not thread-safe.

Friends

class ServerSocket
 Grants ServerSocket access to private members.

Detailed Description

TCP client connection abstraction (Java-like interface).

The Socket class represents a TCP connection between your application and a remote host. It provides a high-level, easy-to-use, and cross-platform API for creating, connecting, sending, and receiving data over TCP sockets. Its interface is inspired by Java's Socket class, but uses modern C++20 features.

Key Features

  • Connect to remote hosts using hostnames or IP addresses (IPv4/IPv6).
  • Blocking or timeout-enabled connect for fine-grained control over connection attempts.
  • Safe resource management: sockets are closed automatically when the object is destroyed.
  • Read/write interface for sending and receiving binary data or text.
  • Move-only: socket resources are never accidentally copied.
  • Exception-based error handling via SocketException.
  • Fine-grained control: configure timeouts, non-blocking mode, TCP_NODELAY, SO_KEEPALIVE, etc.

Typical Usage Example

#include <iostream>
int main() {
try {
jsocketpp::Socket sock("example.com", 8080); // Connect to example.com:8080
sock.connect(3000); // Try to connect with 3-second timeout
sock.write("GET / HTTP/1.0\r\n\r\n");
std::string response = sock.read<std::string>();
std::cout << "Received: " << response << std::endl;
sock.close();
} catch (const jsocketpp::SocketException& ex) {
std::cerr << "Socket error: " << ex.what() << std::endl;
}
}
TCP client socket abstraction for jsocketpp.
Represents socket-related errors in the jsocketpp library.
Definition SocketException.hpp:58
TCP client connection abstraction (Java-like interface).
Definition Socket.hpp:91
int main()
Definition client.cpp:89

Internal Buffer

Error Handling

  • Almost all methods throw jsocketpp::SocketException on error (e.g., connect failure, write error, etc).
  • You should catch exceptions to handle network errors gracefully.

Thread Safety

  • Not thread-safe. Use a separate Socket object per thread if needed.

Platform Support

  • Windows, Linux, macOS. Handles all necessary platform differences internally.

Advanced Usage

See Also

Member Function Documentation

◆ addressToString()

std::string Socket::addressToString ( const sockaddr_storage & addr)
static

Convert an address and port to a string using getnameinfo.

Uses getnameinfo to convert a sockaddr_storage structure to a human-readable string (ip:port). Handles both IPv4 and IPv6 addresses.

Parameters
addrsockaddr_storage structure.
Returns
String representation (ip:port).
Exceptions
SocketExceptionif getnameinfo fails.

◆ enableKeepAlive()

void Socket::enableKeepAlive ( bool enable)

Enable or disable SO_KEEPALIVE on the socket.

SO_KEEPALIVE is a socket option that enables periodic transmission of keepalive probes on an otherwise idle TCP connection. When enabled (set to true), the operating system will periodically send keepalive messages to the remote peer if no data has been exchanged for a certain period. If the peer does not respond, the connection is considered broken and will be closed.

This feature is useful for detecting dead peers or broken network links, especially for long-lived connections where silent disconnects would otherwise go unnoticed. It is commonly used in server applications, remote control systems, and protocols that require reliable detection of dropped connections.

By default, SO_KEEPALIVE is disabled (i.e., keepalive probes are not sent) on new sockets.

Platform-Specific Details

  • Linux: Configure via /proc/sys/net/ipv4/tcp_keepalive_*
  • Windows: Default 2-hour idle time before first probe
  • macOS: System-wide keepalive settings apply

Example Usage

Socket sock("example.com", 8080);
sock.connect();
// Enable keepalive for long-lived connection
sock.enableKeepAlive(true);
Socket(SOCKET client, const sockaddr_storage &addr, socklen_t len, std::size_t recvBufferSize, std::size_t sendBufferSize, std::size_t internalBufferSize)
Protected constructor used internally to create Socket objects for accepted client connections.
Definition Socket.cpp:12
Parameters
enabletrue to enable keepalive probes (SO_KEEPALIVE), false to disable (default).
Exceptions
SocketExceptionIf setting the SO_KEEPALIVE option fails:
  • Invalid socket state (EBADF)
  • Permission denied (EACCES)
  • Memory allocation error (ENOMEM)

◆ enableNoDelay()

void Socket::enableNoDelay ( bool enable)

Enable or disable TCP_NODELAY (Nagle's algorithm) on the socket.

When TCP_NODELAY is enabled (set to true), Nagle's algorithm is disabled. This means that small packets of data are sent immediately over the network, without waiting to accumulate more data. This can reduce latency for applications that require fast, interactive communication (such as games, real-time systems, or protocols where low latency is more important than bandwidth efficiency).

When TCP_NODELAY is disabled (set to false), Nagle's algorithm is enabled. This causes the socket to buffer small outgoing packets and send them together, which can reduce network congestion and improve throughput for bulk data transfers, but may introduce slight delays for small messages.

By default, TCP_NODELAY is disabled (i.e., Nagle's algorithm is enabled) on new sockets.

Example Usage

Socket sock("example.com", 8080);
sock.connect();
// Enable TCP_NODELAY for low-latency communication
sock.enableNoDelay(true);
// Send data immediately without buffering
sock.write("time-sensitive-data");
Parameters
enabletrue to disable Nagle's algorithm (enable TCP_NODELAY, lower latency), false to enable Nagle's algorithm (disable TCP_NODELAY, higher throughput).
Exceptions
SocketExceptionIf setting the TCP_NODELAY option fails:
  • Invalid socket state (EBADF)
  • Permission denied (EACCES)
  • Protocol not available (ENOPROTOOPT)

◆ getOption()

int Socket::getOption ( int level,
int optName ) const
nodiscard

Get the current value of a socket option at the specified level.

This method retrieves the value of a low-level socket option from the underlying socket. This can be useful to check the current settings for options like buffer sizes or timeouts.

Example usage to read the receive buffer size:

int recvBuf = socket.getOption(SOL_SOCKET, SO_RCVBUF);
Parameters
levelThe protocol level at which the option resides (e.g., SOL_SOCKET, IPPROTO_TCP).
optNameThe name of the option (e.g., SO_RCVBUF, SO_KEEPALIVE).
Returns
The integer value currently set for the option.
Exceptions
SocketExceptionif the operation fails (see the error code/message for details).

◆ isConnected()

bool Socket::isConnected ( ) const

Check if the socket is still connected (TCP only).

This method performs a non-destructive check of the socket's connection status by attempting a zero-byte send (on Windows) or checking socket errors (on POSIX). While not 100% reliable due to the nature of TCP/IP, it provides a best-effort indication of connection status.

Implementation Details

  • Windows: Uses send() with zero bytes
  • POSIX: Checks SO_ERROR socket option
  • Does not generate network traffic
  • Non-blocking operation

Example Usage

Socket sock("example.com", 8080);
sock.connect();
// Periodically check connection
while (sock.isConnected()) {
// Connection is still alive
std::this_thread::sleep_for(std::chrono::seconds(1));
}
// Connection lost
Returns
true if the socket appears to be connected, false if disconnected or in an error state.
Note
This check is not guaranteed to detect all network failures, especially temporary outages or routing problems.
See also
enableKeepAlive() For reliable connection monitoring

◆ setOption()

void Socket::setOption ( int level,
int optName,
int value )

Set a socket option at the specified level.

This method sets a low-level socket option on the underlying socket. Socket options allow advanced users to customize various aspects of socket behavior, such as timeouts, buffer sizes, and address reuse policies.

Example usage to enable address reuse (SO_REUSEADDR):

socket.setOption(SOL_SOCKET, SO_REUSEADDR, 1);
Parameters
levelThe protocol level at which the option resides (e.g., SOL_SOCKET, IPPROTO_TCP).
optNameThe name of the option (e.g., SO_REUSEADDR, SO_RCVBUF).
valueThe integer value to set for the option.
Exceptions
SocketExceptionif the operation fails (see the error code/message for details).

◆ stringToAddress()

void Socket::stringToAddress ( const std::string & str,
sockaddr_storage & addr )
static

Convert a string (ip:port) to sockaddr_storage.

Parameters
strAddress string.
addrOutput sockaddr_storage.

◆ waitReady()

bool Socket::waitReady ( bool forWrite,
int timeoutMillis ) const

Wait for the socket to be ready for reading or writing.

Parameters
forWritetrue to wait for write, false for read.
timeoutMillisTimeout in milliseconds.
Returns
true if ready, false if timeout.
Exceptions
SocketExceptionon error.

◆ ServerSocket

friend class ServerSocket
friend

Grants ServerSocket access to private members.

ServerSocket needs access to Socket's private members during accept() operations to:

  • Initialize client Socket objects directly with the accepted socket descriptor
  • Set address information for the connected client
  • Configure internal buffers
See also
ServerSocket::accept() Creates new Socket instances from accepted connections
Socket(SOCKET,const sockaddr_storage&,socklen_t,std::size_t,std::size_t) Protected constructor used by accept()

Member Data Documentation

◆ _cliAddrInfo

addrinfo* jsocketpp::Socket::_cliAddrInfo = nullptr
private

Address info for connection (from getaddrinfo)

◆ _internalBuffer

std::vector<char> jsocketpp::Socket::_internalBuffer
private

Internal buffer for read operations, not thread-safe.

◆ _remoteAddr

sockaddr_storage jsocketpp::Socket::_remoteAddr
private

(portability)

sockaddr_in for IPv4; sockaddr_in6 for IPv6; sockaddr_storage for both

◆ _remoteAddrLen

socklen_t jsocketpp::Socket::_remoteAddrLen = 0
mutableprivate

Length of remote address (for recvfrom/recvmsg)

◆ _selectedAddrInfo

addrinfo* jsocketpp::Socket::_selectedAddrInfo = nullptr
private

Selected address info for connection.

◆ _sockFd

SOCKET jsocketpp::Socket::_sockFd = INVALID_SOCKET
private

Underlying socket file descriptor.


The documentation for this class was generated from the following files: