我有一个使用LibCurl
上传文件的应用程序。我用下面的函数显示上传进度和百分比,效果很好。但是,我无法获得CURLINFO_SPEED_UPLOAD
函数的平均上传速度(CURLINFO_TOTAL_TIME
)和经过的时间(curl_easy_getinfo
)。我在这做错了什么?我与Libcurl的原始示例有很多不同之处?
static int ReceiveFileProgress(void *p, curl_off_t dltotal, curl_off_t dlnow, curl_off_t ultotal, curl_off_t ulnow) {
if (ultotal > 0) {
string Output;
double curtime = 0;
char ulspeed[10000];
double ulspeed_curl = 0;
double ulnow_db = (double)ulnow;
double ultotal_db = (double)ultotal;
double percentage = ceil((ulnow_db / ultotal_db) * 100);
struct myprogress *myp = (struct myprogress *)p;
CURL *curl = myp->curl;
if (curl) {
cout << "CURL OK" << endl;
}
else {
cout << "CURL FAILED" << endl;
}
if (percentage != 100) {
curl_easy_getinfo(curl, CURLINFO_SPEED_UPLOAD, &ulspeed_curl);
}
curl_easy_getinfo(curl, CURLINFO_TOTAL_TIME, &curtime);
readable_fs(ulspeed_curl, ulspeed);
stringstream OutputStream;
OutputStream << percentage;
Output = PadString(OutputStream.str(), 3, " ");
OutputStream.str("");
OutputStream << Output << "%";
if (percentage != 100) {
OutputStream << " (" << ulspeed << "/s)";
}
Output = OutputStream.str();
if (Output.length() > SendOffFileMaxProgressLength) {
Output.substr(0, SendOffFileMaxProgressLength - 3);
Output += "...";
}
else {
while (Output.length() < SendOffFileMaxProgressLength) {
Output += ' ';
}
}
cout << Output << '\r';
}
return 0;
}
卷曲请求:
string PerformCurlRequest(string RequestType, struct curl_httppost &formpost, struct curl_httppost &lastptr) {
CURL *curl;
CURLcode res;
bool UsedProxy;
string CurlResponse;
int LibCurlError = 0;
int ProxyRetryCount = 1;
bool TryWithProxy = true;
struct curl_slist *LibcurlHeaders = NULL;
curl = curl_easy_init();
if (curl) {
host = "url/";
host += RequestType;
host += "/";
LibcurlHeaders = curl_slist_append(LibcurlHeaders, "Expect:");
curl_easy_setopt(curl, CURLOPT_URL, (host).c_str());
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 1);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 1);
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, LibcurlHeaders);
curl_easy_setopt(curl, CURLOPT_VERBOSE, CurlVerbose);
curl_easy_setopt(curl, CURLOPT_HTTPPOST, formpost);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, LibcurlResponse);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, &CurlResponse);
curl_easy_setopt(curl, CURLOPT_DEBUGFUNCTION, GetCurlVerboseData);
curl_easy_setopt(curl, CURLOPT_XFERINFOFUNCTION, ReceiveFileProgress);
curl_easy_setopt(curl, CURLOPT_XFERINFODATA, &progress);
curl_easy_setopt(curl, CURLOPT_NOPROGRESS, false);
res = curl_easy_perform(curl);
curl_slist_free_all(LibcurlHeaders);
curl_easy_cleanup(curl);
}
return CurlResponse;
}
发送文件:
PerformCurlRequest("SendFile", *formpostReceiveFile, *lastptrReceiveFile)
答案 0 :(得分:1)
我不知道你正在使用什么libcurl版本,或者你是否可能在其他地方弄乱你的代码,但是我可以从这个示例代码中的libcurl进程回调中做CURLINFO_SPEED_UPLOAD
做HTTP“上传“(为简单起见,在这里使用PUT):
#include <stdio.h>
#include <curl/curl.h>
#include <sys/stat.h>
struct myprogress {
CURL *curl;
};
static int xferinfo(void *p, curl_off_t dltotal, curl_off_t dlnow,
curl_off_t ultotal, curl_off_t ulnow)
{
struct myprogress *myp = (struct myprogress *)p;
CURL *curl = myp->curl;
double ulspeed_curl = 0;
curl_easy_getinfo(curl, CURLINFO_SPEED_UPLOAD, &ulspeed_curl);
fprintf(stderr, "UP: %" CURL_FORMAT_CURL_OFF_T " of %" CURL_FORMAT_CURL_OFF_T
" DOWN: %" CURL_FORMAT_CURL_OFF_T " of %" CURL_FORMAT_CURL_OFF_T
" AVRUP: %.1f"
"\r\n",
ulnow, ultotal, dlnow, dltotal, ulspeed_curl);
return 0;
}
/* send off a random test file lying around */
#define FILENAME "file-to-send"
int main(void)
{
CURL *curl;
CURLcode res = CURLE_OK;
struct myprogress prog;
curl = curl_easy_init();
if(curl) {
FILE *strace;
struct stat file_info;
prog.curl = curl;
strace = fopen(FILENAME, "rb");
if(!strace)
return 1;
/* get the file size of the local file */
stat(FILENAME, &file_info);
curl_easy_setopt(curl, CURLOPT_URL, "http://localhost/");
curl_easy_setopt(curl, CURLOPT_XFERINFOFUNCTION, xferinfo);
curl_easy_setopt(curl, CURLOPT_XFERINFODATA, &prog);
curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 0L);
curl_easy_setopt(curl, CURLOPT_UPLOAD, 1L);
curl_easy_setopt(curl, CURLOPT_INFILESIZE_LARGE,
(curl_off_t)file_info.st_size);
curl_easy_setopt(curl, CURLOPT_READDATA, strace);
res = curl_easy_perform(curl);
if(res != CURLE_OK)
fprintf(stderr, "%s\n", curl_easy_strerror(res));
/* always cleanup */
curl_easy_cleanup(curl);
}
return (int)res;
}