Get image file from a client request - c++

I want to get a .bmp format image via HTTP request. When I send a test request via Postman there are headlines added such as Content-Type and when the request is saved to the stream they are automatically added to the generated .bmp file and the file doesn’t work properly. When I remove not needed headlines by hand in Nano the image can be opened the way I expect it to be.
Is there a way in cpprestsdk to not add the headlines and post only the image file or the headlines need to be deleted?
void Service::handlePost(http_request request)
{
auto fileStream = std::make_sharde<Concurrency::streams::ostream>();
utility::string_t file = "file.bmp";
// open stream to output file
*fileStream = Concurrency::streams::fstream::open_stream(file).get();
request.body().read_to_end(fileStream->streambuf()).wait();
fileStream.close();
//...
}
------------------------------553993878653478454105895
Content-Disposition: form-data; name="image"; filename="file.bmp"
Content-Type: image/bmp
BM /^#^#^#^#^#^#^#^#
(BMP binary file)
^#^#^#^#^#^#^#
------------------------------553993878653478454105895--

According to the documentation(https://github.com/Microsoft/cpprestsdk/wiki/Getting-Started-Tutorial), there is no such way, so you should remove the headers yourself.

Related

How to create postman multipart/form-data request with an embedded file?

I'm creating a set of postman requests, in a collection, so that I can test an endpoint which accepts file uploads. I need to embed files in the request because otherwise the test collection isn't self contained and can't be used in the postman runner directly.
I can "embed" text files without line breaks (CRLF) but I can't embed binary files since they contain CRLFs.
Ways to embed single line text files
Embed single line text files
This can be achieved by setting a custom header and body
Header
content-type: multipart/form-data; boundary=--------------------------separator
Body (raw type)
----------------------------separator
Content-Disposition: form-data; name="file"; filename="file.json"
Content-Type: application/json
{ "id": "ecee0102-51c9-4a86-b5e7-0378f117f991" }
----------------------------separator--
"Embed" big single-line files using a pre-request script
Header
content-type: multipart/form-data; boundary=--------------------------separator
Body (raw type)
----------------------------separator
Content-Disposition: form-data; name="file"; filename="file.json"
Content-Type: application/json
{{tooBigFileContent}}
----------------------------separator--
Pre-request script
pm.globals.set("tooBigFileContent", "9".repeat((10*1024*1024)+1));
Things I have tried but didn't work
Try to inject file contents into the body, decoding base64 to "binary", using pre-request script
Try to use Content-Transfer-Encoding with base64 (the endpoint doesn't support the encoding
Ideas on how to achieve this?

Use cpprest (Casablanca) to return PDF response

I am using cpprest in a server on Ubuntu Linux. So far I am able to process requests, and reply with JSON responses.
One of the requests that I accept needs to respond with a PDF file. I see that the http_request class has a reply() method that accepts an asynchronous stream. For the life of me, I can't figure out how to associate this stream with my PDF file on disk.
utility::string_t pdfFilename = getPdfFilename();
concurrency::streams::istream stream; // how do associate my pdfFilename?
request.reply(web::http::status_codes::OK, stream, "application/pdf");
I hope you already figured it out. Here's how I reply with local pdf files
void replyPdf(web::http::http_request message, string_t file_name)
{
concurrency::streams::fstream::open_istream(file_name, std::ios::in)
.then([=](concurrency::streams::istream is)
{
web::http::http_response response(web::http::status_codes::OK);
response.headers().add(L"Content-Disposition", U("inline; filename = \"") + file_name + U("\""));
response.set_body(std::move(is), U("application/pdf"));
message.reply(response).then([](pplx::task<void> t) {});
});
}

Displaying file: MessageBodyReader not found for media type=application/octet-stream

My requirement is that I should display a file using RESTFul services. Here how I proceeded:
Server:
#GET
#Path("/{name}")
#Produces(MediaType.APPLICATION_OCTET_STREAM)
public Response getFile {
...
return Response.ok(inputStream).header("Content-Disposition", "attachment; filename=" + fileName).build();
Client:
final WebTarget target = createRestClient("path/" + fileName, new HashMap<String, Object>());
return target.request(MediaType.APPLICATION_OCTET_STREAM).get().readEntity(Part.class);
When I run it, I've got this error:
MessageBodyReader not found for media type=application/octet-stream, type=interface javax.servlet.http.Part, genericType=interface javax.servlet.http.Part.
Do you have any idea where did this come from?
Thanks.
javax.servlet.http.Part should be used to obtain upload multipart data, and is created by the servlet container, which you obtain from a HttpServletRequest. It should not be used in this way. Beside the data is not even multipart.
Instead, you can simply get the InputStream from the from the Response and the Content-Dispostion get explicitly from the header. Something like
Response response = target.request()
.accept(MediaType.APPLICATION_OCTET_STREAM)
.get();
// get InputStream
InputStream is = response.readEntity(InputStream.class);
// get Content-Disposition header
String contentDisposition = (String)response
.getHeaderString(HttpHeaders.CONTENT_DISPOSITION);
// get filename
contentDisposition = contentDisposition
.substring(contentDisposition.indexOf("filename=") + "filename".length() + 1);
System.out.println(contentDisposition);

How do I get the Content-Encoding in a POCO::Net::HTTPResponse object?

I'm fetching a server page using Poco::Net::HTTPClientSession with an appropriate Poco::Net::HTTPRequest, which works fine. Now I get a response back, and sometimes the returned page will be gzipped.
I need to find out when that is the case, so that I may deflate if necessary. The HTTP header that should indicate this, is Content-Encoding: gzip; but there's no getContentEncoding() method in Poco::Net::HTTPResponse.
Here's a non-working snippet (because there's no resp.getContentEncoding()):
// resp is the Poco::Net::HTTPResponse object,
// sess is the Poco::Net::HTTPClientSession
std::istream &in = sess.receiveResponse(resp);
// Get the server-returned body as a string (potentially deflate)
std::ostringstream serveroutput;
if (resp.getContentEncoding() == "gzip") {
Poco::InflatingInputStream
inflater(in, Poco::InflatingStreamBuf::STREAM_GZIP);
Poco::StreamCopier::copyStream(inflater, serveroutput);
} else
Poco::StreamCopier::copyStream(in, serveroutput);
// Now we can get at the body as a string
std::string txt = serveroutput.str();
Does anyone know how to get at the raw headers, so that I can inspect the header Content-Encoding myself, or of another useful method to determine whether a server response is gzipped?
if the server set the Content-Encoding header
you could get the encoding value like the following.
resp.get("Content-Encoding")

HttpClient and extracting audio from server response

I am using Apache HttpClient to connect to a server for downloading a .wav file. I am using HTTP POST method in my program.
The server correctly responds with the following header and body:
> HTTP/1.1 200 OK\r\n Content-Disposition: attachment;
> filename=saveme1.mp3\r\n Content-Length: 6264\r\n
> Content-Transfer-Encoding: binary\r\n Content-Type: audio/mp3\r\n
How do I now extract the saveme1.mp3 file from the HTTP response? I am using the following code:
ResponseHandler<String> responseHandler = new BasicResponseHandler();
byte[] data = httpclient.execute(httppost, responseHandler).getBytes();
However, I am getting garbage when I am writing the data to a file.
FileOutputStream fileoutputstream = new FileOutputStream(outputFile);
for (int i = 0; i < data.length; i++)
fileoutputstream.write(data[i]);
If you want download mp3 I Think easiest way is :
HttpResponse response = httpclient.execute(httppost);
HttpEntity entity = response.getEntity();
Now you have entity and can call entity.getContent(); This give you you a inputStream , now you can save this stream with every method you want , ofcurse you need mime type and filename to save your file. if you have problem with filename and mime type tell me to add some sample code.
You are getting MIME attachment that you need to parse first. The BasicResponseHandler just return the response string, but you need the body of the attachment that contains the binary of your .mp3. You would need to do the following steps:
Understand the MIME format. You could skim the Wikipedia Entry for gaining quick familiarity
Once you understood, you need to create a MIME Parser. This would basically extract each part of the MIME message especially the body of your attachment. I think there should be something out there that you could reuse. You probably should look MimeMultipart. The only thing that I am not sure about it is whether it handles "binary" encoding in your message.
Create your own extension of ResponseHandler that will utilize the MIME Parser that you have in the previous step