ftpclient-cpp
ftpclient-cpp copied to clipboard
How to use PassiveMode?
Hi Matteo,
It's possible to use the passive mode. I will give you an answer tonight.
Regards.
@matteocostantini By default, the FTP client is in passive mode (m_bActive is initialized to false), so there's nothing to do.
To use the active mode use SetActive(true), in active mode, the client will choose a port and the FTP server will initialize the connection (not recommended if there's a firewall).
This is my implementation, dont connect . i'm in UI environment.
How i can use?
My FTP credentials is valid ('m tryng with WINSCP!!)
in FTPCLient.cpp go in this rows else if (m_eSettingsFlags & ENABLE_LOG) m_oLog(StringFormat(LOG_ERROR_CURL_FILELIST_FORMAT, strRemoteFolder.c_str(), res, curl_easy_strerror(res)));
void BDImport::OnRunButton() { //m_pFTPClient = new CFTPClient(CFTPClient::LogFnCallback);
CFTPClient FTPClient([](const std::string& strLogMsg) { std::cout << strLogMsg << std::endl; });
CString host = _T("fqdnftp");
std::string stdHost = CT2CA(host);
CString user = _T("");
std::string stdUser = CT2CA(user);
CString pwd = _T("");
std::string stdpwd = CT2CA(pwd);
FTPClient.InitSession(stdHost, 6321, stdUser, stdpwd, CFTPClient::FTP_PROTOCOL::FTPES);
std::string strList;
FTPClient.List("/", strList, false);
I never tested the FTP Client with this protocol CFTPClient::FTP_PROTOCOL::FTPES.
If you are trying to access a normal FTP server (port 21), remove that parameter (it will default to FTP_PROTOCOL::FTP) or set the protocol to FTP_PROTOCOL::SFTP if you want to connect to an SFTP server (port 22).
Also, in a debugger, check that the string parameters are well encoded (I don't know if CT2CA is doing its job properly). And that "stdHost" doesn't contain any protocol scheme.
I'm not sure but to access secure servers, I think you need to set an SSL cert file with the static method SetSSLCertFile.
You can use this file : https://curl.haxx.se/ca/cacert.pem (from libcurl website)
and then CFTPClient::SetSSLCertFile("C:\\etc...............\\cacert.pem");
UPDATE : ignore this comment
@matteocostantini You can also compile with this preprocessor macro DEBUG_CURL, and use this method : static void SetCurlTraceLogDirectory(const std::string &strPath);
to specify a directory where debug logs will be stored. They will give you an information on why things are not working properly.
Also, don't forget to set a preprocessor macro WINDOWS as I believe you are not using the CMake scripts.
Regards.
@embeddedmz : I'm able to connect to my server with this instructions:
curl_easy_setopt(m_pCurlSession, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_easy_setopt(m_pCurlSession, CURLOPT_SSL_VERIFYHOST, FALSE);
curl_easy_setopt(m_pCurlSession, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_0);
curl_easy_setopt(m_pCurlSession, CURLOPT_FTP_SSL, CURLOPT_FTPSSLAUTH);
curl_easy_setopt(m_pCurlSession, CURLOPT_FTPSSLAUTH, CURLFTPAUTH_TLS);
Can you improve this calls in your ::Perform()?
First of all, to what kind of FTP servers are you connecting (SFTP, FTPES or FTPS). I know that the client work with SFTP but not the 2 others (FTPES, FTPS).
You can remove these 2 lines :
curl_easy_setopt(m_pCurlSession, CURLOPT_SSL_VERIFYPEER, 0);
curl_easy_setopt(m_pCurlSession, CURLOPT_SSL_VERIFYHOST, 0);
if you use this : curl_easy_setopt(m_pCurlSession, CURLOPT_CAINFO, "C:\....\cacert.pem");
In my previous comment I mistaken this for CFTPClient::SetSSLCertFile("C:\etc...............\cacert.pem"); it's missing in this client (but not in the httpclient-cpp). But your server must have a valid SSL certificate and not a quick & dirty one. Settings those 2 parameters to 0 is not good for all cases (security issues).
So, if you have the chance to add and test these getter/setters method :
// in .h static const std::string& GetCertificateFile() { return s_strCertificationAuthorityFile; } static void SetCertificateFile(const std::string& strPath) { s_strCertificationAuthorityFile = strPath; } //.... //SSL static std::string s_strCertificationAuthorityFile;
// in .cpp // just look to this https://github.com/embeddedmz/httpclient-cpp/blob/master/HTTP/HTTPClient.cpp and to the code that sets CURLOPT_CAINFO
In line 857 (if (m_eFtpProtocol == FTP_PROTOCOL::FTPS || m_eFtpProtocol == FTP_PROTOCOL::FTPES)
) , you can add :
curl_easy_setopt(m_pCurlSession, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_0);
curl_easy_setopt(m_pCurlSession, CURLOPT_FTP_SSL, CURLOPT_FTPSSLAUTH);
curl_easy_setopt(m_pCurlSession, CURLOPT_FTPSSLAUTH, CURLFTPAUTH_TLS);
and eventually remove curl_easy_setopt(m_pCurlSession, CURLOPT_USE_SSL, CURLUSESSL_ALL);
if it's not necessary
If everything is OK, create a pull request and I will merge your patches.
the connection function successfully only if i put curl_easy_setopt(m_pCurlSession, CURLOPT_USE_SSL, CURLUSESSL_ALL); curl_easy_setopt(m_pCurlSession, CURLOPT_SSL_VERIFYPEER, FALSE); curl_easy_setopt(m_pCurlSession, CURLOPT_SSL_VERIFYHOST, FALSE); curl_easy_setopt(m_pCurlSession, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_0); curl_easy_setopt(m_pCurlSession, CURLOPT_FTP_SSL, CURLOPT_FTPSSLAUTH); curl_easy_setopt(m_pCurlSession, CURLOPT_FTPSSLAUTH, CURLFTPAUTH_TLS);
The server is ftp with explicit autentication
@matteocostantini OK, I googled curl FTPS/FTPES and I found the following stuff :
https://stackoverflow.com/questions/32491790/php-curl-ftpes-w-explicit-tls-ssl => in the code, instead of prefixing the URL with ftps:// prefix it with ftp:// that should be sufficient.
https://curl.haxx.se/docs/manual.html (curl doc.) => FTPS : It is just like for FTP, but you may also want to specify and use SSL-specific options for certificates etc. Note that using FTPS:// as prefix is the "implicit" way as described in the standards while the recommended "explicit" way is done by using FTP:// and the --ftp-ssl option.
So, can you please try this fix and tell me if the example you posted in the beginning of this thread is working : In line 194, add "case FTP_PROTOCOL::FTPES:" so that in a FTPES session, the url will be prefixed with ftp:// and remove the case of lines 203 and 205 (old code prefixing the url with ftpes://)
That should work fine (I hope so).