Pages

Tuesday, January 6, 2015

Mail from ORACLE database by using UTL_SMTP package

paid surveys

This procedure uses the UTL_SMTP package to send an email message.
Up to three file names may be specified as attachments.

  Parameters are:
    1) from_name (varchar2)
    2) to_name   (varchar2)
    3) subject   (varchar2)
    4) message   (varchar2)
    5) max_size  (number)
    5) filename1 (varchar2)
    6) filename2 (varchar2)
    7) filename3 (varchar2)
  eg.

  mail_files( from_name => 'oracle' ,
                    to_name   => 'someone@somewhere.com' ,
                    subject   => 'A test',
                    message   => 'A test message',
                    filename1 => '/data/oracle/dave_test1.txt',
                    filename2 => '/data/oracle/dave_test2.txt');



Most of the parameters are self-explanatory. "message" is a varchar2 parameter, up to 32767 bytes long which contains the text of the message to be placed in the main body of the email.

filename{1,2,3} are the names of the files to be attached to the email. The full pathname of each file must be specified. The files must exist in one of the directories specified in the init. ora parameter
UTL_FILE_DIR. All filename parameters are optional: It is not necessary to specify unused file parameters (eg. filename3 is missing in the above example).

 The max_size parameter enables you to place a constraint on the maximum size of message, including all attachments, that the procedure will send.  If this limit is exceeded, the procedure will truncate the message at  that point with a '*** truncated ***' message. The default is effectively unlimited. However, the text of message body is still limited to 32Kb, as it is passed in as a varchar2.

Obviously, as with any Oracle procedure, the parameter values can (and usually will be) PL/SQL variables, rather than hard-coded literals, as shown here.

You may need to modify the following variable if you don't have a local SMTP service running (particularly relevant to Windows 2000 servers).

CREATE OR REPLACE PROCEDURE send_mail_attachment(  
   from_name VARCHAR2,  
   to_name VARCHAR2,  
   cc_name VARCHAR2 DEFAULT NULL,  
   bcc_name VARCHAR2 DEFAULT NULL,  
   subject VARCHAR2,  
   message VARCHAR2,  
   max_size NUMBER DEFAULT 9999999999,  
   filename1 VARCHAR2 DEFAULT NULL,  
   filename2 VARCHAR2 DEFAULT NULL,  
   filename3 VARCHAR2 DEFAULT NULL,  
   filename4 VARCHAR2 DEFAULT NULL,  
   DEBUG NUMBER DEFAULT 0 )  
 IS  
   v_smtp_server       VARCHAR2(30) := 'MAIL_SERVER_DOMAIN_NAME';  
   v_smtp_server_port  NUMBER := 25; -- SMTP PORT NAME (Default port 25)  
   v_directory_name    VARCHAR2(100);  
   v_file_name         VARCHAR2(100);  
   v_line              VARCHAR2(1000);  
   crlf                VARCHAR2(2):= chr(13) || chr(10);  
   mesg                VARCHAR2(32767);  
   msg_header          VARCHAR2(32767);  
   mesg_len            NUMBER;  
   conn                UTL_SMTP.CONNECTION;  
   TYPE varchar2_table IS TABLE OF VARCHAR2(200) INDEX BY BINARY_INTEGER;  
   file_array          varchar2_table;  
   i                   BINARY_INTEGER;  
   v_file_handle       utl_file.file_type;  
   v_slash_pos         NUMBER;  
   mesg_too_long       EXCEPTION;  
   invalid_path        EXCEPTION;  
   mesg_length_exceeded BOOLEAN := FALSE;  
   var_length          INTEGER;  
   var_rcpt            VARCHAR2(500);  
   var_i               INTEGER;  
   var_start           INTEGER;  
 BEGIN  
   -- first load the three filenames into an array for easier handling later ...  
   file_array(1) := filename1;  
   file_array(2) := filename2;  
   file_array(3) := filename3;  
   file_array(4) := filename4;  
   -- Open the SMTP connection ...  
   -- ------------------------  
   conn := utl_smtp.open_connection( v_smtp_server, v_smtp_server_port );  
   -- Initial handshaking ...  
   -- -------------------  
   utl_smtp.helo( conn, v_smtp_server );  
   utl_smtp.mail( conn, from_name );  
   -- Handling multiple TO List ...  
   -- ----------------  
   var_i := 1;   
   var_length := nvl(length(to_name), 0);  
   LOOP  
     EXIT WHEN var_i >= var_length;  
     var_start := var_i;  
     LOOP  
      EXIT WHEN var_i >= var_length OR substr(to_name, var_i+1, 1) = ',';  
      var_i := var_i + 1;      
     END LOOP;  
     var_rcpt := substr(to_name, var_start, var_i-var_start+1);  
     utl_smtp.rcpt(conn, var_rcpt);  
     var_i := var_i + 2;  
   END LOOP;   
   -- Handling multiple CC List ...  
   -- ----------------  
   var_i := 1;   
   var_length := nvl(length(cc_name), 0);  
   LOOP  
     EXIT WHEN var_i >= var_length;  
     var_start := var_i;  
     LOOP  
      EXIT WHEN var_i >= var_length or substr(cc_name, var_i+1, 1) = ',';  
      var_i := var_i + 1;      
     END LOOP;  
     var_rcpt := substr(cc_name, var_start, var_i-var_start+1);  
     utl_smtp.rcpt(conn, var_rcpt);  
     var_i := var_i + 2;  
   END LOOP;  
   -- Handling multiple BCC List ...  
   -- --------------------------  
   var_i := 1;   
   var_length := nvl(length(bcc_name), 0);  
   LOOP  
     EXIT WHEN var_i >= var_length;  
     var_start := var_i;  
     LOOP  
      EXIT WHEN var_i >= var_length OR substr(bcc_name, var_i+1, 1) = ',';  
      var_i := var_i + 1;      
     END LOOP;  
     var_rcpt := substr(bcc_name,var_start,var_i-var_start+1);  
     utl_smtp.rcpt(conn, var_rcpt);  
     var_i := var_i + 2;  
   END LOOP;  
   utl_smtp.open_data ( conn );  
   -- build the start of the mail message ...  
   -- -----------------------------------  
   msg_header := 'Date: ' || TO_CHAR( SYSDATE-1/4, 'dd Mon yy hh24:mi:ss' ) || crlf ||  
      'From: ' || from_name || crlf ||  
      'Subject: ' || subject || crlf ||  
      'To: ' || to_name || crlf ||  
      'CC: ' || cc_name || crlf ||  
      'BCC: ' || bcc_name || crlf ||  
      'Mime-Version: 1.0' || crlf ||  
      'Content-Type: multipart/mixed; boundary="DMW.Boundary.605592468"' || crlf ||  
      '';  
   utl_smtp.write_data ( conn, msg_header);     
   mesg:= crlf ||  
      'This is a Mime message, which your current mail reader may not' || crlf ||  
      'understand. Parts of the message will appear as text. If the remainder' || crlf ||  
      'appears as random characters in the message body, instead of as' || crlf ||  
      'attachments, then you''ll have to extract these parts and decode them' || crlf ||  
      'manually.' || crlf ||  
      '' || crlf ||  
      '--DMW.Boundary.605592468' || crlf ||  
      'Content-Type: text/plain; charset=US-ASCII' || crlf ||  
      'Content-Disposition: inline; ' || crlf ||  
      'Content-Transfer-Encoding: 7bit' || crlf ||  
      '' || crlf ||  
      message || crlf ;  
   -- To send message as attachment  
   -- In Content-Type  
   mesg_len := length(mesg);  
   IF mesg_len > max_size THEN  
     mesg_length_exceeded := TRUE;  
   END IF;  
   utl_smtp.write_data ( conn, mesg );  
   -- Append the files ...  
   -- ----------------  
   FOR i IN 1..4 LOOP  
     -- Exit if message length already exceeded ...  
     EXIT WHEN mesg_length_exceeded;  
     -- If the filename has been supplied ...  
     IF file_array(i) IS NOT NULL THEN  
      BEGIN  
        -- locate the final '/' or '\' in the pathname ...  
        v_slash_pos := instr(file_array(i), '/', -1 );  
        IF v_slash_pos = 0 THEN  
         v_slash_pos := instr(file_array(i), '\', -1 );  
        END IF;  
        -- separate the filename from the directory name ...  
        v_directory_name := substr(file_array(i), 1, v_slash_pos - 1 );  
        v_file_name   := substr(file_array(i), v_slash_pos + 1 );  
        -- open the file ...  
        v_file_handle := utl_file.fopen(v_directory_name, v_file_name, 'r' );  
        -- generate the MIME boundary line ...  
        mesg := crlf || '--DMW.Boundary.605592468' || crlf ||  
        'Content-Type: application/octet-stream; name="' || v_file_name || '"' || crlf ||  
        'Content-Disposition: attachment; filename="' || v_file_name || '"' || crlf ||  
        'Content-Transfer-Encoding: 7bit' || crlf || crlf ;  
        mesg_len := mesg_len + length(mesg);  
        utl_smtp.write_data ( conn, mesg );  
        -- and append the file contents to the end of the message ...  
        LOOP  
          utl_file.get_line(v_file_handle, v_line);  
          IF mesg_len + length(v_line) > max_size THEN  
           mesg := '*** truncated ***' || crlf;  
           utl_smtp.write_data ( conn, mesg );  
           mesg_length_exceeded := TRUE;  
           RAISE mesg_too_long;  
          END IF;  
          mesg := v_line || crlf;  
          utl_smtp.write_data ( conn, mesg );  
          mesg_len := mesg_len + length(mesg);  
        END LOOP;  
      EXCEPTION  
        WHEN utl_file.invalid_path THEN  
          IF DEBUG > 0 THEN  
           dbms_output.put_line('Error in opening attachment '|| file_array(i) );  
          END IF;  
        WHEN UTL_SMTP.INVALID_OPERATION THEN  
          dbms_output.put_line(' Invalid Operation in SMTP transaction.');  
        WHEN UTL_SMTP.TRANSIENT_ERROR THEN  
          dbms_output.put_line(' Temporary problems with sending email - try again later.');  
        WHEN UTL_SMTP.PERMANENT_ERROR THEN  
          dbms_output.put_line(' Errors in code for SMTP transaction.');  
          -- All other exceptions are ignored ....  
        WHEN OTHERS THEN  
          NULL;  
      END;  
      mesg := crlf;  
      utl_smtp.write_data ( conn, mesg );  
      -- close the file ...  
      utl_file.fclose(v_file_handle);  
     END IF;  
   END LOOP;  
   -- append the final boundary line ...  
   mesg := crlf || '--DMW.Boundary.605592468--' || crlf;  
   utl_smtp.write_data ( conn, mesg );  
   -- and close the SMTP connection ...  
   utl_smtp.close_data( conn );  
   utl_smtp.quit( conn );  
 END; 

--Execution Example


 BEGIN  
   send_mail_attachment    (from_name  => 'abc@domain_name.com',  
                         to_name    => 'xyz@domain_name.com',  
                         cc_name    => null,  
                         bcc_name   => mill,  
                         subject      => 'Test Mail',  
                         message    => 'Hello',  
                         filename1   => 'abc.jpg',  
                         filename2   => 'pqr.pdf',  
                         filename3   => null,  
                         filename4   => null );  
 END; 


paid surveys

No comments:

Post a Comment