在Delphi中用希伯来文本创建Base64字符串

时间:2013-01-12 12:00:03

标签: delphi utf-8 base64 delphi-7

我正在尝试将用希伯来语写成的'subject'字段编码到Base64中,以便在所有浏览器中正确读取主题。目前,我正在使用Windows-1255编码,它可以在某些客户端上运行但不是全部,所以我想使用utf-8,base64。

我对这个主题的阅读(没有双关语)表明文本必须采用

形式
=?<charset>?<encoding>?<encoded text>?=

例如

=?windows-1255?Q?=E0=E1?=

我已经使用UTF-8B编码以希伯来语发送给我的信件中的编码主题行,并在本网站www.webatic.com/run/convert/base64.php上成功解码。我还使用这个网站编码简单的字母,并注意到返回编码与我从Delphi算法得到的结果相同。

所以 - 我正在寻找一种成功编码字母的算法,例如aleph(ord = 224),bet(ord = 225)等。根据网站,由两个字母aleph和bet组成的字符串返回代码15DXkq ==,但基本的Delphi算法返回Ue4,TIdEncoderQuotedPrintable组件返回= E0 = E1(这是ISO-8859编码)。

修改(经过多次评论后):

我让一位朋友给我发了一封来自她Mac电脑的电子邮件,不出所料地使用了UTF-8编码(而不是Windows-1255)。主题是一个字母,aleph,ord 224.编码主题出现在电子邮件的标题中,如下所示

=?UTF-8?B?15A=?=

这可以分为三个部分:'prefix'(=?UTF-8?B?),这意味着正在使用带有base64编码的UTF-8; '有效载荷'(15A =),我引用的网站将其正确翻译为字母aleph;和后缀(?=)。

我需要一个算法来翻译任意字母串,其中大部分都是希伯来语(因此ord> = 224)到base64 / utf-8;正确的解决方案是在引用的网站上正确解码的解决方案。

2 个答案:

答案 0 :(得分:1)

很抱歉浪费了你所有的时间。今天我又花了几个小时讨论这个主题,发现我使用的base64代码有一个很大的bug。

发送base64编码的UTF-8主题行所需的步骤是:

  1. 通过AnsiToUTF8函数将“普通”文本(即本地ANSI代码页)转换为UTF-8
  2. 将其编码为base64
  3. 创建一个前缀为'=?UTF-8?B?'的字符串,第2阶段的结果和后缀'=?='
  4. 发送!
  5. 以下是创建和发送电子邮件的完整代码(显然简化)

     with IdSMTP1 do
      begin
       host:= ....;
       username:= ....;
       password:= ....;
      end;
    
     with email do
      begin
       From.Address:= ....;
       Recipients.EMailAddresses:= ....;
       cclist.add.address:= ....;
       email.subject:= '=?UTF-8?B?' + encode64 (AnsiToUTF8 (edit1.text)) +  '=?=';
       email.Body.text:= ....;
      end;
    
     try
      IdSMTP1.Connect (1000);
      IdSMTP1.Send (email);
     finally
      if IdSMTP1.Connected
       then IdSMTP1.Disconnect;
     end;
    

    使用此page上与此page相同的代码,'codes64'字符串以数字开头,然后是大写字母,然后是小写字母,然后是标点符号。但是这个page表明大写字母应该首先出现,然后是小写字母,接着是数字,然后是标点符号。

    一旦我做了这个修正,字符串开始被'正确'编码 - 我可以在我的电子邮件客户端中正确地读取它们,我将其视为'正确'的定义。

    阅读其他人是否遇到我找到的base64编码代码有问题会很有趣。

答案 1 :(得分:0)

您根本不需要手动编码Subject属性。 TIdMessage会自动为您编码。只需指定  Edit1.Text的价值与...相同  Subject并让TIdMessage编码  它根据需要。

如果你想自定义方式  TIdMessage对标头进行编码,使用TIdMessage.OnInitializeISO  事件提供所需的字符集和编码  值。在Delphi 2009+中,默认为UTF-8和Base64。在早期版本中,TIdMessage读取RTL的当前操作系统语言,并为已知语言选择一些默认值。但是,希伯来语不是其中之一,因此ISO-8859-1和QuotedPrintable最终会被使用。您可以覆盖这些值,例如:

email.Subject := Edit1.Text;

procedure TForm1.emailInitializeISO(var VHeaderEncoding: Char; var VCharSet: string);
begin
  VHeaderEncoding := 'B';
  VCharSet := 'UTF-8';
end;