我在oracle9i中写了一个存储过程,来发邮件。成功了,但是在数据库中是中文,而接收到的,却出现乱码,请问各位大虾有没有办法解决。

解决方案 »

  1.   

    能否共享一下代码啊,smtp认证怎么搞的啊
      

  2.   

    Note that the original SMTP protocol communicates using 7-bit ASCII. Using UTL_
    SMTP, all text data (in other words, those in VARCHAR2) will be converted to
    US7ASCII before it is sent over the wire to the server. Some implementations of
    SMTP servers that support SMTP extension 8BITMIME [RFC1652] support full 8-bit
    communication between client and server.
    这是关于UTL_SMTP的一个说明,在Oracle8i Supplied PL/SQL Packages Reference Release 2 (8.1.6) 里的,看样子是不行了,不支持中文字符!
      

  3.   

    是oracle的问题 
    解决办法:
    CREATE OR REPLACE PROCEDURE send_mail
    ( i_from in varchar2, i_to in varchar2, i_cc in varchar2, i_bcc  in varchar2, 
      i_subject in varchar2, i_content in varchar2, 
      i_smtp_server in varchar2, 
      i_port in number := 25, i_user in varchar2 := null, i_pwd in varchar2 := null) 
    is 
      c utl_smtp.connection; 
      v_tmp varchar2(256); 
      v_adr varchar2(256); 
      v_from  varchar2(256); 
      v_to    varchar2(256); 
      v_cc    varchar2(256); 
      v_bcc   varchar2(256); 
      -- encodeBase64 
      function EncodeBase64(i_str varchar2) return varchar2 is 
      begin 
        return twd_base64.encode( utl_raw.cast_to_raw(i_str) ); 
      end; 
      -- EncodeAddress 
      function EncodeAddress(i_str varchar2) return varchar2 is 
      begin 
        return ('=?GB2312?B?'||EncodeBase64(i_str)||'?='); 
      end; 
      -- getAddress 
      function getAddress(x_addr in out varchar2, x_addr_encoded in out varchar2) 
      return varchar2 is 
        v_addr          varchar2(256); 
        v_addr_encoded  varchar2(256); 
        v_separator     varchar2(5); 
        i       pls_integer; 
        function lookup_unquoted_char(li_str varchar2, li_chrs varchar2) return pls_integer as 
          c varchar2(5); 
          k pls_integer; 
          l pls_integer; 
          inside_quote boolean; 
        begin 
          inside_quote := false; 
          k := 1; 
          l := length(li_str); 
          while (k <= l) 
          loop 
            c := substr(li_str, k, 1); 
            if (inside_quote) then 
              if (c = '"') then 
                inside_quote := false; 
              elsif (c = '\') then 
                k := k + 1; -- skip the quote character 
              end if; 
              goto next_char; 
            end if; 
            if (c = '"') then 
              inside_quote := true; 
              goto next_char; 
            end if; 
            if (instr(li_chrs, c) >= 1) then 
              return k; 
            end if; 
            <<next_char>> 
            k := k + 1; 
          end loop; 
          return 0; 
        end; 
      begin 
        x_addr := ltrim(x_addr); 
        i := lookup_unquoted_char(x_addr, ',;'); 
        if (i >= 1) then 
          v_separator := substr(x_addr, i, 1); 
          v_addr := substr(x_addr, 1, i - 1); 
          x_addr := substr(x_addr, i + 1); 
        else 
          v_addr := x_addr; 
          x_addr := ''; 
        end if; 
        i := lookup_unquoted_char(v_addr, '<'); 
        if (i >= 1) then 
          v_addr_encoded := EncodeAddress(substr(v_addr, 1, i - 1)) || substr(v_addr, i); 
          v_addr := substr(v_addr, i + 1); 
          i := instr(v_addr, '>'); 
          if (i >= 1) then 
            v_addr := substr(v_addr, 1, i - 1); 
          end if; 
        else 
          v_addr_encoded := v_addr; 
        end if; 
        x_addr_encoded := x_addr_encoded || v_addr_encoded || v_separator; 
        return v_addr; 
      end getAddress; 
    BEGIN 
      c := utl_smtp.open_connection(i_smtp_server, i_port); 
      utl_smtp.helo(c, i_smtp_server);   -- 校验认证 
      if i_user is not null then 
        utl_smtp.command(c, 'auth login', ''); 
        utl_smtp.command(c, EncodeBase64(i_user), ''); 
        utl_smtp.command(c, EncodeBase64(i_pwd), ''); 
      end if;   -- 解析 发信人 
      v_tmp := i_from; 
      v_adr := getAddress(v_tmp, v_from); 
      utl_smtp.mail(c, v_adr);   -- 解析 收件人列表 
      v_tmp := i_to; 
      while (v_tmp is not null) loop 
        v_adr := getAddress(v_tmp, v_to); 
        utl_smtp.rcpt(c, v_adr); 
      end loop; 
      -- 解析 抄送人列表 
      v_tmp := i_cc; 
      while (v_tmp is not null) loop 
        v_adr := getAddress(v_tmp, v_cc); 
        utl_smtp.rcpt(c, v_adr); 
      end loop; 
      -- 解析 暗送人列表 
      v_tmp := i_bcc; 
      while (v_tmp is not null) loop 
        v_adr := getAddress(v_tmp, v_bcc); 
        utl_smtp.rcpt(c, v_adr); 
      end loop;   utl_smtp.open_data(c); 
      utl_smtp.write_data(c, 'From: '||v_from||utl_tcp.CRLF); 
      utl_smtp.write_data(c, 'To: '||v_to||utl_tcp.CRLF); 
      utl_smtp.write_data(c, 'Cc: '||v_cc||utl_tcp.CRLF); 
      utl_smtp.write_data(c, 'Subject: '||EncodeAddress(i_subject)||utl_tcp.CRLF); 
      utl_smtp.write_data(c, 'Mime-Version: 1.0'||utl_tcp.CRLF); 
      utl_smtp.write_data(c, 'Content-Type: text/plain; charset="GB2312"'||utl_tcp.CRLF); 
      utl_smtp.write_data(c, utl_tcp.CRLF);   -- data 
      utl_smtp.write_raw_data(c, utl_raw.cast_to_raw(i_content)); 
      utl_smtp.write_data(c, utl_tcp.CRLF);   utl_smtp.close_data(c); 
      utl_smtp.quit(c); EXCEPTION 
      WHEN utl_smtp.transient_error OR utl_smtp.permanent_error THEN 
      utl_smtp.quit(c); 
      raise_application_error(-20000, 
      'Failed to send mail due to the following error: ' || sqlerrm); 
    END send_mail;