文章分两部分
首先先容cURL的用法;实现一个定时上传日志文件的一个大略的程序。观点cURL 是常用的命令行工具,用来要求 Web 做事器。它的名字便是客户端(client)的 URL 工具的意思。
cURL 的原作者是 Daniel Stenberg (目前是 cURL 的核心开拓者),同时也是 IETF HTTPbis 事情组的资深成员。Daniel 在 1998 年创建了 curl 项目,他编写了最初的 curl 版本,并创建了 libcurl 库。到目前为止,代码仓库包括的 24000 次 commit 有超过一半是 Daniel 本人提交的,他依然是项目的核心开拓者。Daniel 表示已将 curl 视为自己的孩子。
作为一款强力工具,支持的协议包括 (DICT, FILE, FTP, FTPS, GOPHER, HTTP, HTTPS, IMAP, IMAPS, LDAP, LDAPS, POP3, POP3S, RTMP, RTSP, SCP, SFTP, SMTP, SMTPS, TELNET and TFTP),还支持POST、cookies、认证、从指定偏移处下载部分文件等功能,具有用户代理字符串、限速、文件大小、进度条、cookie支持、用户认证、断点续传等特色。
一、命令的安装sudoapt-getinstallcurl
二、cURL命令语法:
curl[options][URL...]
三、URL格式
URL的格式定义要参考 RFC 1808 。
地址:http://www.w3.org/Addressing/rfc1808.txt《RelativeUniformResourceLocators》
URL由三部分组成:资源类型、存放资源的主机域名、资源文件名。 也可认为由4部分组成:协议、主机、端口、路径URL的一样平常语法格式为:
protocol://hostname[:port]/path/[;parameters][?query]#fragment
(带方括号[]的为可选项)。
指定利用的传输协议,下表列出 protocol 属性的有效方案名称。 最常用的是HTTP协议,它也是WWW中运用最广的协议。
file 资源是本地打算机上的文件。格式file:///,把稳后边应是三个斜杠。ftp 通过 FTP访问资源。格式 FTP://gopher 通过 Gopher 协议访问该资源。http 通过 HTTP 访问该资源。 格式 HTTP://https 通过安全的 HTTPS 访问该资源。 格式 HTTPS://mailto 资源为电子邮件地址,通过 SMTP 访问。 格式 mailto:MMS 通过 支持MMS(流媒体)协议的播放该资源。(代表软件:Windows Media Player)格式 MMS://ed2k 通过 支持ed2k(专用下载链接)协议的P2P软件访问该资源。(代表软件:电驴) 格式 ed2k://Flashget 通过 支持Flashget:(专用下载链接)协议的P2P软件访问该资源。(代表软件:快车) 格式 Flashget://thunder 通过 支持thunder(专用下载链接)协议的P2P软件访问该资源。(代表软件:迅雷) 格式 thunder://news 通过 NNTP 访问该资源。是指存放资源的做事器的域名系统(DNS) 主机名或 IP 地址。有时,在主机名前也可以包含连接到做事器所需的用户名和密码(格式:username:password@hostname)。
整数,可选,省略时利用方案的默认端口,各种传输协议都有默认的端口号,如http的默认端口为80。如果输入时省略,则利用默认端口号。有时候出于安全或其他考虑,可以在做事器上对端口进行重定义,即采取非标准端口号,此时,URL中就不能省略端口号这一项。
由零或多个“/”符号隔开的字符串,一样平常用来表示主机上的一个目录或文件地址。
这是用于指定分外参数的可选项。
可选,用于给动态网页(如利用CGI、ISAPI、PHP/JSP/ASP/ASP.NET等技能制作的网页)通报参数,可有多个参数,用“&”符号隔开,每个参数的名和值用“=”符号隔开。
字符串,用于指定网络资源中的片断。例如一个网页中有多个名词阐明,可利用fragment直接定位到某一名词阐明。
四、curl命令参数详解:由于linux curl功能十分强大,以是命令参数十分多,下表只筛选出来部分常用的参数,更多参数请运行“man curl”命令查看。
参数功能-a/--append上传文件时,附加到目标文件-A/--user-agent设置用户代理发送给做事器-anyauth可以利用“任何”身份验证方法-b/--cookie <name=string/file>cookie字符串或文件读取位置--basic利用HTTP基本验证-B/--use-ascii利用ASCII /文本传输-c/--cookie-jar操作结束后把cookie写入到这个文件中-C/--continue-at断点续转-d/--dataHTTP POST办法传送数据--data-ascii以ascii的办法post数据--data-binary以二进制的办法post数据--negotiate利用HTTP身份验证--digest利用数字身份验证--disable-eprt禁止利用EPRT或LPRT--disable-epsv禁止利用EPSV-D/--dump-header把header信息写入到该文件中--egd-file为随机数据(SSL)设置EGD socket路径--tcp-nodelay利用TCP_NODELAY选项-e/--referer来源网址-E/--cert <cert[:passwd]>客户端证书文件和密码 (SSL)--cert-type证书文件类型 (DER/PEM/ENG) (SSL)--key私钥文件名 (SSL)--key-type私钥文件类型 (DER/PEM/ENG) (SSL)--pass私钥密码 (SSL)--engine加密引擎利用 (SSL). "--engine list" for list--cacertCA证书 (SSL)--capathCA目录 (made using c_rehash) to verify peer against (SSL)--ciphersSSL密码--compressed哀求返回是压缩的形势 (using deflate or gzip)--connect-timeout设置最大要求韶光--create-dirs建立本地目录的目录层次构造--crlf上传是把LF转变成CRLF-f/--fail连接失落败时不显示http缺点--ftp-create-dirs如果远程目录不存在,创建远程目录--ftp-method [multicwd/nocwd/singlecwd]掌握CWD的利用--ftp-pasv利用 PASV/EPSV 代替端口--ftp-skip-pasv-ip利用PASV的时候,忽略该IP地址--ftp-ssl考试测验用 SSL/TLS 来进行ftp数据传输--ftp-ssl-reqd哀求用 SSL/TLS 来进行ftp数据传输-F/--form <name=content>仿照http表单提交数据--form-string <name=string>仿照http表单提交数据-g/--globoff禁用网址序列和范围利用{}和[]-G/--get以get的办法来发送数据-H/--header自定义头信息通报给做事器--ignore-content-length忽略的HTTP头信息的长度-i/--include输出时包括protocol头信息-I/--head只显示要求头信息-j/--junk-session-cookies读取文件进忽略session cookie--interface利用指定网络接口/地址--krb4利用指定安全级别的krb4-k/--insecure许可不该用证书到SSL站点-K/--config指定的配置文件读取-l/--list-only列出ftp目录下的文件名称--limit-rate设置传输速率--local-port逼迫利用本地端口号-m/--max-time设置最大传输韶光--max-redirs设置最大读取的目录数--max-filesize设置最大下载的文件总量-M/--manual显示全手动-n/--netrc从netrc文件中读取用户名和密码--netrc-optional利用 .netrc 或者 URL来覆盖-n--ntlm利用 HTTP NTLM 身份验证-N/--no-buffer禁用缓冲输出-o/--output把输出写到该文件中-O/--remote-name把输出写到该文件中,保留远程文件的文件名-p/--proxytunnel利用HTTP代理--proxy-anyauth选择任一代理身份验证方法--proxy-basic在代理上利用基本身份验证--proxy-digest在代理上利用数字身份验证--proxy-ntlm在代理上利用ntlm身份验证-P/--ftp-port利用端口地址,而不是利用PASV-q作为第一个参数,关闭 .curlrc-Q/--quote文件传输前,发送命令到做事器-r/--range检索来自HTTP/1.1或FTP做事器字节范围--range-file读取(SSL)的随机文件-R/--remote-time在本地天生文件时,保留远程文件韶光--retry传输涌现问题时,重试的次数--retry-delay传输涌现问题时,设置重试间隔韶光--retry-max-time传输涌现问题时,设置最大重试韶光-s/--silent静默模式。不输出任何东西-S/--show-error显示缺点--socks4 <host[:port]>用socks4代理给定主机和端口--socks5 <host[:port]>用socks5代理给定主机和端口--stderr-t/--telnet-option <OPT=val>Telnet选项设置--trace对指定文件进行debug--trace-asciiLike --跟踪但没有hex输出--trace-time跟踪/详细输出时,添加韶光戳-T/--upload-file上传文件--urlSpet URL to work with-u/--user <user[:password]>设置做事器的用户和密码-U/--proxy-user <user[:password]>设置代理用户名和密码-w/--write-out [format]什么输出完成后-x/--proxy <host[:port]>在给定的端口上利用HTTP代理-X/--request指定什么命令-y/--speed-time放弃限速所要的韶光,默认为30-Y/--speed-limit停滞传输速率的限定,速率韶光
五、Linux curl命令退出码:下面是linux curl命令的缺点代码和她们的相应的缺点,命令实行缺点的时候可以通过缺点码来查看出错缘故原由,方便开拓调试。
退 出 码缺点描述1Unsupported protocol. This build of curl has no support for this protocol.2Failed to initialize.3URL malformed. The syntax was not correct.5Couldn't resolve proxy. The given proxy host could not be resolved.6Couldn't resolve host. The given remote host was not resolved.7Failed to connect to host.8FTP weird server reply. The server sent data curl couldn't parse.9FTP access denied. The server denied login or denied access to the particular resource or directory you wanted to reach. Most often you tried to change to a directory that doesn't exist on the server.11FTP weird PASS reply. Curl couldn't parse the reply sent to the PASS request.13FTP weird PASV reply, Curl couldn't parse the reply sent to the PASV request.14FTP weird 227 format. Curl couldn't parse the 227-line the server sent.15FTP can't get host. Couldn't resolve the host IP we got in the 227-line.17FTP couldn't set binary. Couldn't change transfer method to binary.18Partial file. Only a part of the file was transferred.19FTP couldn't download/access the given file, the RETR (or similar) command failed.21FTP quote error. A quote command returned error from the server.22HTTP page not retrieved. The requested url was not found or returned another error with the HTTP error code being 400 or above. This return code only appears if -f/--fail is used.23Write error. Curl couldn't write data to a local filesystem or similar.25FTP couldn't STOR file. The server denied the STOR operation, used for FTP uploading.26Read error. Various reading problems.27Out of memory. A memory allocation request failed.28Operation timeout. The specified time-out period was reached according to the conditions.30FTP PORT failed. The PORT command failed. Not all FTP servers support the PORT command, try doing a transfer using PASV instead!31FTP couldn't use REST. The REST command failed. This command is used for resumed FTP transfers.33HTTP range error. The range "command" didn't work.34HTTP post error. Internal post-request generation error.35SSL connect error. The SSL handshaking failed.36FTP bad download resume. Couldn't continue an earlier aborted download.37FILE couldn't read file. Failed to open the file. Permissions?38LDAP cannot bind. LDAP bind operation failed.39LDAP search failed.41Function not found. A required LDAP function was not found.42Aborted by callback. An application told curl to abort the operation.43Internal error. A function was called with a bad parameter.45Interface error. A specified outgoing interface could not be used.47Too many redirects. When following redirects, curl hit the maximum amount.48Unknown TELNET option specified.49Malformed telnet option.51The peer's SSL certificate or SSH MD5 fingerprint was not ok.52The server didn't reply anything, which here is considered an error.53SSL crypto engine not found.54Cannot set SSL crypto engine as default.55Failed sending network data.56Failure in receiving network data.58Problem with the local certificate.59Couldn't use specified SSL cipher.60Peer certificate cannot be authenticated with known CA certificates.61Unrecognized transfer encoding.62Invalid LDAP URL.63Maximum file size exceeded.64Requested FTP SSL level failed.65Sending the data requires a rewind that failed.66Failed to initialize SSL Engine.67The user name, password, or similar was not accepted and curl failed to log in.68File not found on TFTP server.69Permission problem on TFTP server.70Out of disk space on TFTP server.71Illegal TFTP operation.72Unknown TFTP transfer ID.73File already exists (TFTP).74No such user (TFTP).75Character conversion failed.76Character conversion functions required.77Problem with reading the SSL CA cert (path? access rights?).78The resource referenced in the URL does not exist.79An unspecified error occurred during the SSH session.80Failed to shut down the SSL connection.82Could not load CRL file, missing or wrong format (added in 7.19.0).83Issuer check failed (added in 7.19.0).XXMore error codes will appear here in future releases. The existing ones are meant to never change.
六、用法演示:为节省篇幅,部分操作不再贴上实行结果。
直接在curl命令后加上网址,就可以看到网页源码。我们以网址www.sina.com为例(选择该网址,紧张由于它的网页代码较短):
root@ubuntu:/home/peng#curlwww.sohu.com<html><head><title>307TemporaryRedirect</title></head><bodybgcolor="white"><center><h1>307TemporaryRedirect</h1></center><hr><center>nginx</center></body></html>
实行结果显示 307 Temporary Redirect,解释该网址须要重定向。
如果要把这个网页保存下来,可以利用-o参数,这就相称于利用wget命令了。
curl-o[文件名]www.sohu.com
有的网址是自动跳转的。利用-L参数,curl就会跳转到新的网址。
curl-Lwww.sohu.com
键入上面的命令,结果就自动跳转为www.sohu.com.cn。
-i参数可以显示http response的头信息,连同网页代码一起。
root@ubuntu:/home/peng/driver/test#curl-iwww.sohu.comHTTP/1.1307TemporaryRedirectContent-Type:text/htmlContent-Length:180Connection:keep-aliveServer:nginxDate:Tue,25Aug202010:10:54GMTLocation:https://www.sohu.com/FSS-Cache:from9790436.18244590.10468709FSS-Proxy:Poweredby2384755.3433341.3062915<html><head><title>307TemporaryRedirect</title></head><bodybgcolor="white"><center><h1>307TemporaryRedirect</h1></center><hr><center>nginx</center></body></html>
-I参数则是只显示http response的头信息。
-v参数可以显示一次http通信的全体过程,包括端口连接和http request头信息。
root@ubuntu:/home/peng/driver/test#curl-vwww.sohu.comAbouttoconnect()towww.sohu.comport80(#0)Trying240e:83:201:3700::5...connected>GET/HTTP/1.1>User-Agent:curl/7.22.0(i686-pc-linux-gnu)libcurl/7.22.0OpenSSL/1.0.1zlib/1.2.3.4libidn/1.23librtmp/2.3>Host:www.sohu.com>Accept:/><HTTP/1.1307TemporaryRedirect<Content-Type:text/html<Content-Length:180<Connection:keep-alive<Server:nginx<Date:Tue,25Aug202010:11:49GMT<Location:https://www.sohu.com/<FSS-Cache:from9855973.18375663.10534247<FSS-Proxy:Poweredby2450292.3564414.3128453<<html><head><title>307TemporaryRedirect</title></head><bodybgcolor="white"><center><h1>307TemporaryRedirect</h1></center><hr><center>nginx</center></body></html>Connection#0tohostwww.sohu.comleftintactClosingconnection#0
如果你以为上面的信息还不足,那么下面的命令可以查看更详细的通信过程。
curl--traceoutput.txtwww.sohu.com
或者
curl--trace-asciioutput.txtwww.sohu.com
运行后,请打开output.txt文件查看。
发送表单信息有GET和POST两种方法。GET方法相对大略,只要把数据附在网址后面就行。
curlexample.com/form.cgi?data=xxx
POST方法必须把数据和网址分开,curl就要用到--data参数。
curl-XPOST--data"data=xxx"example.com/form.cgi
如果你的数据没有经由表单编码,还可以让curl为你编码,参数是--data-urlencode。
curl-XPOST--data-urlencode"date=April1"example.com/form.cgi
curl默认的HTTP动词是GET,利用-X参数可以支持其他动词。
curl-XPOSTwww.example.comcurl-XDELETEwww.example.com
假定文件上传的表单是下面这样:
<formmethod="POST"enctype='multipart/form-data'action="upload.cgi"><inputtype=filename=upload><inputtype=submitname=pressvalue="OK"></form>
你可以用curl这样上传文件:
curl--formupload=@localfilename--formpress=OK[URL]
有时你须要在http request头信息中,供应一个referer字段,表示你是从哪里跳转过来的。
curl--refererhttp://www.example.comhttp://www.example.com
这个字段是用来表示客户真个设备信息。做事器有时会根据这个字段,针对不同设备,返回不同格式的网页,比如手机版和桌面版。
iPhone4的User Agent是
Mozilla/5.0(iPhone;U;CPUiPhoneOS4_0likeMacOSX;en-us)AppleWebKit/532.9(KHTML,likeGecko)Version/4.0.5Mobile/8A293Safari/6531.22.7
curl可以这样仿照:
curl--user-agent"[UserAgent]"[URL]
利用--cookie参数,可以让curl发送cookie。
curl--cookie"name=xxx"www.example.com
至于详细的cookie的值,可以从http response头信息的Set-Cookie字段中得到。
-c cookie-file可以保存做事器返回的cookie到文件,-b cookie-file可以利用这个文件作为cookie信息,进行后续的要求。
curl-ccookieshttp://example.comcurl-bcookieshttp://example.com
有时须要在http request之中,自行增加一个头信息。--header参数就可以起到这个浸染。
$curl--header"Content-Type:application/json"http://example.com
利用curl选项 -u 可以完成HTTP或者FTP的认证,可以指定密码,也可以不指定密码在后续操作中输入密码:
curl-uuser:pwdhttp://man.linuxde.netcurl-uuserhttp://man.linuxde.net
curlftp://www.xxx.com/--username:passwdcurlftp://www.xxx.com/–uname:passwd#简洁写法curlftp://name:passwd@www.xxx.com#简洁写法2
例如:在IP地址192.168.43.117上搭建FTP做事器,并设置用户名为user,密码为123456现在我们要显示做事器上根目录下的所有文件信息,命令如下:
curl-uuser:123456ftp://192.168.43.117
实行结果如下:
简洁写法:
curlftp://user:123456@192.168.43.117
实行结果如下:
curlftp://www.xxx.com–uname:passwd-s
格式
curlftp://www.xxx.com/size.zip–uname:passwd-osize.zip
示例如下: 从做事器的根目录下下载文件test.c,保存到本地,本地文件名也为test.c。 【把稳】如果没有-o选项,程序会吧数据流定向到stdout,即直接把文件内容显示到终端上。
curlftp://user:123456@192.168.43.117/test.c-otest.c
实行结果如下:
简洁模式
curl-uuser:123456ftp://192.168.43.117/list.h-olist.h
实行结果如下:
curl–uname:passwd-Tsize.mp3ftp://www.xxx.com/mp3/
举例如下:
curl-uuser:123456ftp://192.168.43.117/-Tlist.h
可以看到文件并没有上传成功,返回缺点码是25,参考第五章
25FTPcouldn'tSTORfile.TheserverdeniedtheSTORoperation,usedforFTPuploading.
可知,是由于做事器没有授予存储的权限,以是设置做事器的write权限即可。
在这里插入图片描述
curl–uname:passwdftp://www.xxx.com/-X'DELEmp3/size.mp3'
curl–uname:passwdftp://www.xxx.com/img/[1-10].gif–O#O字母大写
curl–uname:passwdftp://www.xxx.com/img/[one,two,three].jpg–O#O字母大写
六、实现日志文件定时上传
在这里插入图片描述
首先记录当前log文件韶光,并记录到全局变量last_mtime中。
读取文件末了修正韶光,并和last_mtime进行比较,如果相同就返回0,不同就返回1.
将当前的日志文件拷贝成备份文件,备份文件名字加上当前韶光。
得到对应文件的属性信息,存放到struct stat构造体变量中。
实行参数中字符串对应的命令
/ Copyright (C) 公众年夜众号: yikoulinux /#include <sys/stat.h>#include <stdio.h>#include <stdlib.h>#include <unistd.h>#include <time.h> typedef struct stat ST;unsigned long last_mtime;/用户名密码暂时写去世,实际该当保存在配置文件/char name[32]="user";char pass[32] ="123456";char ip[32] ="192.168.43.117";char filename[32]="t.log";char dstfile[256] ={0};int init(void){ //准备构造体 ST status; //调用stat函数 int res = stat(filename,&status); if(-1 == res) { perror("error:open file fail\n"); return 0; } last_mtime = status.st_mtime; printf("init time:%s \n",ctime(&last_mtime)); return 1;} int check_file_change(void){ //准备构造体 ST status; //调用stat函数 int res = stat(filename,&status); if(-1 == res) { perror("error:open file fail\n"); return 0; }// printf("old:%s new:%s",ctime(&last_mtime),ctime(&status.st_mtime)); if(last_mtime == status.st_mtime) { printf("file not change\n"); return 0; }else{ printf("file updated\n"); last_mtime = status.st_mtime; return 1; }}void file_name_add_time(void){ ST status; time_t t; struct tm tblock; char cmd[1024]={0}; t = time(NULL); tblock = localtime(&t); sprintf(dstfile,"t-%d-%d-%d-%d-%d-%d.log", tblock->tm_year+1900, tblock->tm_mon, tblock->tm_mday, tblock->tm_hour, tblock->tm_min, tblock->tm_sec); sprintf(cmd,"cp %s %s",filename,dstfile);// printf("cdm=%s\n",cmd); system(cmd);}int main(void){ char cmd[1024]={0}; init(); while(1) { if(check_file_change() == 1) { file_name_add_time(); sprintf(cmd,"curl -u %s:%s ftp://%s/ -T %s",name,pass,ip,dstfile); // printf("cdm=%s\n",cmd); system(cmd); unlink(dstfile); } sleep(10); }}
第一步:
由于log文件没有被修正过,以是程序不会上传。
第二步:手动输入字符串 yikoulinux 到日志文件 t.log中。
第三步: 由于文件发生了改变,以是打印“file updated”,同时可以看到curl上传文件的log信息。
以下是FTP做事器的根目录,可以看到,上传的日志文件:t-2020-7-26-1-19-45.log。
配置信息,直接在代码中写去世,常日该当从配置文件中读取,为方便读者阅读,本代码没有增加该功能;FTP做事器搭建,本文没有解释,干系文件比较多,大家可以自行搜索,一口君用的是File zilla;常日这种须要永劫光运行的程序,须要设置成守护进程,本文没有添加相应功能,读者可以自行搜索。如果强烈哀求可以单开一篇详细先容。代码中time的管理函数,请读者自行搜索干系文章。curl也供应了干系的函数库curl.lib,如果要实现更灵巧的功能可以利用对应的api。之以是先把文件拷贝成备份文件,紧张是考虑其他模块随时可能修正日志文件,起到一定保护浸染。
想和博主互换,请关注"大众年夜众号「一口Linux」