我试图将我的代码从Delphi 2007移植到Delphi XE(还没有更新1)。我遇到的问题是,在使用Delphi XE发送第二个GET消息后,我收到了服务器不同的响应。
HTML格式的信息显示我的会话已过期。但是,在Delphi 2007下,同样的代码一直可以正常工作。我在互联网上搜索了相关信息,并发现我应该使用CookieManager?
问题在于,我在Delphi 2007中没有使用任何CookieManager,在Delphi XE中分配了一个,但我的代码结果并没有改变。我仍然收到关于过期会话的消息。
我还能尝试什么?
更新:我发现Indy 10存在cookie问题,但已经修复。
我下载了Indy10_4722快照,但错误仍然存在。
更新2-提供的代码
因此,我准备了一个示例代码。这与Delphi(2007和XE)兼容。但是要在2007年之前编译它,您需要拥有GraphicEx库。
该代码连接到真实服务器,加载安全图像并在窗体上显示图像。将图像中的字符重写到编辑框中,然后关闭窗体。这就是测试它所需做的一切。
program IndyTest;
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, Contnrs, Menus, ExtCtrls, IdBaseComponent,
IdComponent, IdTCPConnection, IdTCPClient, IdHTTP,
{$IFDEF VER220}PngImage{$ELSE}GraphicEx{$ENDIF}, StrUtils;
{$R *.res}
procedure LoadSecurityImage(AImage: TImage; AIdHTTP: TIdHTTP; AImgLink: String);
var
PNGGraphic: {$IFDEF VER220}TPngImage{$ELSE} TPNGGraphic{$ENDIF};
ResponseStream: TMemoryStream;
begin
ResponseStream := TMemoryStream.Create;
PNGGraphic := {$IFDEF VER220}TPngImage.Create{$ELSE}TPNGGraphic.Create{$ENDIF};
try
AIdHTTP.Get(AImgLink, ResponseStream);
ResponseStream.Position := 0;
PNGGraphic.LoadFromStream(ResponseStream);
AImage.Picture.Assign(PNGGraphic);
finally
ResponseStream.Free;
PNGGraphic.Free;
end;
end;
function GetImageLink(AIdHTTP: TIdHTTP): String;
var
WebContentStream: TStringStream;
Index, Index2: Integer;
begin
Result := '';
WebContentStream := TStringStream.Create('');
try
AIdHTTP.Request.ContentType := 'application/x-www-form-urlencoded';
AIdHTTP.Get('http://czat.wp.pl/i,1,chat.html', WebContentStream);
Index := Pos('id="secImg">', WebContentStream.DataString);
if Index > 0 then
begin
Index := PosEx('src="', WebContentStream.DataString, Index) + 5;
Index2 := PosEx('">', WebContentStream.DataString, Index);
if Index > 10 then
begin
Result := Copy(WebContentStream.DataString, Index, Index2 - Index);
end;
end;
finally
WebContentStream.Free;
end;
end;
procedure CheckForContent(const ANick, AImageSeed: String; AIdHTTP: TIdHTTP);
var
WebContent: TStringStream;
S: String;
begin
WebContent := TStringStream.Create('');
try
AIdHTTP.Request.ContentType := 'application/x-www-form-urlencoded';
S := 'http://czat.wp.pl/chat.html?i=31179&auth=nie&nick=' + ANick
+ '®ulamin=tak&simg=' + AImageSeed + '&x=39&y=13';
AIdHTTP.Get(S, WebContent);
if Pos('<div class="applet">', WebContent.DataString) > 0 then
ShowMessage('It works properly.')
else if Pos('<div id="alert">Sesja wygas', WebContent.DataString) > 0 then
ShowMessage('Session expired')
else
ShowMessage('Unknown result.');
finally
WebContent.Free;
end;
end;
var
LogForm: TForm;
SecurityImage: TImage;
Edit: TEdit;
IdHTTPWp: TIdHTTP;
begin
Application.Initialize;
IdHTTPWp := TIdHTTP.Create(Application);
IdHTTPWp.AllowCookies := True;
IdHTTPWp.HandleRedirects := True;
IdHTTPWp.HTTPOptions := [hoForceEncodeParams];
LogForm := TForm.Create(Application);
LogForm.Position := poScreenCenter;
SecurityImage := TImage.Create(LogForm);
SecurityImage.Parent := LogForm;
SecurityImage.AutoSize := True;
Edit := TEdit.Create(LogForm);
Edit.Parent := LogForm;
Edit.Top := 64;
LoadSecurityImage(SecurityImage, IdHTTPWp, GetImageLink(IdHTTPWp));
LogForm.ShowModal;
CheckForContent('TestUser', Edit.Text, IdHTTPWp);
Application.Run;
end.
更新3
Delphi 2007示例的数据包在此处。
Delphi XE示例的数据包在此处。
可用于分析数据包的免费程序SmartSniff。
谢谢。
TIdCookieManager
对象,TIdHTTP
将在内部使用一个隐式TIdCookieManager
对象。Indy 10 的旧版本存在一些与 cookie 相关的问题,但是现代版本已经采用了基于2011年发布的新cookie RFC的全新设计的cookie处理系统,并且据我所知对大多数已知系统都正常工作。如果您仍然认为存在 cookie 问题,则需要查看实际的 cookie 及其相关的 HTTP 请求/响应流量,以便我们可以确定 cookie 是否被正确发送回服务器。 - Remy LebeauTIdHTTP.Request.Connection
中添加了keep-alive
,我的过期会话就消失了。你试过这个方法吗? - James L.