0

2日間正しい方法を推測しようとした後、私はあきらめました。件名に関する多くの質問がありますが、何も役に立ちません。

私の間違いを見せてください。

タスク: multipart-form (文字列フィールドとファイル) をサーバーに送信します。サーバーは ISO-8859-1 エンコーディングを待機します。

    http.Request.Host := fHost;
    http.Request.AcceptEncoding := '*';
    http.Request.UserAgent := HTTPUserAgent;
    http.Request.ContentEncoding := 'ISO-8859-1';
//        http.Request.CharSet  := 'ISO-8859-1';
    if HTTPProxyActive then
      http.Request.ProxyConnection := 'close'
    else
      http.Request.Connection := 'close';
    http.Request.ContentType := 'text/plain';

    addr := 'https://'+Host+URL;

    if ValCount>0 then begin
      Stream := TIdMultipartFormDataStream.Create;
      for i:=0 to ValCount-1 do begin
        if Values[i].Name<>'' then
        begin
          field := Stream.AddFormField(Values[i].Name, Values[i].Value, 'ISO-8859-1');
//              field.Charset := 'ISO-8859-1';
//              field.ContentTransfer := '7bit';
        end;
        if Values[i].Filename<>'' then
          Stream.AddFile(Values[i].FileName, Values[i].Value, 'text/plain');
      end;
      resp := TStringStream.Create;
      http.Post(addr, Stream, resp);
      st := resp.DataString;
      resp.Destroy;
      Stream.Destroy;
    end

投稿の結果、私は???????を持っています サーバー上のシーケンス。フィールドまたはリクエストの文字セットを定義すると、サーバーでエラーが発生します。

助けてください、または不足している情報は何ですか?

更新: UTF-8 で結果を取得できます。しかし、サーバーでは UTF-8 値を取得し、ISO-8859-1 が必要です。

UTF-8 ソリューション:

field := Stream.AddFormField(Values[i].Name, Values[i].Value, 'UTF-8');
field.ContentTransfer := '8bit';
4

2 に答える 2

1

Indy 10 の最新バージョンを使用していると仮定するとTIdMultipartFormDataStream、ISO-8859-1 で問題なく動作します。UTF-8 を指定する場所に指定するだけです。割り当てのバグも修正する必要がありますRequest.ContentEncoding。文字列の文字セットは有効なコンテンツ エンコーディングではありません。これは、HTTP とはまったく異なる機能です。また、応答文字列データのデコードTStringStreamを妨げるため、を取り除く必要があります。TIdHTTP

これを試して:

if ValCount > 0 then
begin
  http.Request.AcceptEncoding := '*';
  http.Request.UserAgent := HTTPUserAgent;
  if HTTPProxyActive then
    http.Request.ProxyConnection := 'close'
  else
    http.Request.Connection := 'close';

  addr := 'https://'+Host+URL;

  Stream := TIdMultipartFormDataStream.Create;
  try
    for i := 0 to ValCount-1 do begin
      if Values[i].Name <> '' then
      begin
        field := Stream.AddFormField(Values[i].Name, Values[i].Value, 'ISO-8859-1');
        field.ContentTransfer := '8bit';
      end;
      if Values[i].FileName <> '' then
        Stream.AddFile(Values[i].Name, Values[i].FileName, 'text/plain');
    end;
    st := http.Post(addr, Stream);
  finally
    Stream.Free;
  end;
end;

または:あなたが示した「解決策」とより一致しています:

if ValCount > 0 then
begin
  http.Request.AcceptEncoding := '*';
  http.Request.UserAgent := HTTPUserAgent;
  if HTTPProxyActive then
    http.Request.ProxyConnection := 'close'
  else
    http.Request.Connection := 'close';

  addr := 'https://'+Host+URL;

  Stream := TIdMultipartFormDataStream.Create;
  try
    for i := 0 to ValCount-1 do begin
      if Values[i].Name <> '' then
      begin
        field := Stream.AddFormField(Values[i].Name, Values[i].Value, 'ISO-8859-1');
        field.ContentTransfer := '8bit';
        field.FileName := Values[i].FileName;
      end;
    end;
    st := http.Post(addr, Stream);
  finally
    Stream.Free;
  end;
end;
于 2012-08-23T02:12:15.090 に答える
0

解決

多くのソリューションがインターネットにあります。レミーからの多くのソリューション。しかし、それらはすべてUTF-8に関するものです。サーバーはUTF-8文字列を取得できません...そして、サーバー側のスクリプトにアクセスして状況を修正できません。そのため、TIdMultipartFormDataStream クラスを使用せずに手動でリクエストを作成します。

私の解決策は次の解決策に役立つと思います。幸運を。

    http.Request.ContentType := 'multipart/form-data; boundary=' + FBound;
    if HTTPProxyActive then
      http.Request.ProxyConnection := 'close'
    else
      http.Request.Connection := 'close';

    addr := 'http://'+Host+URL;
    resp := TStringStream.Create;
    if ValCount>0 then
    begin
      cont := '';
      for i:=0 to ValCount - 1 do
      begin
        cont := cont + '--' + FBound + #13#10;
        cont := cont + 'Content-Disposition: form-data';
        if Values[i].Filename<>'' then
          cont := cont + '; filename="' + Values[i].Filename + '"';
        if Values[i].Name<>'' then
          cont := cont + '; name="' + Values[i].Name + '"';
        cont := cont + #13#10+#13#10;
        cont := cont + Values[i].Value;
        cont := cont + #13#10;
      end;
      cont := cont + '--' + FBound + '--' + #13#10#13#10;
      http.Request.ContentLength := Length(cont);
      req := TStringStream.Create(cont);
      http.Post(addr, req, resp);
      FreeAndNil(req);
    end
    else
    begin
      http.Get(addr, resp);
    end;
    st := resp.DataString;
    resp.Destroy;
于 2012-08-22T18:40:59.973 に答える