MFC C++ HTTP Post

Giovanni Polese
Giovanni Polese used Ask the Experts™
on
I had this question after viewing How to use OpenRequest() of CHttpConnection?.

I need to send a POST to Google.Vision server, using MFC and c++. The code is the following:

        CString strHeaders = _T("Content-Type: application/x-www-form-urlencoded");
      CString strFormData = "{'requests':[{'image':{'source':{'imageUri':'https://www.galileo2000.it/download/1.jpg'}},'features':[{'type':'FACE_DETECTION'}]}]}";

      CInternetSession session;
      CHttpConnection *pConnection = session.GetHttpConnection(_T("https://vision.googleapis.com/v1/images:annotate?key=MY_GOOGLE_API_KEY"));
      CHttpFile *pFile = pConnection->OpenRequest(CHttpConnection::HTTP_VERB_POST,_T("https://vision.googleapis.com"));
      BOOL result = pFile->SendRequest(strHeaders, (LPVOID)(LPCTSTR)strFormData,strFormData.GetLength());


Actually I am not very fond on these topics, so I got the above code in Internet. But I successfully wrote a WebService in C#, which works. The strFormData is the same I use in the WebService, so it should be correct. The main doubt is the second parameter of the OpenRequest. Of course I get an error "Impossible to resolve the server or the address". (Unluckily the message is in Italian and I translated back to English, so the actual error message could be slightly different).
Thanks
Comment
Watch Question

Do more with

Expert Office
EXPERT OFFICE® is a registered trademark of EXPERTS EXCHANGE®
David FavorFractional CTO
Distinguished Expert 2018

Commented:
The problem looks to be here...

CString strFormData = "{'requests':[{'image':{'source':{'imageUri':'https://www.galileo2000.it/download/1.jpg'}},'features' [{'type':'FACE_DETECTION'}]}]}";

Open in new window


The data your passing looks like JSON.

Tip: If your data is JSON, then use https://jsonformatter.org/ to verify your JSON is well formed, then pass the well formed JSON to your call.

Author

Commented:
Hi. Thanks for answering. Yes, the request is a Json, but it is well formed. At least, as I wrote, other programs I did, work with such a string (I just barely copied the string, so I have few doubts on it). The problem is that I don't figure out the meaning of the "Action" parameter of the OpenRequest (namely the second parameter). In documentation it is written that it may be a file, etc. but I don't have anything like a file. Moreover, in other examples, this second parameter is part of the Url. I am completely confused on it. The problem is what to write in OpenRequest, after the HTTP_VERB. To further explain, I reproduce the part of the Microsoft documentation. My problem is what is pstrObjectName.

CHttpFile* OpenRequest(
    LPCTSTR pstrVerb,
    LPCTSTR pstrObjectName,
    LPCTSTR pstrReferer = NULL,
    DWORD_PTR dwContext = 1,
    LPCTSTR* ppstrAcceptTypes = NULL,
    LPCTSTR pstrVersion = NULL,
    DWORD dwFlags = INTERNET_FLAG_EXISTING_CONNECT);

CHttpFile* OpenRequest(
    int nVerb,
    LPCTSTR pstrObjectName,
    LPCTSTR pstrReferer = NULL,
    DWORD_PTR dwContext = 1,
    LPCTSTR* ppstrAcceptTypes = NULL,
    LPCTSTR pstrVersion = NULL,
    DWORD dwFlags = INTERNET_FLAG_EXISTING_CONNECT);

Thanks
David FavorFractional CTO
Distinguished Expert 2018

Commented:
The JSON you posted is broken.

Run your JSON through https://jsonformatter.org/ + fix formatting, till you get a clean validation.

Tip: Just because you copied this JSON, doesn't mean it's well formed.
Expert Spotlight: Joe Anderson (DatabaseMX)

We’ve posted a new Expert Spotlight!  Joe Anderson (DatabaseMX) has been on Experts Exchange since 2006. Learn more about this database architect, guitar aficionado, and Microsoft MVP.

Author

Commented:
Hi. Thanks for your patience. The problem on Json may exist, as you say, but then I have two problems.. As a matter of fact, the string that I wrote is not validated by the formatter that you suggest. The reason is that the correct Json contains quotes " that cannot be written in a CString object. That's why I substituted the internal " with ' in the string, and, obviously, the formatter says that it is wrong. But, this was just a low level temptative. Actually, to embed a " in a CString, in what I know, I must write \" instead of the single ". Therefore the CString representing the Json, becomes: (first is commented because impossible in C++ MFC)

//CString strFormData = "{"requests":[{"image":{"source":{"imageUri":      "https:://www.galileo2000.it/download/1.jpg"}},"features":[      {"type":"FACE_DETECTION","maxResults" : 20}      ]}]}";

      CString strFormData = "{\"requests\":[{\"image\":{\"source\":{\"imageUri\":      \"https:://www.galileo2000.it/download/1.jpg\"}},\"features\":[      {\"type\":\"FACE_DETECTION\",\"maxResults\" : 20}      ]}]}";

And, of course, your formatter says that it is wrong. Then I don't know how to proceed. Please note that, in C#, the following code works (no question about, I can prove it):

var uri = "https://vision.googleapis.com/v1/images:annotate?key=" + MY_GOOGLE_KEY;
               
                client.Headers.Add("Content-Type:application/json");
                client.Headers.Add("Accept:application/json");
                string Req = "{'requests':[{'image':{'source':{'imageUri':'https://www.galileo2000.it/download/1.jpg'}},'features':[{'type':'FACE_DETECTION'}]}]}";
                var response = client.UploadString(uri, "POST", Req);//
                return response;

That's why I "copied" the Req string: first I tried in C# and saw that it was working. Nevertheless, the Json validator says that that string is wrong. The reason is the presence of the ', that, evidently, is valid in C# and not in C++ (unmanaged). The difference could be just this.
Thanks for your patience.

Author

Commented:
Sorry. I wrote: "The reason is the presence of the ', that, evidently, is valid in C# and not in C++ (unmanaged)" and this is not correct. As a matter of fact, the ' is valid either in C# or in C++ and that's why I used the CString with ' and not with \". But, either with ' or with \" the Json validator refuses the string. I repeat: the C# code works, despite the validator says that the string is wrong. This is the reason why I don't think that the problem is the JSon. By the way, in C++, putting the \" for the single " produces exactly the requested valid string.

Author

Commented:
Hi. By the way i solved the problem using curl library. The json string may have, for the internal fields, the (apex) ' instead of (quote) ", and it works in my case. Thanks again.

Do more with

Expert Office
Submit tech questions to Ask the Experts™ at any time to receive solutions, advice, and new ideas from leading industry professionals.

Start 7-Day Free Trial