I created a simple client and server using CPPRESTSDK
. The client sends an image and on the server, I save the incoming file and then start doing the processing phase afterwards.
Now I want to check if the sent file is actually an image file and not some other random file. For that, I check the first few bytes of the file and this allows me to know what I'm dealing with.
This is the snippet responsible for saving the file:
//...
auto fileStream = std::make_shared<Concurrency::streams::ostream >();
Concurrency::streams::ostream outFile = Concurrency::streams::fstream::open_ostream(tmpFileName).get();
*fileStream = outFile;
uintmax_t bytesRead = 0;
int ret = 1;
bool isChecked = false;
while (ret > 0)
{
ret = request.body().read(fileStream->streambuf(), this->READ_CHUNK).get();
bytesRead += ret;
if (!isChecked)
{
isChecked = true;
auto streamBuffer = fileStream->streambuf();
unsigned char byteBuffer[4];
for (int i = 0; i < 4; i++)
{
byteBuffer[i] = (unsigned int)streamBuffer.bumpc().get();
std::cout << byteBuffer[i] << ", ";
}
// reset the read pointer
//streamBuffer.seekpos(std::streampos(), std::ios::in);
// check and see if this is indeed an image file
std::string imgFormat = Utils::Misc::GetImageType(byteBuffer);
if (imgFormat == "")
{
fileStream->close().get();
auto msg = U("Unsupported file has been sent! Expected an image file such as a JPEG, PNG, OR BMP");
this->ReplyMessage(request, status_codes::BadRequest, json::value::string(msg));
return;
}
}
ucout << "--" << bytesRead << U(" bytes read so far[")
<< Utils::Misc::GetFileSize(bytesRead , Utils::Misc::FileSizeTypes::KByte)
<< U(" KB]") << std::endl;
if (bytesRead > MAX_FILE_SIZE)
break;
}
// Close the file.
fileStream->close().get();
// ...
This clearly fails as the fileStream
is an ostream
and its can_read
returns false
thus bumpc()
doesn't work. So how should I be going about this? How can I access the underlying byte buffer and see what was received so far?
Update
Using the request
's streambuf()
also doesn't yield any success as the file pointer seems not to be moveable, thus doing something like seekpos(std::streampos(0), std::ios::in)
will not reset it to the beginning of the buffer. What am I missing here?