📄 libcurl-tutorial.3
字号:
.IP "FTP Custom Commands"Not all protocols are HTTP-like, and thus the above may not help you whenyou want to make for example your FTP transfers to behave differently.Sending custom commands to a FTP server means that you need to send thecommands exactly as the FTP server expects them (RFC959 is a good guidehere), and you can only use commands that work on the control-connectionalone. All kinds of commands that requires data interchange and thus needsa data-connection must be left to libcurl's own judgment. Also be awarethat libcurl will do its very best to change directory to the targetdirectory before doing any transfer, so if you change directory (with CWDor similar) you might confuse libcurl and then it might not attempt totransfer the file in the correct remote directory.A little example that deletes a given file before an operation:.nf headers = curl_slist_append(headers, "DELE file-to-remove"); /* pass the list of custom commands to the handle */ curl_easy_setopt(easyhandle, CURLOPT_QUOTE, headers); curl_easy_perform(easyhandle); /* transfer ftp data! */ curl_slist_free_all(headers); /* free the header list */.fiIf you would instead want this operation (or chain of operations) to happen_after_ the data transfer took place the option to \fIcurl_easy_setopt(3)\fPwould instead be called CURLOPT_POSTQUOTE and used the exact same way.The custom FTP command will be issued to the server in the same order they areadded to the list, and if a command gets an error code returned back from theserver, no more commands will be issued and libcurl will bail out with anerror code (CURLE_QUOTE_ERROR). Note that if you use CURLOPT_QUOTE to sendcommands before a transfer, no transfer will actually take place when a quotecommand has failed.If you set the CURLOPT_HEADER to true, you will tell libcurl to getinformation about the target file and output "headers" about it. The headerswill be in "HTTP-style", looking like they do in HTTP.The option to enable headers or to run custom FTP commands may be useful tocombine with CURLOPT_NOBODY. If this option is set, no actual file contenttransfer will be performed..IP "FTP Custom CUSTOMREQUEST"If you do what list the contents of a FTP directory using your own defined FTPcommand, CURLOPT_CUSTOMREQUEST will do just that. "NLST" is the default onefor listing directories but you're free to pass in your idea of a goodalternative..SH "Cookies Without Chocolate Chips"In the HTTP sense, a cookie is a name with an associated value. A server sendsthe name and value to the client, and expects it to get sent back on everysubsequent request to the server that matches the particular conditionsset. The conditions include that the domain name and path match and that thecookie hasn't become too old.In real-world cases, servers send new cookies to replace existing one toupdate them. Server use cookies to "track" users and to keep "sessions".Cookies are sent from server to clients with the header Set-Cookie: andthey're sent from clients to servers with the Cookie: header.To just send whatever cookie you want to a server, you can use CURLOPT_COOKIEto set a cookie string like this: curl_easy_setopt(easyhandle, CURLOPT_COOKIE, "name1=var1; name2=var2;");In many cases, that is not enough. You might want to dynamically savewhatever cookies the remote server passes to you, and make sure those cookiesare then use accordingly on later requests.One way to do this, is to save all headers you receive in a plain file andwhen you make a request, you tell libcurl to read the previous headers tofigure out which cookies to use. Set header file to read cookies from withCURLOPT_COOKIEFILE.The CURLOPT_COOKIEFILE option also automatically enables the cookie parser inlibcurl. Until the cookie parser is enabled, libcurl will not parse orunderstand incoming cookies and they will just be ignored. However, when theparser is enabled the cookies will be understood and the cookies will be keptin memory and used properly in subsequent requests when the same handle isused. Many times this is enough, and you may not have to save the cookies todisk at all. Note that the file you specify to CURLOPT_COOKIEFILE doesn'thave to exist to enable the parser, so a common way to just enable the parserand not read able might be to use a file name you know doesn't exist.If you rather use existing cookies that you've previously received with yourNetscape or Mozilla browsers, you can make libcurl use that cookie file asinput. The CURLOPT_COOKIEFILE is used for that too, as libcurl willautomatically find out what kind of file it is and act accordingly.The perhaps most advanced cookie operation libcurl offers, is saving theentire internal cookie state back into a Netscape/Mozilla formatted cookiefile. We call that the cookie-jar. When you set a file name withCURLOPT_COOKIEJAR, that file name will be created and all received cookieswill be stored in it when \fIcurl_easy_cleanup(3)\fP is called. This enabledcookies to get passed on properly between multiple handles without anyinformation getting lost..SH "FTP Peculiarities We Need"FTP transfers use a second TCP/IP connection for the data transfer. This isusually a fact you can forget and ignore but at times this fact will comeback to haunt you. libcurl offers several different ways to custom how thesecond connection is being made.libcurl can either connect to the server a second time or tell the server toconnect back to it. The first option is the default and it is also what worksbest for all the people behind firewalls, NATs or IP-masquerading setups.libcurl then tells the server to open up a new port and wait for a secondconnection. This is by default attempted with EPSV first, and if that doesn'twork it tries PASV instead. (EPSV is an extension to the original FTP specand does not exist nor work on all FTP servers.)You can prevent libcurl from first trying the EPSV command by settingCURLOPT_FTP_USE_EPSV to FALSE.In some cases, you will prefer to have the server connect back to you for thesecond connection. This might be when the server is perhaps behind a firewallor something and only allows connections on a single port. libcurl theninforms the remote server which IP address and port number to connect to.This is made with the CURLOPT_FTPPORT option. If you set it to "-", libcurlwill use your system's "default IP address". If you want to use a particularIP, you can set the full IP address, a host name to resolve to an IP addressor even a local network interface name that libcurl will get the IP addressfrom.When doing the "PORT" approach, libcurl will attempt to use the EPRT and theLPRT before trying PORT, as they work with more protocols. You can disablethis behavior by setting CURLOPT_FTP_USE_EPRT to FALSE..SH "Headers Equal Fun"Some protocols provide "headers", meta-data separated from the normaldata. These headers are by default not included in the normal data stream,but you can make them appear in the data stream by setting CURLOPT_HEADER toTRUE.What might be even more useful, is libcurl's ability to separate the headersfrom the data and thus make the callbacks differ. You can for example set adifferent pointer to pass to the ordinary write callback by settingCURLOPT_WRITEHEADER.Or, you can set an entirely separate function to receive the headers, byusing CURLOPT_HEADERFUNCTION.The headers are passed to the callback function one by one, and you candepend on that fact. It makes it easier for you to add custom header parsersetc.\&"Headers" for FTP transfers equal all the FTP server responses. They aren'tactually true headers, but in this case we pretend they are! ;-).SH "Post Transfer Information" [ curl_easy_getinfo ].SH "Security Considerations"libcurl is in itself not insecure. If used the right way, you can use libcurlto transfer data pretty safely.There are of course many things to consider that may loosen up thissituation:.IP "Command Lines"If you use a command line tool (such as curl) that uses libcurl, and you giveoption to the tool on the command line those options can very likely get readby other users of your system when they use 'ps' or other tools to listcurrently running processes.To avoid this problem, never feed sensitive things to programs using commandline options..IP ".netrc"\&.netrc is a pretty handy file/feature that allows you to login quickly andautomatically to frequently visited sites. The file contains passwords inclear text and is a real security risk. In some cases, your .netrc is alsostored in a home directory that is NFS mounted or used on another networkbased file system, so the clear text password will fly through your networkevery time anyone reads that file!To avoid this problem, don't use .netrc files and never store passwords inplain text anywhere..IP "Clear Text Passwords"Many of the protocols libcurl supports send name and password unencrypted asclear text (HTTP Basic authentication, FTP, TELNET etc). It is very easy foranyone on your network or a network nearby yours, to just fire up a networkanalyzer tool and eavesdrop on your passwords. Don't let the fact that HTTPuses base64 encoded passwords fool you. They may not look readable at a firstglance, but they very easily "deciphered" by anyone within seconds.To avoid this problem, use protocols that don't let snoopers see yourpassword: HTTPS, FTPS and FTP-kerberos are a few examples. HTTP Digestauthentication allows this too, but isn't supported by libcurl as of thiswriting..IP "Showing What You Do"On a related issue, be aware that even in situations like when you haveproblems with libcurl and ask someone for help, everything you reveal in orderto get best possible help might also impose certain security relatedrisks. Host names, user names, paths, operating system specifics etc (not tomention passwords of course) may in fact be used by intruders to gainadditional information of a potential target.To avoid this problem, you must of course use your common sense. Often, youcan just edit out the sensitive data or just search/replace your trueinformation with faked data..SH "Multiple Transfers Using the multi Interface"The easy interface as described in detail in this document is a synchronousinterface that transfers one file at a time and doesn't return until itsdone.The multi interface on the other hand, allows your program to transfermultiple files in both directions at the same time, without forcing you touse multiple threads.To use this interface, you are better off if you first understand the basicsof how to use the easy interface. The multi interface is simply a way to makemultiple transfers at the same time, by adding up multiple easy handles in toa "multi stack".You create the easy handles you want and you set all the options just like youhave been told above, and then you create a multi handle with\fIcurl_multi_init(3)\fP and add all those easy handles to that multi handlewith \fIcurl_multi_add_handle(3)\fP.When you've added the handles you have for the moment (you can still add newones at any time), you start the transfers by call\fIcurl_multi_perform(3)\fP.\fIcurl_multi_perform(3)\fP is asynchronous. It will only execute as little aspossible and then return back control to your program. It is designed to neverblock. If it returns CURLM_CALL_MULTI_PERFORM you better call it again soon,as that is a signal that it still has local data to send or remote data toreceive.The best usage of this interface is when you do a select() on all possiblefile descriptors or sockets to know when to call libcurl again. This alsomakes it easy for you to wait and respond to actions on your own application'ssockets/handles. You figure out what to select() for by using\fIcurl_multi_fdset(3)\fP, that fills in a set of fd_set variables for youwith the particular file descriptors libcurl uses for the moment.When you then call select(), it'll return when one of the file handles signalaction and you then call \fIcurl_multi_perform(3)\fP to allow libcurl to dowhat it wants to do. Take note that libcurl does also feature some time-outcode so we advice you to never use very long timeouts on select() before youcall \fIcurl_multi_perform(3)\fP, which thus should be called unconditionallyevery now and then even if none of its file descriptors have signaledready. Another precaution you should use: always call\fIcurl_multi_fdset(3)\fP immediately before the select() call since thecurrent set of file descriptors may change when calling a curl function.If you want to stop the transfer of one of the easy handles in the stack, youcan use \fIcurl_multi_remove_handle(3)\fP to remove individual easyhandles. Remember that easy handles should be \fIcurl_easy_cleanup(3)\fPed.When a transfer within the multi stack has finished, the counter of runningtransfers (as filled in by \fIcurl_multi_perform(3)\fP) will decrease. Whenthe number reaches zero, all transfers are done.\fIcurl_multi_info_read(3)\fP can be used to get information about completedtransfers. It then returns the CURLcode for each easy transfer, to allow youto figure out success on each individual transfer..SH "SSL, Certificates and Other Tricks" [ seeding, passwords, keys, certificates, ENGINE, ca certs ].SH "Sharing Data Between Easy Handles" [ fill in ].SH "Footnotes".IP "[1]"libcurl 7.10.3 and later have the ability to switch over to chunkedTransfer-Encoding in cases were HTTP uploads are done with data of an unknownsize..IP "[2]"This happens on Windows machines when libcurl is built and used as aDLL. However, you can still do this on Windows if you link with a staticlibrary..IP "[3]"The curl-config tool is generated at build-time (on unix-like systems) andshould be installed with the 'make install' or similar instruction thatinstalls the library, header files, man pages etc.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -