Advertisement
Guest User

setting options for ftp upload with libcurl

a guest
Nov 9th, 2011
324
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.74 KB | None | 0 0
  1. template<typename OptionType>
  2. void Set_Easy_Opt(CURL* easyHandle, CURLoption option, OptionType value) throw(std::exception)
  3. {
  4.     CURLcode result = curl_easy_setopt(easyHandle, option, value);
  5.     if (result != CURLE_OK)
  6.     {
  7.         std::ostringstream str;
  8.         str << "curl_easy_setopt FAILED for option: " << option << ", value: " << value
  9.             << " returned: " << (int) result << " " << curl_easy_strerror(result);
  10.         throw std::runtime_error(str.str());
  11.     }
  12. }
  13.  
  14. tm_error_t TransferManager::SetupTransfer(transfer_data& transfer, CURL* handle)
  15. {
  16.     const long MIN_OPERATION_TIME = 20;
  17.     const long FTP_RESPONSE_TIMEOUT = 90;
  18.     const long CONNECT_TIMEOUT = 60;
  19.    
  20.     long timeout = difftime(transfer.task.expireTime, std::time(0));
  21.     if (timeout < MIN_OPERATION_TIME)
  22.     {
  23.         LOG_INFO("There is not enough time for the operation: " << timeout
  24.                     << " s, minimum is: " << MIN_OPERATION_TIME << " s");
  25.         Fclose(transfer.fileHandle);
  26.        
  27.         return TM_OP_TOUT;
  28.     }
  29.     long connectTimeout = (timeout > CONNECT_TIMEOUT) ? CONNECT_TIMEOUT : timeout/2;
  30.     long ftpResponseTimeout = (FTP_RESPONSE_TIMEOUT < timeout) ? FTP_RESPONSE_TIMEOUT : (timeout - 1);
  31.    
  32.     // for now it's only for upload
  33.     if (not transfer.fileHandle)    // it can be initial try
  34.     {
  35.         transfer.fileHandle = fopen(transfer.task.GetLocalPath().c_str(), "r");
  36.         if (not transfer.fileHandle)
  37.         {
  38.             LOG_ERROR("CURL: Could not open file handle to: " << transfer.task.GetLocalPath());
  39.             return TM_FILE_ERR;
  40.         }
  41.     }
  42.    
  43.     try {
  44.         curl_easy_reset(handle);
  45.  
  46.         transfer.errorBuffer[0] = '\0'; // we clean buffer before every retry of transfer
  47.         Set_Easy_Opt(handle, CURLOPT_ERRORBUFFER, transfer.errorBuffer);
  48.  
  49.         Set_Easy_Opt(handle, CURLOPT_URL, transfer.task.urlToFile.c_str());
  50.        
  51.         Set_Easy_Opt(handle, CURLOPT_UPLOAD, 1l);
  52.         Set_Easy_Opt(handle, CURLOPT_APPEND, 1l);
  53.         //Set_Easy_Opt(handle, CURLOPT_RESUME_FROM, -1l); // continue upload
  54.         //Set_Easy_Opt(handle, CURLOPT_RESUME_FROM_LARGE, -1l); // continue upload
  55.         Set_Easy_Opt(handle, CURLOPT_READDATA, transfer.fileHandle);
  56.        
  57.  
  58.         std::string userPass = mFtpUser + ":" + mFtpPass;
  59.         Set_Easy_Opt(handle, CURLOPT_USERPWD, userPass.c_str());
  60.  
  61.         Set_Easy_Opt(handle, CURLOPT_NOSIGNAL, 1l);
  62.        
  63.         LOG_DEBUG("Setting timeout for task with " << transfer.task.urlToFile
  64.                     << ", timeout = " << timeout << ", connect timeout = " << connectTimeout
  65.                     << ", ftpResponseTimeout = " << ftpResponseTimeout);
  66.         Set_Easy_Opt(handle, CURLOPT_TIMEOUT, timeout);
  67.         Set_Easy_Opt(handle, CURLOPT_CONNECTTIMEOUT, connectTimeout);
  68.         Set_Easy_Opt(handle, CURLOPT_FTP_RESPONSE_TIMEOUT, ftpResponseTimeout);
  69.  
  70. #ifdef CURL_DEBUG_CALLBACK
  71.         Set_Easy_Opt(handle, CURLOPT_VERBOSE, 1l);
  72.         Set_Easy_Opt(handle, CURLOPT_DEBUGFUNCTION, CurlDebugCallback);
  73. #endif
  74.         Set_Easy_Opt(handle, CURLOPT_LOW_SPEED_TIME, 60l);
  75.         Set_Easy_Opt(handle, CURLOPT_LOW_SPEED_LIMIT, 1l);
  76.  
  77.         Set_Easy_Opt(handle, CURLOPT_IPRESOLVE, CURL_IPRESOLVE_WHATEVER);
  78.     } catch (std::runtime_error const& e) {
  79.         LOG_ERROR("CURL: easy handle could not be configured for server task with url: \""
  80.                     << transfer.task.urlToFile << "\", local path: \"" << transfer.task.GetLocalPath()
  81.                     << "\", exception: " << e.what());
  82.         if (transfer.errorBuffer[0])
  83.             LOG_ERROR("CURL: ConfigureCurlHandle: curl error buffer: " << transfer.errorBuffer);
  84.         Fclose(transfer.fileHandle);
  85.         return TM_SOFTWARE_ERR;
  86.     }
  87.    
  88.     CURLMcode curlResult = curl_multi_add_handle(mMultiHandle, handle);
  89.     if (curlResult != CURLM_OK)
  90.     {
  91.         LOG_ERROR("CURL: easy handle could not be added to multi!!!! error code: "
  92.                     << (int) curlResult << " " << curl_multi_strerror(curlResult));
  93.         Fclose(transfer.fileHandle);
  94.        
  95.         return TM_SOFTWARE_ERR;
  96.     }
  97.    
  98.     return TM_NO_ERR;
  99. }
  100.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement