Idhttp组件用的比较多,使用中的问题也很多。目前很多网站如百度都禁止indy组件访问。因此必须注意UserAgent和http1.1的设置。.
以下是Delphi的代码:
IdHTTP1.Request.Connection:='Keep-Alive';
IdHTTP1.Request.UserAgent:='Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; Maxthon)';
IdHTTP1.Request.ContentType:='application/x-www-form-urlencoded';
IdHTTP1.Request.Referer:='http://www.xxx.com';
IdHTTP1.Request.Accept:='image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, application/x-shockwave-flash, application/vnd.ms-excel, application/msword, */*';
IdHTTP1.Request.AcceptLanguage:='zh-cn';
IdHTTP1.Request.AcceptEncoding:='gzip, deflate';
IdHTTP1.Request.CacheControl:='no-cache';
IdHTTP1.ReadTimeout:=60000;
IdHTTP1.HTTPOptions:=IdHTTP1.HTTPOptions+[hoKeepOrigProtocol]; //关键这行
IdHTTP1.ProtocolVersion:=pv1_1;
sHtml:=IdHTTP1.Post('http://www.xxx.com/login.asp',sPost);
以下c++builder 采用 dHTTP1+TIdCookieManager组件登录代码:
过程大体如下:
Cookie = new TIdCookieManager(this);
Cookie->OnNewCookie = &CookieNewCookie;
IOSocket = new TIdSSLIOHandlerSocket(this);
HTTP = new TIdHTTP(this);
HTTP->ReadTimeout = 5000;
HTTP->AllowCookies = true;
HTTP->IOHandler = IOSocket;
HTTP->CookieManager = Cookie;
HTTP->ProtocolVersion = pv1_1;
HTTP->HTTPOptions << hoKeepOrigProtocol << hoInProcessAuth << hoForceEncodeParams;
在OnNewCookie事件中保存ACookie.
void __fastcall TfrmFireWall::CookieNewCookie(TObject *ASender,
TIdCookieRFC2109 *ACookie, bool &VAccept)
{
int pos = ACookie->CookieText.Pos(";");
if ( pos > 0 )
FSessionID = ACookie->CookieText.SubString( 1, pos -1 );
else
FSessionID = ACookie->CookieText;
}
//登录:
TStringStream *Response;
TStringStream *Source;
bool rSuccess;
AnsiString URL, User, Password;
User = usr;
Password = pwd;
Source = new TStringStream("");
Response = new TStringStream("");
HTTP->ReadTimeout = 50000;
try{
try
{
URL = FUrl + LOGIN_CGI;
Source->WriteString("username=" + User + "&password=" + Password);
HTTP->Post( URL, Source, Response );
Response->Position = 0;
Rtl = Response->DataString;
if ( Rtl == "" ){
rSuccess = true;
}else{
rSuccess = false;
if ( Rtl.Pos("系统繁忙") > 0 )
{
Status = "系统繁忙,请稍后登录";
}
else
{
Status = "登陆失败!请检查用户名、密码是否正确";
}
}
}
catch( Exception &exception )
{
Status = exception.Message;
rSuccess = false;
Timer1->Enabled = false;
}
} __finally{
delete Source;
delete Response;
}
//后续操作
AnsiString URL, LinkHead;
TStringList *Source;
TStringStream* Response;
URL = FUrl + cgi;
Source = new TStringList;
Source->Text = Para;
Response->Position = 0;
try{
HTTP->ReadTimeout = OverTimeInterval;
HTTP->Request->CustomHeaders->Add("Cookie:" + FSessionID);
HTTP->Post( URL, Source, Response );
if ( Response->DataString.Pos("登录过时") > 0 )
{
Timer1->Enabled = false;
AnsiString ErrInfo = "登录过时,请重新登录";
}
}
catch(Exception &exception){
if ( exception.Message == "Read Timeout" )
{
Application->MessageBox( exception.Message.c_str(), "信息提示", MB_OK | MB_ICONWARNING );
}else if ( exception.Message.Pos("400 Bad Request") > 0 )
{
}else{
}
}
delete Source;