1. 程式人生 > >用curl訪問HTTPS站點並登入(對HTTP返回的結果特別清楚)

用curl訪問HTTPS站點並登入(對HTTP返回的結果特別清楚)

      現在的網站為了加強安全性,都啟用了HTTPS協議。所謂HTTPS,也就是HTTP文字在SSL協議中傳輸。用curl命令列來測試HTTPS站點是個很有用的功能,寫點指令碼,就可以做功能測試。

      假定Ubuntu系統執行著一個HTTPS站點,用CppCMS編寫,Nginx配置了SSL證書,通過FastCGI和CppCMS編寫的後臺程序連線在一起。

第一步,安裝

apt-get install curl 

    我的Ubuntu是13.04, 因此安裝的curl版本很新,下面的命令檢查版本號和其他資訊:

curl -V  
curl 7.29.0 (x86_64-pc-linux-gnu) libcurl/7.29.0 OpenSSL/1.0.1c zlib/1.2.7 libidn/1.25 librtmp/2.3  
Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtmp rtsp smtp smtps telnet tftp  

     我們可以看到啟用了SSL, 並且openssl版本是1.0.1c。

第二步,訪問HTTP站點

curl http://www.baidu.com  
<!DOCTYPE html><!--STATUS OK--><html><head><meta http-equiv="content-type" content="text/html;charset=utf-8"><title>百度一下,你就知道<unction(){var _t=new Date().getTime();document.cookie = "WWW_ST=" + _t +";expires=" + new Date(_t + 10000).toGMTString()})}catch(e){}</script></html><!--b5d54ba904675fbf-->  

    返回了百度的網頁內容。內容太多,裁剪了。

第三步,檢視詳細資訊,用-v引數。

 curl -v http://www.baidu.com  
* About to connect() to www.baidu.com port 80 (#0)  
*   Trying 61.135.169.125...  
* Connected to www.baidu.com (61.135.169.125) port 80 (#0)  
> GET / HTTP/1.1  
> User-Agent: curl/7.29.0  
> Host: www.baidu.com  
> Accept: */*  
>   
< HTTP/1.1 200 OK  
< Date: Wed, 03 Jul 2013 13:55:45 GMT  
< Server: BWS/1.0  
< Content-Length: 10437  
< Content-Type: text/html;charset=utf-8  
< Cache-Control: private  
< Set-Cookie: BDSVRTM=24; path=/  
< Set-Cookie: H_PS_PSSID=2757_1457_2704_2726_1788_2249_2702; path=/; domain=.baidu.com  
< Set-Cookie: BAIDUID=5E81F8E70C5DE6EDB5C24088E3E56359:FG=1; expires=Wed, 03-Jul-43 13:55:45 GMT; path=/; domain=.baidu.com  
< Expires: Wed, 03 Jul 2013 13:55:45 GMT  
< P3P: CP=" OTI DSP COR IVA OUR IND COM "  
< Connection: Keep-Alive  
<   
<!DOCTYPE html><!--STATUS OK--><html><head><meta http-equiv="content-type" content="text/html;charset=utf-8"><title>百度一下,你就知道</title><style >html,body{height:100%}html{overflow-y:auto}#wrapper{position:relative;_position:;min-height:100%}#content{padding-bottom:100px;text-align:center}#ftCon{height:100px;position:absolute;bottom:44px;text-align:center;width:100%;margin:0 auto;z-index:0;overflow:hidden}#ftConw{width:720px;margin:0 auto}body{font:12px arial;text-align:;background:#fff}body,p,form,ul,li{margin:0;padding:0;list-style:none}body,form,#fm{position:relative}td{text-align:left}img{border:0}a{color:#00c}a:active{color:#f60}#u{color:#999;padding:4px 10px 5px 0;text-align:right}#u a{margin:0 5px}#u .reg{margin:0}#m{width:720px;margin:0 auto}#nv a,#nv b,.btn,#lk{font-size:14px}#fm{padding-left:110px;text-align:left;z-index:1}input{border:0;padding:0}#nv{height:19px;font-size:16px;margin:0 0 4px;text-alig  

      這樣詳細的資訊都顯示出來了。-v引數很有用,一般除錯時都開啟。

      如果只想檢視頭部資訊,用-i代替-v.

第四步,訪問本地HTTPS站點

curl --insecure https://localhost/your_site/login_page  
  
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">  
<html xmlns="http://www.w3.org/1999/xhtml">  
  <head>  
    <meta http-equiv="content-type" content="text/html; charset=utf-8">  
      <meta http-equiv="pragma" content="no-cache">  
    <meta http-equiv="cache-control" content="no-cache">  

     ---insecure表示忽略校驗步驟。

    我試過用--cacert選項指定server.crt檔案,也就是我的nginx使用的那個檔案。但是報錯。所以直接忽略算了。

第五步,呼叫HTTPS的login API登入

curl -v --insecure -d "[email protected]&pwd=123456&language=en" https://localhost/your_site/login  
* About to connect() to localhost port 443 (#0)  
*   Trying 127.0.0.1...  
* Connected to localhost (127.0.0.1) port 443 (#0)  
* successfully set certificate verify locations:  
*   CAfile: none  
  CApath: /etc/ssl/certs  
* SSLv3, TLS handshake, Client hello (1):  
* SSLv3, TLS handshake, Server hello (2):  
* SSLv3, TLS handshake, CERT (11):  
* SSLv3, TLS handshake, Server key exchange (12):  
* SSLv3, TLS handshake, Server finished (14):  
* SSLv3, TLS handshake, Client key exchange (16):  
* SSLv3, TLS change cipher, Client hello (1):  
* SSLv3, TLS handshake, Finished (20):  
* SSLv3, TLS change cipher, Client hello (1):  
* SSLv3, TLS handshake, Finished (20):  
* SSL connection using ECDHE-RSA-AES256-SHA  
* Server certificate:  
*    subject: C=AU; ST=Some-State; O=Internet Widgits Pty Ltd  
*    start date: 2013-06-02 07:24:53 GMT  
*    expire date: 2014-06-02 07:24:53 GMT  
*    issuer: C=AU; ST=Some-State; O=Internet Widgits Pty Ltd  
*    SSL certificate verify result: self signed certificate (18), continuing anyway.  
> POST /your_site/login HTTP/1.1  
> User-Agent: curl/7.29.0  
> Host: localhost  
> Accept: */*  
> Content-Length: 51  
> Content-Type: application/x-www-form-urlencoded  
>   
* upload completely sent off: 51 out of 51 bytes  
< HTTP/1.1 200 OK  
< Server: nginx/1.5.1  
< Date: Wed, 03 Jul 2013 14:02:38 GMT  
< Content-Type: text/html; charset=utf-8  
< Transfer-Encoding: chunked  
< Connection: keep-alive  
< X-Powered-By: CppCMS/1.0.3  
< Set-Cookie: cml_session=518b7fc5117e87bce28f2444; Max-Age=36000; Path=/; Version=1  
<   
* Connection #0 to host localhost left intact  
{"message":"Login succeeded!","status":0,"value":""}  

    -d "...&..." 的引數是通過POST方法傳送引數。服務端最終回覆一個JSON格式的字串,表示登入成功。並且拿到了cml_session的值,也就是cookie.

第六步,用cookie訪問HTTP網頁。後面的網頁只需要HTTP訪問,提供正確的cookie即可。

curl -v --cookie "cml_session=518b7fc5117e87bce28f2444" http://localhost/your_site/home  
* About to connect() to localhost port 80 (#0)  
*   Trying 127.0.0.1...  
* Connected to localhost (127.0.0.1) port 80 (#0)  
> GET /your_site/home HTTP/1.1  
> User-Agent: curl/7.29.0  
> Host: localhost  
> Accept: */*  
> Cookie: cml_session=518b7fc5117e87bce28f2444  
>   
< HTTP/1.1 200 OK  
< Server: nginx/1.5.1  
< Date: Wed, 03 Jul 2013 14:06:43 GMT  
< Content-Type: text/html; charset=utf-8  
< Transfer-Encoding: chunked  
< Connection: keep-alive  
< X-Powered-By: CppCMS/1.0.3  
<   
  
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">  
<html xmlns="http://www.w3.org/1999/xhtml">  
  <head>  
    <meta http-equiv="content-type" content="text/html; charset=utf-8">  
      <meta http-equiv="pragma" content="no-cache">  
    <meta http-equiv="cache-control" content="no-cache">  
      <meta http-equiv="expires" content="0">  
        <title>CML Cloud</title>  
        <link type="text/css" href="../style/reset.css" rel="stylesheet"/>  
        <link type="text/css" href="../style/style.css" rel="stylesheet"/>