2015-10-20 20 views
0

我在libcurl的幫助下編寫了一個簡單的文件下載程序。下面是從HTTP服務器下載文件的代碼:使用libcurl下載UTF-8文件(ANSI工作正常)

static size_t WriteCallback(void *contents, size_t size, size_t nmemb, void *userp) { 
    ((std::string*)userp)->append((char*)contents, size * nmemb); 
    return size * nmemb; 
} 

std::wstring result; //result with polish letters (ą, ę etc.) 
CURL *curl; 
CURLcode res; 
std::string readBuffer; 

curl = curl_easy_init(); 
ERROR_HANDLE(curl, L"CURL could not been inited.", MOD_INTERNET); 
curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); 
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, WriteCallback); 
curl_easy_setopt(curl, CURLOPT_WRITEDATA, &readBuffer); 
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0L); 
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0L); 
curl_easy_setopt(curl, CURLOPT_HTTPAUTH, CURLAUTH_BASIC); 
curl_easy_setopt(curl, CURLOPT_USERPWD, (login + ":" + password).c_str()); //e.g.: "login:password" 
curl_easy_setopt(curl, CURLOPT_POST, true); 
//curl_easy_setopt(curl, CURLOPT_ENCODING, "UTF-8"); //does not change anything 
res = curl_easy_perform(curl); 
curl_easy_cleanup(curl); 

result = C::toWString(readBuffer); 
return res == 0; //0 = OK 

當我要下載的文件被編碼爲ANSI它工作正常(根據例如記事本++)。但是,當我嘗試下載UTF-8文件(UTF-8 without BOM)時,由於編碼問題,我得到某些字符(例如波蘭語字母)的錯誤。

例如,我使用相同的文本(「to jestteśćto」)運行兩個文件的代碼並將其保存到std::wstring。該resultANSI文件和result2(有問題的)從UTF-8版本:enter image description here

這兩個文件打開了服務器例如Notepad ++顯示正確的文本。

那麼,我怎麼能得到UTF-8文件內容與libcurl並將其保存到std::wstring用正確的編碼(這樣的Visual Studio調試器將顯示它爲to jest teść to)?

+0

在寬字符串中存儲UTF-8並沒有什麼意義。這麼做的意義何在? – MrEricSir

+0

該代碼未將UTF-8存儲在「std :: wstring」中。它將UTF-8存儲在'std :: string'中,然後在下載完成後將其轉換爲'std :: wstring'。問題在於轉換,而不是下載本身。 –

+0

@MrEricSir正如我的想法(糾正我,如果我錯了)wstring可以存儲寬字符,並將與UTF-8(它將使用超過1個字節來存儲我的波蘭文本字符)很好地工作。調試器也顯示這一點。並且將其存儲在字符串內部還不清楚(還有像find這樣的方法不會像他們應該那樣工作)。 – PolGraphic

回答

1

這不是一個libcurl問題。您將原始數據存儲在std::string中,然後在下載完成後將其轉換爲std::wstring。您必須查看HTTP響應中報告的字符集,並相應地將數據解碼爲std::wstringC::toWString()沒有字符集的概念,所以你應該使用別的東西,比如ICONV或ICU。或者,如果您知道數據始終爲UTF-8,則手動執行轉換(UTF轉換很容易手工編寫),或者使用std::wstring_convert類使用內置UTF-8轉換的C++ 11。

+0

如何查看使用libcurl請求的HTTP響應中報告的字符集? – PolGraphic

+1

charset在'Content-Type'響應標題中,你可以使用''curl_easy_getinfo()'](http://curl.haxx.se/libcurl/c/curl_easy_getinfo.html)和'info'參數設置爲['CURLINFO_CONTENT_TYPE'](http://curl.haxx.se/libcurl/c/CURLINFO_CONTENT_TYPE.html)。 –

+0

謝謝。對於一些我得到的文件'text/html的; charset = ISO-8859-1',但是對於其中的很多人,我只有'text/plain'(在ANSI和UTF-8的情況下)。我能做點什麼嗎? – PolGraphic

1

libcurl不會爲您轉換或翻譯內容。它會將確切的字節傳遞給服務器發出的應用程序。

您可以使用HTTP Accept頭等來影響服務器響應的內容,但是如果您對獲得的內容不滿意,則需要檢查收到的字符集並自行進行相應轉換。

相關問題