使用 ORACLE utl_smtp 的 chaset 编码问题

Problem with chaset encoding using ORACLE utl_smtp

我正在使用 Oracle 12.2.0.1.0。 我们创建了一个发送带有 UTL_SMTP 包的电子邮件的程序。 一切正常,但我们丢失了波兰语的特定编码。

NLS 设置: NLS_CHARACTERSET = EE8MSWIN1250; NLS_NCHAR_CHARACTERSET = AL16UTF16;

我们在 table 的 CLOB 列中保留消息文本。

...
mime_type  IN VARCHAR2  DEFAULT 'text/plain',
message IN CLOB,
...
conn utl_smtp.connection;
...
    conn := utl_smtp.open_connection(mail_host, mail_port);
    utl_smtp.helo(conn, mail_host);
...
    utl_smtp.mail(conn, get_address(my_sender));
    utl_smtp.rcpt(conn, get_address(my_recipients));

    utl_smtp.open_data(conn);
    write_mime_header(conn, 'From', sender);
    write_mime_header(conn, 'To', recipients);
    write_mime_header(conn, 'Subject', subject);
    write_mime_header(conn, 'Content-Type', mime_type);
...
    loop
       exit when offset > dbms_lob.getlength(message);
       utl_smtp.write_data(conn, dbms_lob.substr( message, 255, offset ));
       offset := offset + 255;
    end loop;
...
    utl_smtp.close_data(conn);
    utl_smtp.quit(conn);
...

write_mime_header

的代码
  PROCEDURE write_mime_header(conn  IN OUT NOCOPY utl_smtp.connection,
                  name  IN VARCHAR2,
                  value IN VARCHAR2) IS
  BEGIN
    utl_smtp.write_data(conn, name || ': ' || value || utl_tcp.CRLF);
  END;
  

很遗憾,我们丢失了 char 编码。前任。邮件中的 clob“uzytkownik”中的“użytkownik”。

我尝试在内容类型中设置字符集,但我们仍然遇到问题。

    write_mime_header(conn, 'Content-Type','text/plain; charset="UTF8"');
    utl_smtp.write_data(conn, 'Content-Type: text/plain; charset="EE8MSWIN1250"' || utl_tcp.CRLF); 

如何设置邮件的编码?

From the documentation:

Usage Notes
...

  • Text (VARCHAR2) data sent using WRITE_DATA is converted to US7ASCII before it is sent. If the text contains multibyte characters, each multibyte character in the text that cannot be converted to US7ASCII is replaced by a '?' character. If 8BITMIME extension is negotiated with the SMTP server using the EHLO subprogram, multibyte VARCHAR2 data can be sent by first converting the text to RAW using the UTL_RAW package, and then sending the RAW data using WRITE_RAW_DATA.

因此您可以将 HELO 更改为 EHLO 并查看是否支持;然后使用类似的东西:

utl_smtp.write_raw_data(conn, utl_raw.cast_to_raw(dbms_lob.substr(message, 255, offset)));

否则您需要对消息进行 base64 编码。