Monday, March 26, 2012

Oracle 10g Webutil Delay on Loading

Slow performance for form embeded with WebUtil 1.0.6

The form takes an extra 30-50 seconds to load. This happens while using Webutil 1.0.6 with Forms 9.0.4.1, 10.1.2 and later releases.

Causes:
1. The problem occurs when the NetBIOS over TCP/IP is enabled for the intranet web clients. WebUtil 1.0.6 has issues when NetBIOS over TCP/IP is enabled.

2. When client access the application using IP address instead of URL with domain name. NetBIOS does computer name to IP address mapping, name resolution via NETBT.SYS in Windows NT and VNBT.VXD in Windows 95. NetBIOS will be invoked when IP address is used instead or domain name.

Solution:
1. The NetBIOS over TCP/IP should be disabled for the intranet web clients accessing the web forms. IP address to computer name mapping and name resolution could also be achieved via DNS.

To disable the NetBIOS over TCP/IP, please execute the following steps:

a. Go to the properties of "Network Configuration" on the client machine.
b. Click on "Internet Protocol(TCP/IP)".
c. Click on "Properties" push button.
d. Click on "Advanced" push button.
e. Click on "WINS" tab.
f. Click the radio button "Disable NetBIOS over TCP/IP.

2. Manually map the IP address at Host file in client machine.
a. Go to path in Windows "C:\WINDOWS\system32\drivers\etc"
b. Edit the "hosts" file using text editor
c. Put in the application IP address and mapping name.
d. Save and close the document.


Note: "If you are running your forms on local area network using application server then add DNS entry on Domain Server"


Saturday, March 17, 2012

How to Read data from an Excel Spreadsheet into an Oracle Form using WebUtil


Description of included files:
1. create_planets.sql – script to create the table used by this sample code
2. planets_ole_excel_read.fmb – sample form which demonstrates the concept
3. planets.xls – Excel (version 2003) sample spreadsheet

Setup steps:
1. Log into your database and run the “create_planets.sql” script
2. Ensure your environment is properly configured to run WebUtil. This document does not cover this configuration – there is plenty of information available in the OTN forums as well on the Internet that covers configuring WebUtil so I will not included it here.
3. Place “planets.xls’ some place on the client computer. I have modified Oracle’s original form to display a “File Select dialog” rather than hard code the file name and location in the code as Oracle demo did.
4. Ensure you have configured the Forms Builder to allow running a form from the Forms Builder. This document does not cover how to perform this configuration.
5. Run the form from the Forms Builder or on the client computer and push the “Read from Excel” button. Choose the ‘planets.xls’ file from the “Select Client filename to Open” dialog and the data will be read from the Excel spreadsheet into the form. You can then push the save button in the toolbar to commit the data to the table.

Here is the code behind the “Read from Excel” button with some explanatory comments:

DECLARE
application Client_OLE2.Obj_Type;
workbooks Client_OLE2.Obj_Type;
workbook Client_OLE2.Obj_Type;
worksheets Client_OLE2.Obj_Type;
worksheet Client_OLE2.Obj_Type;
worksheet2 Client_OLE2.Obj_Type;
cell Client_OLE2.OBJ_TYPE;
args Client_OLE2.OBJ_TYPE;
cell_value varchar2(100);
num_wrkshts NUMBER;
wksht_name VARCHAR2(250);
eod Boolean := false;
j integer := 1;
v_fName VARCHAR2(250);
BEGIN
-- Get the name of the file to open
--v_fName :=
'D:\MyDevelopment\Forms\Samples\WebUtil\Read_Excel\planets3.xls';
-- My Way: Use a File Open Dialog to let the user select the file.
v_fName := WebUtil_File.File_Open_Dialog(
directory_name => 'C:\'
,File_Filter => null
,Title => 'Select Client filename to Open.'
);

-- Make sure the user selected a file
IF ( v_fName IS NOT NULL ) THEN
-- The following sets up communication with the excel spreadsheet
-- --------------------------------------------------------------

-- Open the OLE application
application := Client_OLE2.create_obj('Excel.Application');
-- Keep the application hidden
Client_OLE2.set_property(application,'Visible','false');

workbooks := Client_OLE2.Get_Obj_Property(application, 'Workbooks');
args := Client_OLE2.CREATE_ARGLIST;

-- Open the selected File
-- ----------------------
Client_OLE2.add_arg(args,v_fName);
workbook := Client_OLE2.GET_OBJ_PROPERTY(workbooks,'Open',args);
Client_OLE2.destroy_arglist(args);

worksheets := Client_OLE2.GET_OBJ_PROPERTY(workbook, 'Worksheets');

-- Get number of worksheets
-- ------------------------
num_wrkshts := Client_OLE2.GET_NUM_PROPERTY(worksheets, 'Count');
worksheet := Client_OLE2.GET_OBJ_PROPERTY(
application,'activesheet');

--Go to the first record
go_block('planets');
first_record;

-- Loop through the Block and create a new row if needed.
loop
If :system.record_status <> 'NEW' then
create_record;
end if;

-- Exit when the last row of the spreadsheet is reached.
exit when eod;

-- Loop through the spreadsheet and get cell values
for k in 1..3 loop --3 fields per record
-- You have to know fields there are
args:= Client_OLE2.create_arglist;
Client_OLE2.add_arg(args, j);
Client_OLE2.add_arg(args, k);
cell:= Client_OLE2.get_obj_property(worksheet, 'Cells', args);
Client_OLE2.destroy_arglist(args);
cell_value :=Client_OLE2.get_char_property(cell, 'Value');

-- Check for End of Data…
if upper(cell_value) = 'EOD' then
eod:=true;
Message('End of Data');
exit;
end if;

-- Copy the value from Excel to the Forms block item
-- This is how the Oracle example copied values
/*if k =1 then
:dept.deptno:=cell_value;
end if;

if k =2 then
:dept.dname:=cell_value;
end if;

if k =3 then
:dept.loc:=cell_value;
end if;
*/

-- This is my way; which is more efficient and less code
copy(cell_value,name_in('system.cursor_item'));
next_item;

end loop; --for

j:=j+1;
end loop; --main loop

-- Release the Client_OLE2 object handles
IF (cell IS NOT NULL) THEN
Client_OLE2.release_obj(cell);
END IF;
IF (worksheet IS NOT NULL) THEN
Client_OLE2.release_obj(worksheet);
END IF;
IF (worksheets IS NOT NULL) THEN
Client_OLE2.release_obj(worksheets);
END IF;
IF (worksheet2 IS NOT NULL) THEN
Client_OLE2.release_obj(worksheet2);
END IF;
IF (workbook IS NOT NULL) THEN
Client_OLE2.release_obj(workbook);
END IF;
IF (workbooks IS NOT NULL) THEN
Client_OLE2.release_obj(workbooks);
END IF;
Client_OLE2.invoke(application,'Quit');
Client_OLE2.release_obj(application);
ELSE
Message('No File selected.');
message(' ');
RAISE Form_Trigger_Failure;
END IF;
END;


Thursday, March 17, 2011

How to use a calendar in a Form

Introduction

How to implement a Calendar object in an Oracle Form is a fairly common question in the Oracle Technology Network Forms Forum. There are a couple of very nice demo’s available on the Internet as well as Oracle’s own demo in the Forms Code Samples. However, because it is getting harder and harder to find the demo’s on Oracle’s site, I decided to write this document.

Disclaimer

I want to be very clear – I did not write either of these calendars. I am simply writing this document as a way of making information that is available in separate documents available in a single document. Please check the references section for information on where I obtained the source code for these calendars.

Between the two solutions (Forms versus Java) I prefer the Forms version solely because it is a little faster (based solely on my experience) than the Java version and the Java version does not conform to the look and feel of a Forms application.

How this document is organized

This document will take you step-by-step through implementing both a Forms based calendar (adapted from Oracle’s supplied demo’s) as well as a Java based calendar (see Resources at the end of this document).
I will list the steps to use the Forms calendar first and then list the step to use the Java version second. This demo is organized such that there are two separate Date items in the Form; the first using the Forms Calendar and the second using the Java calendar. This allows you to judge for yourself which one is more suitable for your needs.
This document will walk you step-by-step through the creation of an Oracle Form that implements both calendars – even though I have included all the source code.
Forms Version

This demo was written using Oracle Developers Suite 10g R1 (10.1.2.0.2) with no patches applied. This makes it usable by any version of Forms 10g.

Objects included in this demo

CALENDAR.olb
FJCalendar.jar
jcalendar-1.3.2.jar
looks-2.0.1.jar
FRM_JAVA_CALENDAR.fmb
How to implement a Calendar object in an Oracle Form.doc
(See the Calendar.zip file in the attachments section below)
Java Requirements!

The Java Runtime Environment (JRE) needed to run this demo is the Sun JRE version 1.5.0_22, but it is highly recommended that you use the latest Sun JRE (currently 1.6.0_22). If you want to configure Forms Builder to use the Sun JRE, but don’t know how too, see my article: "Forms How to – Configure Forms Builder to use Sun JRE.”

If you need a version of the Java calendar that runs with the Oracle Jinitiator please the references section for the URL where I got the Java calendar.

Setup

Copy the supplied CALENDAR.olb to a directory listed in your FORMS_PATH.
The .jar files listed above must be copied to the \forms\server\java folder and you must modify the default.env CLASSPATH to include the full path to the FJCalendar.jar.
(For example: C:\DevSuiteHome10g\forms\java\FJCalendar.jar)
The .jar file must be listed in the ARCHIVE parameter in the formsweb.cfg.
(For example: archive=frmall.jar,FJCalendar.jar
Let’s get started!

First, you will need to have the Oracle Developer Suite 10g R2 (10.1.2.0.2) installed and configured to run forms locally. If you are unable to run a form from the Forms Builder – then you will need an application server available where you can deploy and test your form. I prefer running a Form from the Forms Builder as it allows me to incrementally develop a form as well as run the Forms Debugger if I run into trouble with a particular section of code. This document assumes you have completed the necessary configuration to run a form from the Forms Builder. If you need assistance configuring Forms Builder to run forms locally, see my article: “"Forms: How to Configure Forms Builder to run forms locally.”

Step-by-Step

Start the Forms Builder and create a new Forms Module.
Log into a database – doesn’t matter which database because the form we’re creating does not have any base table objects.
Open the CALENDAR.olb and double-click on the CALENDAR node in the Object Libraries.

This will open the CALENDAR object library pane.
From the CALENDAR object library pane, click on CALENDAR and drag and drop it on the Object Groups node of your new form.

You will be prompted to Subclass, Copy or cancel the operation. It is recommended that you subclass the objects, but you can copy them if you prefer.
If you subclass – the CALENDAR.olb must be located in a directory listed in your FORMS_PATH (as mentioned above).
Once copied or subclassed, you should see the following objects in the Forms Object Navigator (note; my example has the little red arrow on each object indicating that this object is subclassed).

Now lets add the rest of the objects needed for this demo. I use a control block in this demo so there is no need to create any tables to support this demo.
Go to the Windows node of the object navigator and open the property pallet of the WINDOW1 object and set the following properties: (WINDOW1 is created by default by the Forms Builder)
Name: MAIN
Width: 380
Height: 225
Now, select the Module node (very top) and set the following properties:
Name: FRM_JAVA_CALENDAR
Title: Forms and Java Calendar Demo
Console Window: MAIN
Add a new Canvas object to the Canvases node and then open the property pallet for the canvas and set the following properties:
Name: CALENDAR
Window: MAIN
Width: 380
Height: 225
Create a new Data Block and select “Build a new block manually”.
Ensure this block appears first in the list before the DATE_CONTROL_BLOCK and DATE_BUTTON_BLOCK blocks.
Open the property pallet for the new block and set the following properties:
Name: CONTROL
Database Data Block: No
Click on the Items node of the CONTROL block and Add 5 new items.
Click on the first item and set the following properties:
Name: FORMS_DATE
Data Type: DATE
Canvas: CALENDAR
X Position: 90
Y Position: 45
Prompt: Forms Dat
Select the second item and set the following properties:
Name: JAVA_DATE
Data Type: DATE
Canvas: CALENDAR
X Position: 90
Y Position: 60
Prompt: Java Date
Select the third item and set the following properties:
Name: BTN_FORMS_DATE
Item Type: Push Button
Label: Forms Date
Canvas: CALENDAR
X Position: 160
Y Position: 45
Select the fourth item and set the following properties:
Name: BTN_JAVA_DATE
Item Type: Push Button
Label: Java Date
Canvas: CALENDAR
X Position: 160
Y Position: 60
Select the fifth item and set the following properties:
Name: BEAN_AREA
Item Type: Bean Area
Implementation Class: oracle.forms.fd.JCalendar
Canvas: CALENDAR
X Position: 20
Y Position: 30
Width: 0
Height:
Note: It is important that your Bean Area be zero size and visible or the Java Calendar will not display properly.

At this point, your Form should look like the following:


Now we are ready to start writing the code to display and capture the dates from the calendars.
First, we need to compile all code in the Form. I prefer keyboard short-cuts, but you can use the menu if you prefer.
Program Menu => Compile PL/SQL => All
OR
Ctrl + Shift + K
Select BTN_FORMS_DATE item and add a When-Button-Pressed trigger with the following code:


DECLARE
cur_x_pos INTEGER := 0;
cur_y_pos INTEGER := 0;
new_x_pos INTEGER := 0;
new_y_pos INTEGER := 0;
item_height INTEGER := 0;
my_date VARCHAR2(25);
BEGIN
cur_x_pos := Get_Item_Property('CONTROL.FORMS_DATE',x_pos);
cur_y_pos := Get_Item_Property('CONTROL.FORMS_DATE',y_pos);
item_height := Get_Item_Property('CONTROL.FORMS_DATE',height);

new_x_pos := cur_x_pos;
new_y_pos := cur_y_pos + item_height + 2;

Date_Lov.get_Date(display_date => sysdate
,return_item => 'CONTROL.FORMS_DATE'
,v_x_pos => new_x_pos
,v_y_pos => new_y_pos
,v_title => 'FORMS DATE PICKER'
,v_ok => 'OK'
,v_cancel => 'Cancel'
,V_highlight => FALSE
,v_autoconfirm => FALSE
,v_autoskip => FALSE
);
END;

Select the BTN_JAVA_DATE item and add a When-Button-Pressed trigger with the following code:
BEGIN
Set_Custom_Property('CONTROL.BEAN_AREA',1,'SHOW_CALENDAR','50,50');
END;

Lastly, we need to add a When-Custom-Item-Event trigger to CONTROL.BEAN_AREA with the following code:

DECLARE
event_name VARCHAR2(30) := :system.custom_item_event;
event_vals ParamList;
event_val_type NUMBER;
jb_date VARCHAR2(256); --Complete Date
jb_day VARCHAR2(256); --Day Number (1-31)
jb_month VARCHAR2(256); --Month Number (1-12)
jb_year VARCHAR2(256); --Year number (YYYY)
BEGIN
IF ( event_name = 'CALENDAR_EVENT' ) THEN
event_vals := Get_Parameter_List(:SYSTEM.Custom_Item_Event_Parameters);
Get_Parameter_Attr(event_vals, 'CALENDAR_EVENT_DATE', event_val_type, jb_date);
Get_Parameter_Attr(event_vals, 'CALENDAR_EVENT_DAY', event_val_type, jb_day);
Get_Parameter_Attr(event_vals, 'CALENDAR_EVENT_MONTH', event_val_type, jb_month);
Get_Parameter_Attr(event_vals, 'CALENDAR_EVENT_YEAR', event_val_type, jb_year);
:CONTROL.JAVA_DATE := jb_month||'/'||jb_day||'/'||jb_year;
Synchronize;
END IF;
END;

We’re now ready to test the form. If you have configured Forms Builder to run forms locally, make sure you start the OC4J Instance first, and then Click on the Run Icon () in the toolbar or press Ctrl + R.

Your form should look like the following:



Forms Date Picker:





Java Date Picker:




Final Results:








Reference:

A Java Swing Calendar, published by Francios Degrelle; December 21, 2007 (http://forms.pjc.bean.over-blog.com/article-14848846.html)
Oracle Corporation; Forms 10g Demo Files (http://www.oracle.com/technetwork/developer-tools/forms/overview/index.html)
Č
ċďv.1
CALENDAR.olb (68k)Craig Butts, Apr 17, 2012, 2:16 PM
ċďv.2
Calendar.zip (558k)Craig Butts, Apr 6, 2011, 2:14 PM

How to install and configure Webutil on Oracle Application Server 10g/Developer 10g both on Windows/Linux

Setup WebUtil for Developer Suite 10g or Oracle AS 10g


WebUtil is a powerful component in Oracle Form 9i,10g, but setting up WebUtil is a nightmare for most of the developer. I hope the guideline below is useful for people who wish to setup WebUtil at Windows environment.

Steps to setup WebUtil in Developer Suite / Oracle Application Server
***********************************************************

1.  Download Webutil_106.zip & Jacob Library from following paths:



2.  Extract the zip files into Copy the files to the specified folders
  • frmwebutil.jar, forms_base_ie.js and forms_ie.js
    • From Folder: webutil_106\webutil_106\java  To: $ORACLE_HOME/forms/java
  • d2kwut60.dll, JNIsharedstubs.dll and sign_webutil.bat
    • From folder: webutil_106\webutil_106\webutil To: $ORACLE_HOME/forms/webutil
  • jacob.jar 
    • From folder: jacob_18  To: $ORACLE_HOME/forms/java
  • jacob.dll
    • From folder: jacob_18 To: $ORACLE_HOME/forms/webutil
  • webutil.olb, webutil.pll and create_webutil_db.sql
    • From folder: webutil_106\webutil_106 To: $ORACLE_HOME/forms
  • webutilbase.htm, webutiljini.htm, webutiljpi.htm and webutil.cfg
    • From folder: webutil_106\webutil_106\server To: $ORACLE_HOME/forms/server
     
3.  Modify the default.env file
You can find this file at C:\DevSuiteHome_1\forms\server\default.env
  • Append webutil file's path in FORMS_PATH entry
    • ;C:\DevSuiteHome_1\forms\webutil
  • Append frmwebutil.jar, jacob.jar file's path into CLASSPATH entry
    • ;c:\DevSuiteHome_1\forms\java\frmwebutil.jar;c:\DevSuiteHome_1\forms\java\jacob.jar;C:\oracle\DevSuiteHome_1\jdk\jre\lib\rt.jar
  • Make sure WEBUTIL_CONFIG entry as
    • C:\DevSuiteHome_1\forms\server\webutil.cfg

4.  Add frmwebutil.jar and Jacob.jar path entries into Windows Registry 

  • Start > Run > type regedit and press enter
  • HKEY_LOCAL_MACHINE > Software > Oracle > KEY_DevSuiteHome1 > FORMS_BUILDER_CLASSPATH and add following entry at the end 
    • c:\DevSuiteHome_1\forms\java\frmwebutil.jar;c:\DevSuiteHome_1\forms\java\frmall.jar;c:\DevSuiteHome_1\forms\java\jacob.jar;

Note: if you are using Linux then instead of this setup the environment variable.


5.  Modify the formsweb.cfg file,
You can find this file at C:\DevSuiteHome_1\forms\server\formsweb.cfg


Append following entries
# Forms applet archive setting for JInitiator
archive_jini=frmall_jinit.jar,frmwebutil.jar,jacob.jar
# Forms applet archive setting for other clients (Sun Java Plugin, Appletviewer, etc)
archive=frmall.jar,jfrmall_jinit.jar,frmwebutil.jar,jacob.jar

At webutil section (at the bottom), you also have to confirm the entries as

[webutil]
WebUtilArchive=frmwebutil.jar,jacob.jar
WebUtilLogging=off
WebUtilLoggingDetail=normal
WebUtilErrorMode=Alert
WebUtilDispatchMonitorInterval=5
WebUtilTrustInternal=true
WebUtilMaxTransferSize=16384
baseHTMLjinitiator=webutiljini.htm
baseHTMLjpi=webutiljpi.htm
archive_jini=frmall_jinit.jar
archive=frmall.jar
lookAndFeel=oracle


6.  Modify the webutil.cfg file (Optional)
You can find this file at  C:\DevSuiteHome_1\forms\server\webutil.cfg

#transfer.database.enabled=FALSE (default value)
transfer.database.enabled=TRUE
#transfer.appsrv.enabled=FALSE (default value)
transfer.appsrv.enabled=TRUE


7.  Signing frmwebutil.jar and Jacob.jar. (make sure form builder is closed)
On Dos Prompt Sign frmwebutil.jar and jacob.jar with following commands

C:\DevSuiteHome_1\forms\webutil>sign_webutil.bat c:\DevSuiteHome_1\forms\java\frmwebutil.jar

Output
Generating a self signing certificate for key=webutil2...
...successfully done.

Backing up C:\oracle\DevSuiteHome_1\forms\java\frmwebutil.jar as C:\oracle\DevSuiteHome_1\forms\java\frmwebutil.jar.old...
1 file(s) copied.
Signing C:\oracle\DevSuiteHome_1\forms\java\frmwebutil.jar using key=webutil2...
...successfully done.

C:\DevSuiteHome_1\forms\webutil>sign_webutil.bat c:\DevSuiteHome_1\forms\java\jacob.jar

Output
Generating a self signing certificate for key=webutil2...
keytool error: java.lang.Exception: Key pair not generated, alias already exists
.
There were warnings or errors while generating a self signing certificate. Please review them.
.
Backing up C:\oracle\DevSuiteHome_1\forms\java\jacob.jar as C:\oracle\DevSuiteHome_1\forms\java\jacob.jar.old...
1 file(s) copied.
Signing C:\oracle\DevSuiteHome_1\forms\java\jacob.jar using key=webutil2...
...successfully done.


8.  Configuration of webutil in database.

  • Open sqlplus and connect with sys as sysdba credentials.
  • Run / execute create_webutil_db.sql. This script will create webutil package in the database user.
  • You need to make this package available to all users. For this execute following command with sys user.
    • create public synonym webutil_db for webutil.webutil_db; 
    • grant execute on webutil_db to public;
    • Commit;

9.  How to use Webutil on Form Development Environment?
  • Open Form builder & connect with any user 
  • Open Webutil.pll file in oracle forms builder located at C:\DevSuiteHome_1\forms\ and press (Shift+Ctrl+K), and generate plx.
  • Open WebUtil.olb object group in oracle form builder and copy / subclass it into your oracle form as
    • Add webutilconfig into parameter node.
    • Add webutil into object group node.
  • Attached the Webutil.pll library to your form with remove path option YES.
  • Compile the PLL file
  • Start OC4J Instance
  • Add following code on when_new_form_instance or any other place where you wan
    • declare 
    • fake_timer TIMER;
    • begin
    • fake_timer:= CREATE_TIMER('webutil',100,NO_REPEAT);
    • end;
  • Add when_timer_expired trigger and add following code
    • :global.user_home := webutil_clientinfo.get_system_property('user.home');
  • Now create 1 text item and 1 push button  in block and show on canvas also
  • Behind push button write the code
    • :text_field:=webutil_clientinfo.get_system_property('user.home');
  • Now compile & run your form.
  • When form loaded then browser will ask to certify these libraries first time, choose always certify.
  • Check java console icon on the taskbar to verify the frmwebutil.jar and jacob.jar loaded successfully. 
On Linux you may compile the library with below command: 
a.frmcmp module=ORACLE_HOME\forms\webutil.pll userid= module_type=library compile_all=yes

In case, you like above material, please remember me in your prayers.

Configure UTL_MAIL and UTL_SMTP in any Oracle Database Version

In order to send e-mail from oracle database, we must needs to install and set up UTL_MAIL and UTL_SMTP packages. To use these package, the smtp_out_server parameter must be set & “network acl” should be created for the relevant user and the relevant privileges must be defined. Here I will guide you how to set up both packages. Please follow all instructions / steps mentioned below.

·         Connect with databases

SYS/password AS SYSDBA;

Or (assume SSK is also a dba user)

SSK/password;

 

Connected

·         First, we have to check, whether UTL_MAIL and UTL_SMTP are installed or not

select * from DBA_OBJECTS where OBJECT_NAME in('UTL_MAIL','UTL_SMTP');

no rows selected.

 

* In our case, we are assuming that both utl_mail & utl_stmp are not installed. Then follow below

·         Next, Install the packages (Change the path below with your Oracle Home path)

In Windows

SQL> @C:\oraclexe\app\oracle\product\11.2.0\server\rdbms\admin\utlmail.sql

Package created

Synonym created

SQL> @C:\oraclexe\app\oracle\product\11.2.0\server\rdbms\admin\utlsmtp.sql

Package created

Synonym created

SQL> @C:\oraclexe\app\oracle\product\11.2.0\server\rdbms\admin\prvtmail.plb

Package body created

 

In Linux

@$ORACLE_HOME/rdbms/admin/utlmail.sql

@$ORACLE_HOME/rdbms/admin/prvtmail.plb

 

Commit;

·         Then, Grant the privilege to all the users for UTL_MAIL package

SQL> GRANT EXECUTE ON utl_mail TO PUBLIC;

SQL> GRANT EXECUTE ON utl_smtp TO PUBLIC;

Commit;

 

You can give a specific username instead of public. If you will not give the grant on UTL_MAIL / UTL_SMTP packages, then you may get the following error:

PLS-00201: identifier 'UTL_MAIL' must be declared

PLS-00201: identifier 'UTL_SMTP' must be declared

·         Check value of SMTP_OUT_SERVER parameter

SQL> select value,display_value from v$parameter where upper(name) like '%SMTP%SERVER%';

 

It will show resultant value of SMTP_OUT_SERVER. If shows wrong / null then set / correct with below.

·         Set the SMTP_OUT_SERVER parameter

Suppose our mail server address is 192.168.255.255. You have to check with your OS admin for this smtp mail server hostname/hostname.

SQL> alter system set smtp_out_server='192.168.255.255' scope=both;

System altered

Commit;

 

*If smtp_out_server is set incorrectly, then it will throw error -: ORA-29278: SMTP transient error: 421 Service not available

·         Create ACL and privileges: Now create ACLS

First, create an ACL as SYS (or any other user with DBMS_NETWORK_ACL_ADMIN execute granted i.e. SSK), this will hold the privileges. You can add as many privileges as you like to this file, but I would recommend to split privileges in the ACL to specific tasks or users. You must create an ACL with at least one privilege, so let’s start with the connect’ & ‘resolve’ privileges for user SSK.

Create ACL with below

SQL> EXECUTE DBMS_NETWORK_ACL_ADMIN.CREATE_ACL('ssk_utlmail.xml','Allow mail to be send','SSK',TRUE,'connect');

Commit;

 

Grant the connect and resource privilege as below

SQL> EXECUTE DBMS_NETWORK_ACL_ADMIN.ADD_PRIVILEGE('ssk_utlmail.xml','SYS',TRUE,'connect');

SQL> EXECUTE DBMS_NETWORK_ACL_ADMIN.ADD_PRIVILEGE('ssk_utlmail.xml','SYS',TRUE,'resolve');

SQL> EXECUTE DBMS_NETWORK_ACL_ADMIN.ASSIGN_ACL('ssk_utlmail.xml','*',25);

SQL> EXECUTE DBMS_NETWORK_ACL_ADMIN.ASSIGN_ACL(acl=>'ssk_utlmail.xml',HOST => '192.168.255.255');

Commit;

·         Test whether user SSK is able to send mail or not

SQL>connect SSK/password

Connected

 

SQL> EXECUTE UTL_MAIL.SEND(SENDER=>'sender_email@ssk.com',RECIPIENTS=>'receiver.email@ssk.com', SUBJECT => 'Test Subject', MESSAGE=>'Test Message');

If every step followed then you will receive email from the system. Otherwise send me your error message to guide you.

·         Dictionary tables for ACLS

SQL> SELECT * FROM DBA_NETWORK_ACLS;

SQL> SELECT * FROM DBA_NETWORK_ACL_PRIVILEGES;