Showing posts with label PL/SQL. Show all posts
Showing posts with label PL/SQL. Show all posts

How to Send a Mail from Within PL/SQL and Java Stored Procedures.

8/02/2012 No Comment

Send a Mail from Within PL/SQL and Java Stored Procedures.

  1. Create a new database user for the JAR-files, for example user "MAIL".
    SQL> CREATE USER mail IDENTIFIED BY mail;

  2. As user SYS give following rights to this user "mail". These rights are necessary to be able to execute the test procedure later.
    The rights given here are necessary to allow the user "mail" to execute commands on the operating system. In below statements you have to replace following values:
    = The hostname of the emailserver
    = The IP-address of the email server
    SQL> exec dbms_java.grant_permission('MAIL','SYS:java.net.SocketPermission','','resolve');
    SQL> exec dbms_java.grant_permission('MAIL','SYS:java.net.SocketPermission','','connect,resolve');

  3. Load the JavaBeans Activation Framework.

    To load the file into the database use following command and replace the values for , and with the values for your database:
    > loadjava -thin -user mail/mail@:: -grant Public -resolve activation.jar
  4. Load the JavaMail API.
    For this step it depends on which environment you are using.
    • If you are using RDBMS 9.2.0.7.0 or 10.2.x then you will have to use JavaMail API version 1.3.1, this version can be obtained from here.
    • If you are using RDBMS 11.1.x then you can use the versions between 1.3.2 and 1.4.1. The version 1.4.1 can be downloaded from here.

    To load the JavaMail API into the database use following command:
    > loadjava -thin -user mail/mail@:: -grant Public -resolve mail.jar

  5. Create a java test class.
    Within an editor create following file and save the file as "zMail.java".

    import java.util.*;
    import javax.mail.*;
    import javax.mail.internet.*;

    public class zMail {

      static InternetAddress fromAddress;
      static String          IncomingServer;
      static Properties      propsOutgoing;

      public static void init( String OutgoingServerName, String IncomingServerName, String SenderAddress) {

        try {
          fromAddress = new InternetAddress(SenderAddress);
        }
        catch (MessagingException e) {
          e.printStackTrace();
        }

        IncomingServer = IncomingServerName;
        propsOutgoing = new Properties();
        propsOutgoing.put("mail.smtp.host", OutgoingServerName);
      }

      public static void sendPlainTextMessage( String To, String Subject, String Body) {

        boolean debug = false;

        Session session = Session.getDefaultInstance(propsOutgoing, null);
        session.setDebug(debug);

        try {
          // create a message
          Message msg = new MimeMessage(session);

          // set the from
          msg.setFrom(fromAddress);

          InternetAddress[] address = {new InternetAddress(To)};
          msg.setRecipients(Message.RecipientType.TO, address);
          msg.setSubject(Subject);

          msg.setContent(Body, "text/plain");
          Transport.send(msg);
        }
        catch (MessagingException e) {
          e.printStackTrace();
        }
      }
    }

  6. Compile and load this class into RDBMS.
    Make sure in the command below that you specify the full path to the necessary libraries and that the used jdk matches the jdk used within the database. That is:

    • RDBMS 9.2.0.7.0 -> jdk 1.3.1
    • RDBMS 10.2.0.3.0 -> jdk 1.4.2
    • RDBMS 11.1.0.6.0 -> jdk 1.5.0
    > javac -classpath \activation.jar;\mail.jar;%CLASSPATH% zMail.java

    > loadjava -thin -user mail/mail@:: -verbose zMail.class
  7. To be able to call the Java Stored Procedure (JSP) from PL/SQL we need to create so called interfaces to the Java Stored Procedures JSP:
    create or replace package mail_service authid CURRENT_USER as

      procedure init( OutServer  in varchar2
                    , InServer   in varchar2
                    , SenderName in varchar2
                    );

      procedure SendPlainTextMsg( ToName     in varchar2
                                , MsgSubject in varchar2
                                , MsgBody    in varchar2
                                );

    end mail_service;
    /

    create or replace package body mail_service as

      procedure init ( OutServer  in varchar2
                     , InServer   in varchar2
                     , SenderName in varchar2
                     )
      as language JAVA name 'zMail.init(java.lang.String, java.lang.String, java.lang.String)';

      procedure SendPlainTextMsg( ToName     in varchar2
                                , MsgSubject in varchar2
                                , MsgBody    in varchar2
                                )
      as language JAVA name 'zMail.sendPlainTextMessage(java.lang.String, java.lang.String, java.lang.String)';

    end mail_service;
    /
  8. Invoke our Sample JSP from SQL*Plus.
    To run the example replace the the following values with your values, , and
    .
    begin
      mail_service.init(
         '',
         '',
         'JAVAMAIL@Oracle.COM');
      mail_service.SendPlainTextMsg(
         '',
         'Test from RDBMS',
         'This is a test message.\nPlease ignore.\nBest regards,\nJAVAMAIL');
    end;
    /

How to Convert from Long Raw to BLOB/CLOB using PL/SQL

7/28/2012 No Comment

Convert from Long Raw to BLOB/CLOB using PL/SQL.

Goal and Aim


This article contains information on how to convert LONG/LONG RAW  with size equal or less 64kB to BLOB/CLOB using PL/SQL.

To convert
LONG/LONG RAW with any size to BLOB/CLOB the SQL functions

  • to_lob()
  • to_clob()
can be used in Oracle 10gR2 (10.2.0.1) and higher.You can apply this function only to a LONG or LONG RAW column, and only in the select list of a subquery in an INSERT statement - NOT in PLSQL as conversion function.

Solution
Example #1 [LONG/LONG RAW to BLOB]


Example #1 demonstrates how to convert a LONG column that is less than 64k into a BLOB using PL/SQL.

-- DROP table 
drop table traw; 
drop table tblob 
 
-- CREATE table 
create table traw (n1 number , l1 long raw); 
create table tblob (n1 number , l1 blob); 
  --- You can use  clob as well 
 
-- INSERT table 
begin 
  for i in 1..10 loop 
    insert into traw values (i,utl_raw.cast_to_raw(rpad(to_char(i),60,'&'))); 
    insert into tblob values (i,empty_blob()); 
  end loop; 
end; 
/ 
 
declare 
 lobloc blob; 
 buffer long raw(32000); 
 amount number ; 
 offset number := 1; 
begin 
 for rec in (select * from traw) loop 
   select l1 into lobloc from tblob where n1=rec.n1 for update; 
   buffer := rec.l1; 
   amount := utl_raw.length(rec.l1); 
   dbms_lob.write(lobloc,utl_raw.length(rec.l1),1,buffer); 
 end loop; 
end; 
/ 

Example #2[LONG/LONG RAW to CLOB]

The following example shows a method for converting LONG columns into CLOB using PL/SQL.

 
CREATE OR REPLACE PROCEDURE Long2Lob( 
  -- Uses DBMS_SQL to select a LONG column identified by p_LongQuery, and 
  -- returns it in p_CLob. 
  p_LongQuery IN VARCHAR2, 
  p_CLob IN OUT CLOB) AS 
 
  c_ChunkSize CONSTANT INTEGER := 100; 
 
  v_CursorID INTEGER; 
  v_RC INTEGER; 
  v_Chunk VARCHAR2(100); 
  v_ChunkLength INTEGER; 
  v_Offset INTEGER := 0; 
BEGIN 
  -- Open the cursor, define, execute, and fetch. 
  v_CursorID := DBMS_SQL.OPEN_CURSOR; 
  DBMS_SQL.PARSE(v_CursorID, p_LongQuery, DBMS_SQL.V7); 
  DBMS_SQL.DEFINE_COLUMN_LONG(v_CursorID, 1); 
  v_RC := DBMS_SQL.EXECUTE_AND_FETCH(v_CursorID); 
 
  -- Loop over the LONG, fetching c_ChunkSize characters at a time from 
  -- the LONG and adding them to the LOB. 
  LOOP 
    DBMS_SQL.COLUMN_VALUE_LONG(v_CursorID, 1, c_ChunkSize, v_Offset, 
                          v_Chunk, v_ChunkLength); 
    DBMS_LOB.WRITE(p_CLob, v_ChunkLength, v_Offset + 1, v_Chunk); 
    IF v_ChunkLength < c_ChunkSize THEN 
      EXIT; 
    ELSE 
      v_Offset := v_Offset + v_ChunkLength; 
    END IF; 
  END LOOP; 
 
  DBMS_SQL.CLOSE_CURSOR(v_CursorID); 
EXCEPTION 
  WHEN OTHERS THEN 
   -- Clean up, and reraise the error. 
    DBMS_SQL.CLOSE_CURSOR(v_CursorID); 
    RAISE; 
END Long2Lob; 
/

How to Identify the sql which cause PL/SQL LOCK TIMER wait event

7/18/2012 No Comment

PL/SQL LOCK TIMER wait event.

How to identify the SQL statement which causes high PL/SQL LOCK TIMER wait event that may appear in statspack reports?

Solution

Please use the below query:
SELECT vs.inst_id,vs.osuser,vw.event,vw.p1,vw.p2,vw.p3 ,vt.sql_text , vs.program
FROM gv$session_wait vw, gv$sqltext vt , gv$session vs
WHERE vw.event = 'PL/SQL lock timer'
AND vt.address=vs.sql_address
AND vs.inst_id = vw.inst_id
AND vs.sid = vw.sid;
 

Aired | The content is copyrighted and may not be reproduced on other websites. | Copyright © 2009-2016 | All Rights Reserved 2016

Contact Us | About Us | Privacy Policy and Disclaimer