#c #sockets #boost-asio
#c #сокеты #boost-asio
Вопрос:
Я получил простое серверно-клиентское приложение.
idia таков: клиент отправляет на сервер строку с sql-запросом. Сервер обрабатывает запрос и отправляет обратно клиенту ответ с данными, отформатированными в строке в стиле csv.
Все уже настроено, примите одну вещь. Проблема в том, чтобы прочитать ответ на клиенте, потому что я не знаю размер полученной строки.
Код приведен ниже:
Сервер:
std::string answer;
answer = sql_read(*msg); //get the string with data from request
clientSock->write_some(buffer(answer, answer.size())); //send it back on client
Клиент:
std::string answer;
bytesRead = sock->read_some(boost::asio::buffer(readBuf, inputSize)); //read the answer, but how do I know correct size of string?
string_ptr msg(new std::string(readBuf, bytesRead));
answer = *msg;
Как прочитать результирующую строку, не зная ее размера?
Или, если мой подход (с отправкой данных в строке) в корне неверен, как сделать это правильно?
Комментарии:
1. Совет:
clientSock->write_some()
возможно, не все данные записаны. Вы должны проверить возвращаемое значение и вызвать его в цикле. У Asio есть вспомогательная функция, позволяющая избежать этого неудобства. Например.:boost::asio::write(sock, boost::asio::buffer(answer));
.
Ответ №1:
Вы должны обработать это самостоятельно в протоколе, который клиент и сервер используют для общения друг с другом.
Один из способов — использовать разделитель и использовать boost::asio::read_until()
. Пример:
boost::asio::streambuf buf;
boost::asio::read_until (sock, buf, "rn"); // or '' if zero terminated
Проверьте ускорение.Документация по Asio.
Другой способ — отправить размер в заголовке фиксированной длины перед отправкой части переменной длины.
Ответ №2:
Вы не будете знать размер строки заранее. Когда вы выполняете read_some, вам нужно будет выполнить цикл для чтения всех данных из сокета. Вам нужно проверить количество прочитанных байтов и размер выделенного вами буфера. Если они равны, то вы заполнили свой буфер чтения, и вам нужно выполнить еще одно чтение, чтобы проверить наличие оставшихся данных.