Delphi7 Indy HTTPServer没有获取表单参数

时间:2016-12-16 10:01:49

标签: html delphi indy

我在Windows应用程序中有一个Indy 10 IdHTTPServer,它提供一个带有两个文本框和一个提交按钮的虚拟HTML表单。当在浏览器中按下按钮时,我没有看到任何形式的参数返回到服务器。 请注意,这是概念代码的一些证明,它将用于使Windows服务响应Web表单中的按钮按下。

HTML表单是这样的:

 <form action="http://<addressofsite>/" method="post">
  First name:<br>
  <input type="text" name="firstname" value="Mickey"><br>
  Last name:<br>
  <input type="text" name="lastname" value="Mouse"><br><br>
  <input type="submit" value="Submit">
</form> 
在Delphi代码中我有这个:

procedure TForm1.HTTPServer1CommandGet(AThread: TIdPeerThread;
 ARequestInfo: TIdHTTPRequestInfo; AResponseInfo: TIdHTTPResponseInfo);
begin

...  

 if ARequestInfo.Command = 'POST' then
    begin
      {******* POSTS ***************}
      Memo1.Text := ARequestInfo.RawHTTPCommand;
    end;
end;

我已经尝试了ARequestInfo结构的各个部分,但无论我在浏览器中按下按钮时看到的是什么:

POST / HTTP 1.1

似乎没有通过参数。

我显然做错了,所以请有人指出我的白痴。

更新

正如下面的Arioch指出,我应该检查浏览器实际上是在发送数据 - 所以使用Chrome开发者工具我检查了标题,其结果是:

Response Headers

  Connection:close
  Content-Type:text/html
  Server:Indy/10.0.52

Request Headers

  Accept:text/html,application/xhtml+xml,application/xml;q=0.9,image  /webp,*/*;q=0.8
  Accept-Encoding:gzip, deflate, br
  Accept-Language:en-GB,en-US;q=0.8,en;q=0.6
  Authorization:Basic YWRtaW46cGFzcw==
  Cache-Control:max-age=0
  Connection:keep-alive
  Content-Length:31
  Content-Type:application/x-www-form-urlencoded
  Host:127.0.0.1:8091
  Origin:http://127.0.0.1:8091
  Referer:http://127.0.0.1:8091/main
  Upgrade-Insecure-Requests:1
  User-Agent:Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36      (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36

Form Data

  firstname:Mickey
  lastname:Mouse

因此浏览器肯定会发送表单数据。

1 个答案:

答案 0 :(得分:1)

原始编码表单数据存储在ARequestInfo.FormParamsARequestInfo.UnparsedParams属性中。

如果TIdHTTPServer.ParseParams为真(默认为默认值),已解码表单数据将存储在ARequestInfo.Params属性中,例如:

procedure TForm1.HTTPServer1CommandGet(AThread: TIdPeerThread;
  ARequestInfo: TIdHTTPRequestInfo; AResponseInfo: TIdHTTPResponseInfo);
var
  FirstName, LastName: string;
begin
  ...  
  if (ARequestInfo.CommandType = hcPOST) and
     IsHeaderMediaType(ARequestInfo.ContentType, 'application/x-www-form-urlencoded') then
  begin
    FirstName := ARequestInfo.Params.Values['firstname'];
    LastName := ARequestInfo.Params.Values['lastname'];
    ...
  end;
end;

请注意TIdHTTPServer是一个多线程组件。包括OnCommandGet在内的各种事件都是在工作线程的上下文中触发的。因此,如果您需要触摸UI控件,例如TMemo,则必须与主UI线程同步,例如:

procedure TForm1.HTTPServer1CommandGet(AThread: TIdPeerThread;
 ARequestInfo: TIdHTTPRequestInfo; AResponseInfo: TIdHTTPResponseInfo);
begin
  ...  
  if (ARequestInfo.CommandType = hcPOST) and
     HeaderIsMediaType(ARequestInfo.ContentType, 'application/x-www-form-urlencoded') then
  begin
    TThread.Synchronize(nil,
      procedure
      begin
        Memo1.Text := ARequestInfo.Params.Text;
      end
    );
    ...
  end;
end;

此外,10.0.52是Indy的过时版本。当前版本(撰写本文时)为10.6.2.5384。