Click here to Skip to main content
15,894,343 members
Please Sign up or sign in to vote.
5.00/5 (1 vote)
See more:
Hi all, the code below compiles and runs perfectly under VS 2013 but when I try and compile it using g++ on a Linux box I get a slew of errors regarding std::wstring, I know this is the problem as if I replace all wstring and wostringstream with string and ostringstream respectively all is good. This is only a personal project and thus very rough at the moment.

C++
#include <vector>
#include <string>
#include <time.h>
#include <iostream>
#include <sstream>
#include <map>
#include "squeezemessage.h"
#include <random>

#include <cpprest/http_client.h>
#include <cpprest/filestream.h>
#include <cpprest/json.h>

using namespace utility;                    // Common utilities like string conversions
using namespace web;                        // Common features like URIs.
using namespace web::http;                  // Common HTTP functionality
using namespace web::http::client;          // HTTP client features
using namespace concurrency::streams;       // Asynchronous streams

int ResultCount = 0;
std::vector<std::pair<std::wstring, std::wstring>> Artists;

void GetJsonResponse(json::value &jsonValue, http_response &response)
{
	jsonValue = response.extract_json().get().at(U("result"));
	ResultCount = jsonValue.size();
}

void SetRequest(http_request &requester, std::wstring &SqueezeMsg)
{
	requester.set_method(methods::POST);
	requester.headers().set_content_type(L"application/json");
	requester.set_body(SqueezeMsg);
}

std::wstring GetClient()
{
	return L"http://10.10.1.11:9000/jsonrpc.js";
}


pplx::task<void> Post(std::wstring SqueezeMsg)
{
	http_request requester;
	SetRequest(requester, SqueezeMsg);
	Artists.clear();

	return pplx::create_task([requester]
	{
		std::wstring URL(GetClient());

		http_client client(URL);

		return client.request(requester);

	}).then([](http_response response)
	{
		int code = response.status_code();

		if (response.status_code() == status_codes::OK)
		{
			json::value jsonValue;
			GetJsonResponse(jsonValue, response);

			std::map<std::wstring, std::wstring> Entities;

			Entities.insert(std::pair<std::wstring, std::wstring>(U("contributors_loop"),U("contributor")));
			Entities.insert(std::pair<std::wstring, std::wstring>(U("albums_loop"),U("album")));
			Entities.insert(std::pair<std::wstring, std::wstring>(U("tracks_loop"),U("track")));	
			
			std::wostringstream ss;

			if (ResultCount > 0)
			{
				ResultCount = 0;

				std::map<std::wstring, std::wstring>::iterator it;

				for (it = Entities.begin(); it != Entities.end(); ++it)
				{
					if (jsonValue.has_field(it->first))
					{
						json::value EntityArray = jsonValue.at(it->first);
						std::wstring FieldName(it->second);

						for (size_t i = 0; i < EntityArray.size(); i++)
						{
							std::wostringstream ss;
							ss << FieldName << ": " << (i + 1);
							std::wstring whatever(EntityArray[i].at(FieldName).as_string());
							Artists.push_back(std::pair<std::wstring, std::wstring>(ss.str(), whatever));
							ResultCount++;
						}
					}
				}
			}
		}
	});
}

int main(int argc, char* argv[])
{
	if (argc < 2)
	{
		std::wcout << L"\n\nUsage: " << argv[0] << L" search term\n";
		return -1;
	}

	SqueezeMessage Squeezer;
	std::wostringstream ss;
	ss << L"term:" << argv[1];
	
	std::wstring SearchTerm(ss.str());

	Squeezer.BuildMessage(L"search", L"0", L"10000", SearchTerm);
	std::wstring SqueezeMsg = Squeezer.SqueezeRequestW;
	std::wcout << L"\n\n*** Running query " << SqueezeMsg << L"\n";

	Post(SqueezeMsg).get();

	for (std::vector<std::pair<std::wstring, std::wstring>>::iterator it = Artists.begin(); it != Artists.end(); ++it)
		std::wcout << it->first << ":" << it->second << '\n';

	std::wcout << L"\n\n*** " << Artists.size() << L" row" << (Artists.size() == 1 ? L"" : L"s") << L" returned ***\n";
}


What I have tried:

Googling, drinking heavily, long walks ( to the pub and back ) and finally posting here.
Posted
Updated 20-Jul-16 0:29am
Comments
OriginalGriff 20-Jul-16 6:28am    
Upvote for honesty! :laugh:

1 solution

There is usually no need to use std::wstring with Linux because it uses UTF-8 strings by default since many years. So you have full Unicode support with char strings.

You will always run into problems when using std:wstring with Linux because nearly all library functions expect char strings.

[UPDATE]
From FAQ · Microsoft/cpprestsdk Wiki · GitHub[^]:
Quote:
The C++ REST SDK uses a different string type dependent on the platform being targeted. For example for the Windows platforms utility::string_t is std::wstring using UTF-16, on Linux std::string using UTF-8.

So you might use the utility::string_t type instead.
[/UPDATE]
 
Share this answer
 
v3
Comments
pkfox 20-Jul-16 7:18am    
Really ( You will always run into problems when using std:wstring with Linux ) ? the cpprestsdk team boast of cross platform support - I like to develop using VS on Windows and then copy the code to Linux - I suppose I'll just have to default to using std::string which is not a big deal - thanks for your help.
Jochen Arndt 20-Jul-16 7:42am    
If you are going to pass such strings to standard library functions: Yes.
You will have to convert them.

I saw that you are using cpprest but have not used it so far. So I did not know how it is handling strings internally. But with internet applications (HTPP, Jason) strings are usually UTF-8. Then it makes no sense to convert them to wide characters upon parsing and back to UTF-8 upon output.

I see two solutions:
Using a OS dependant typedef for the strings used by your application or using always char strings which must be then converted from UTF-8 to wide characters with Windows.

Which is better here depends on how strings are handled by cpprest for Windows and Linux. A quick search shows that cpprest provides the required conversion functions.

And it brought up a FAQ. I will update my answer.
pkfox 20-Jul-16 8:45am    
Hi Jochen, cpprest has this little gem in basic_types.h

#ifdef _UTF16_STRINGS
typedef std::wstring string_t;
#else
typedef std::string string_t;
#endif
which is what you suggested.
I changed all my wstring to string_t and all is fine - thanks for your time

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900