Tuesday, September 13, 2011

PL/SQL Easy Reference

PL/SQL Easy reference:-

Advantages of PL/SQL

PL/SQL is a completely portable, high-performance transaction processing language
that offers the following advantages:
■ Tight Integration with SQL
■ Better Performance
■ Higher Productivity
■ Full Portability
■ Tight Security
■ Access to Pre-defined Packages
■ Support for Object-Oriented Programming
■ Support for Developing Web Applications and Pages

Block Structure:-

[DECLARE
-- declarations]
BEGIN
-- statements
[EXCEPTION
-- handlers]
END;



1) Declaring Variables:-


part_no NUMBER(6);
part_name VARCHAR2(20);
in_stock BOOLEAN;
part_price NUMBER(6,2);
raise_app_err exception;

emp_rec1 employees%ROWTYPE; -- The datatype of all columns of employees table.

eg:-

DECLARE
CURSOR c1 IS
SELECT last_name, salary, hire_date, job_id FROM employees
WHERE employee_id = 120;
employee_rec c1%ROWTYPE;
BEGIN
OPEN c1;
FETCH c1 INTO employee_rec;
DBMS_OUTPUT.PUT_LINE('Employee name: ' || employee_rec.last_name);
CLOSE C1;
END;
/



emp_rec2 employees.ename%TYPE; -- The datatype of ename column of employee table.


name varchar2(30);
anname name%type -- (anname datatype will be as per name datatype)



Collections:- (Similar to arrarys)

TYPE commissions IS TABLE OF NUMBER INDEX BY PLS_INTEGER; -- Used for storing array values
comm_tab commissions;

TYPE staff_list IS TABLE OF employees.employee_id%TYPE;
staff staff_list ;

begin
staff := staff_list(100,200,300,400,500);
FOR i IN staff.FIRST..staff.LAST LOOP
SELECT last_name, first_name INTO lname, fname FROM employees
WHERE employees.employee_id = staff(i);
DBMS_OUTPUT.PUT_LINE ( TO_CHAR(staff(i)) || ': ' || lname || ', ' || fname );
END LOOP;
END;
/

Record:- (Records are composite data structures whose fields can have different datatypes.)

TYPE meetin_typ IS RECORD(
date_held DATE,
duration timerec, -- nested record
location VARCHAR2(20),
purpose VARCHAR2(50));
met_ty meetin_typ




Different methods to assign arrays:-

DECLARE
TYPE nested_type IS TABLE OF VARCHAR2(30);
TYPE varray_type IS VARRAY(5) OF INTEGER;
TYPE assoc_array_num_type IS TABLE OF NUMBER INDEX BY PLS_INTEGER;
TYPE assoc_array_str_type IS TABLE OF VARCHAR2(32) INDEX BY PLS_INTEGER;
TYPE assoc_array_str_type2 IS TABLE OF VARCHAR2(32) INDEX BY VARCHAR2(64);
v1 nested_type;
v2 varray_type;
v3 assoc_array_num_type;
v4 assoc_array_str_type;
v5 assoc_array_str_type2;
BEGIN
-- an arbitrary number of strings can be inserted v1
v1 := nested_type('Shipping','Sales','Finance','Payroll');
v2 := varray_type(1, 2, 3, 4, 5); -- Up to 5 integers
v3(99) := 10; -- Just start assigning to elements
v3(7) := 100; -- Subscripts can be any integer values
v4(42) := 'Smith'; -- Just start assigning to elements
v4(54) := 'Jones'; -- Subscripts can be any integer values
v5('Canada') := 'North America'; -- Just start assigning to elements
v5('Greece') := 'Europe'; -- Subscripts can be string values
END;
/





2) Assigning values to variables:-

hourly_salary NUMBER := 22.50;
v_ename_first varchar2(30) := 'MANZOOR';
v_ename_last varchar2(30);
in_stock BOOLEAN := TRUE;
done BOOLEAN;

begin
comm_tab(5) := 20000 * 0.15;
select ename_last into v_ename_last from emp where empid = 10;
done := (counter > 100);
end;

blood_type char := 'O'; (OR) blood_type char default 'O';

cnt number not null := 100;



3) Declaring Constants

cons constant number := 10;


4) Processsing Queries with pl/sql

BEGIN
FOR someone IN (SELECT * FROM employees WHERE employee_id < 120 )
LOOP
DBMS_OUTPUT.PUT_LINE('First name = ' || someone.first_name ||
',Last name = ' || someone.last_name);
END LOOP;
END;
/


5) IF Statement

Syntax:-
if condition then
stmt;
elseif condition then
stmt;
else
stmt;
end if;

6) Case Statement

Syntax:-

Case when condition then
stmt;
when condition then
stmt;
else
stmt;
end case;

7) Loop Statements:-

Syntax:-
Loop
stmt;
exit when condition;
End loop;
For Loop

Syntax:-
for i in 1..n loop
stmt;
end loop;

for i in (select * from emp) loop
stmt;
end loop;
While loop

Syntax:-

while condition loop
Stmt;
end loop;

8) Goto Statement (unconditional control transfer):-

Syntax:-
<>

eg:
i:=0;
<>
i := 1+1;
if i > 10 then
goto gothere;
else
goto comehere;
end if;
<>
end;

9) Using a Block Label for Name Resolution

<
>
DECLARE
last_name VARCHAR2(10) := 'King';
BEGIN
-- deletes everyone, because both LAST_NAMEs refer to the column
DELETE FROM employees2 WHERE last_name = last_name;
DBMS_OUTPUT.PUT_LINE('Deleted ' || SQL%ROWCOUNT || ' rows.');
ROLLBACK;
-- OK, column and variable have different names
DELETE FROM employees2 WHERE last_name = main.last_name;
DBMS_OUTPUT.PUT_LINE('Deleted ' || SQL%ROWCOUNT || ' rows.');
ROLLBACK;
END;
/




9) Creating a Stored procedures:-
create or replace procedure get_emp_name (v_emp in number) as
ss varchar2(30);
begin
select ename into ss from emp where empno = v_emp;
dbms_output.put_line ('Name of the Employee is :' || ss);
exception
when no_data_found then
dbms_output.put_line ('There is no employ with emp id :' || v_emp);
end;
/


To Exec (1st method):-


declare
emp_id number;
begin
emp_id := 100;
get_emp_name(emp_id);
end;
/

To Exec (2nd method):-
SQL> var emp_id number;
SQL> exec :emp_id := 100;
SQL> call get_emp_name(:emp_id);
Name of the Employee is :Ahamed
Call completed.


10) Creating Packages:-

I) Create Package Specification:-

CREATE OR REPLACE PACKAGE emp_actions AS
PROCEDURE hire_employee (employee_id NUMBER);
PROCEDURE fire_employee (emp_id NUMBER);
FUNCTION num_above_salary (emp_id NUMBER) RETURN VARCHAR2;
END emp_actions;
/

II) Create Package Body:-

CREATE OR REPLACE PACKAGE body emp_actions AS
PROCEDURE hire_employee (employee_id NUMBER) is
begin
insert into emp (empno) values (employee_id);
commit;
end;
PROCEDURE fire_employee (emp_id NUMBER) is
begin
delete from emp where empno = emp_id;
commit;
end;
FUNCTION num_above_salary (emp_id NUMBER) RETURN varchar2 is
emp_sal varchar2(30);
BEGIN
SELECT ename INTO emp_sal FROM emp WHERE empno = emp_id;
RETURN emp_sal;
END num_above_salary;
END emp_actions;
/

To Exec:-

a) SQL> exec emp_actions.hire_employee(100);
b) SQL> exec emp_actions.fire_employee(100);
C) SQL> select emp_actions.num_above_salary(10) from dual;
EMP_ACTIONS.NUM_ABOVE_SALARY(10)
--------------------------------
Ahamed


D) CALL emp_actions.hire_employee(300);
E)
BEGIN
DBMS_OUTPUT.PUT_LINE( 'NAME of employees whose emp id 120 is: ' ||
TO_CHAR(emp_actions.num_above_salary(120)));
emp_actions.fire_employee(300);
END;
/




Creation of triggers:-

CREATE TABLE emp_audit ( emp_audit_id NUMBER(6), up_date DATE,
new_sal NUMBER(8,2), old_sal NUMBER(8,2) );
CREATE OR REPLACE TRIGGER audit_sal
AFTER UPDATE OF salary ON employees FOR EACH ROW
BEGIN
-- bind variables are used here for values
INSERT INTO emp_audit VALUES( :old.employee_id, SYSDATE,
:new.salary, :old.salary );
END;
/



===== Still to add more===================================

Sunday, September 11, 2011

11g Dataguard Features

11g Dataguard Features:-

A. Setup dataguard using active database.

Normally when setting up datagurad using rman we need to copy the backup files to the
destination server and then we need to start using the duplicate command, but in
11g we dont need to copy the backup files to the destination server when creating
the standby databse using active database method.

Steps:-

1. Configure th listner.ora parameter to do a static registration of the
Standby database.

Eg:-

LISTENER =
(DESCRIPTION_LIST =
(DESCRIPTION =
(ADDRESS = (PROTOCOL = IPC)(KEY = EXTPROC1521))
(ADDRESS = (PROTOCOL = TCP)(HOST = rhel11gstdby.manzoor.com)(PORT = 1521))
)
)

SID_LIST_LISTENER =
(SID_LIST =
(SID_DESC =
(SID_NAME = PLSExtProc)
(ORACLE_HOME = /u01/app/oracle/product/10.2.0/db_1)
(PROGRAM = extproc)
)
(SID_DESC =
(SID_NAME = orclstdb )
(ORACLE_HOME = /u01/app/oracle/product/10.2.0/db_1)
)
)


2. Configure the tnsnames.ora file in target and the destination server accordingly.

3. Take the backup of the init parameter file from the target and modify it accordinly and transfer it to the destination server and modify it accordingly as per the destinaton database requirements.


4. Create the password file with same password as the target password.

5. startup the instance in nomount state in the destination server and exit the session.

6. In target connect to the target and the auxiliary database and execute the duplicate command.

[oracle@rhel11g u01]$ rman target sys/admin@orcl11g auxiliary sys/admin@orclstdb

Recovery Manager: Release 11.1.0.6.0 - Production on Mon Sep 12 09:45:07 2011

Copyright (c) 1982, 2007, Oracle. All rights reserved.

connected to target database: ORCL11G (DBID=867589313)
connected to auxiliary database: ORCL11G (not mounted)

RMAN> duplicate target database for standby from active database;

Starting Duplicate Db at 12-SEP-11
using target database control file instead of recovery catalog
allocated channel: ORA_AUX_DISK_1
channel ORA_AUX_DISK_1: SID=153 device type=DISK
allocated channel: ORA_AUX_DISK_2
channel ORA_AUX_DISK_2: SID=170 device type=DISK
allocated channel: ORA_AUX_DISK_3
channel ORA_AUX_DISK_3: SID=154 device type=DISK

contents of Memory Script:
{
backup as copy reuse
file '/u01/app/oracle/product/10.2.0/db_1/dbs/orapworcl11g' auxiliary format
'/u01/app/oracle/product/10.2.0/db_1/dbs/orapworclstdb' ;
}
executing Memory Script

Starting backup at 12-SEP-11
allocated channel: ORA_DISK_1
channel ORA_DISK_1: SID=129 device type=DISK
allocated channel: ORA_DISK_2
channel ORA_DISK_2: SID=134 device type=DISK
allocated channel: ORA_DISK_3
channel ORA_DISK_3: SID=130 device type=DISK
Finished backup at 12-SEP-11

contents of Memory Script:
{
backup as copy current controlfile for standby auxiliary format '/u01/app/oracle/oradata/orclstdb/control01.ctl';
restore clone controlfile to '/u01/app/oracle/oradata/orclstdb/control02.ctl' from
'/u01/app/oracle/oradata/orclstdb/control01.ctl';
restore clone controlfile to '/u01/app/oracle/oradata/orclstdb/control03.ctl' from
'/u01/app/oracle/oradata/orclstdb/control01.ctl';
sql clone 'alter database mount standby database';
}
executing Memory Script

Starting backup at 12-SEP-11
using channel ORA_DISK_1
using channel ORA_DISK_2
using channel ORA_DISK_3
channel ORA_DISK_1: starting datafile copy
copying standby control file
output file name=/u01/app/oracle/product/10.2.0/db_1/dbs/snapcf_orcl11g.f tag=TAG20110912T094518 RECID=2 STAMP=761651119
channel ORA_DISK_1: datafile copy complete, elapsed time: 00:00:03
Finished backup at 12-SEP-11

Starting restore at 12-SEP-11
using channel ORA_AUX_DISK_1
using channel ORA_AUX_DISK_2
using channel ORA_AUX_DISK_3

channel ORA_AUX_DISK_1: skipped, AUTOBACKUP already found
channel ORA_AUX_DISK_2: skipped, AUTOBACKUP already found
channel ORA_AUX_DISK_3: skipped, AUTOBACKUP already found
channel ORA_DISK_1: no AUTOBACKUP in 7 days found
channel ORA_DISK_2: no AUTOBACKUP in 7 days found
channel ORA_DISK_3: no AUTOBACKUP in 7 days found
channel clone_default: copied control file copy
Finished restore at 12-SEP-11

Starting restore at 12-SEP-11
using channel ORA_AUX_DISK_1
using channel ORA_AUX_DISK_2
using channel ORA_AUX_DISK_3

channel ORA_AUX_DISK_1: skipped, AUTOBACKUP already found
channel ORA_AUX_DISK_2: skipped, AUTOBACKUP already found
channel ORA_AUX_DISK_3: skipped, AUTOBACKUP already found
channel ORA_DISK_1: no AUTOBACKUP in 7 days found
channel ORA_DISK_2: no AUTOBACKUP in 7 days found
channel ORA_DISK_3: no AUTOBACKUP in 7 days found
channel clone_default: copied control file copy
Finished restore at 12-SEP-11

sql statement: alter database mount standby database

contents of Memory Script:
{
set newname for tempfile 1 to
"/u01/app/oracle/oradata/orclstdb/temp01.dbf";
switch clone tempfile all;
set newname for datafile 1 to
"/u01/app/oracle/oradata/orclstdb/system01.dbf";
set newname for datafile 2 to
"/u01/app/oracle/oradata/orclstdb/sysaux01.dbf";
set newname for datafile 3 to
"/u01/app/oracle/oradata/orclstdb/undotbs01.dbf";
set newname for datafile 4 to
"/u01/app/oracle/oradata/orclstdb/users01.dbf";
set newname for datafile 5 to
"/u01/app/oracle/oradata/orclstdb/example01.dbf";
backup as copy reuse
datafile 1 auxiliary format
"/u01/app/oracle/oradata/orclstdb/system01.dbf" datafile
2 auxiliary format
"/u01/app/oracle/oradata/orclstdb/sysaux01.dbf" datafile
3 auxiliary format
"/u01/app/oracle/oradata/orclstdb/undotbs01.dbf" datafile
4 auxiliary format
"/u01/app/oracle/oradata/orclstdb/users01.dbf" datafile
5 auxiliary format
"/u01/app/oracle/oradata/orclstdb/example01.dbf" ;
sql 'alter system archive log current';
}
executing Memory Script

executing command: SET NEWNAME

renamed tempfile 1 to /u01/app/oracle/oradata/orclstdb/temp01.dbf in control file

executing command: SET NEWNAME

executing command: SET NEWNAME

executing command: SET NEWNAME

executing command: SET NEWNAME

executing command: SET NEWNAME

Starting backup at 12-SEP-11
using channel ORA_DISK_1
using channel ORA_DISK_2
using channel ORA_DISK_3
channel ORA_DISK_1: starting datafile copy
input datafile file number=00001 name=/u01/app/oracle/oradata/orcl11g/system01.dbf
channel ORA_DISK_2: starting datafile copy
input datafile file number=00002 name=/u01/app/oracle/oradata/orcl11g/sysaux01.dbf
channel ORA_DISK_3: starting datafile copy
input datafile file number=00005 name=/u01/app/oracle/oradata/orcl11g/example01.dbf
output file name=/u01/app/oracle/oradata/orclstdb/example01.dbf tag=TAG20110912T094549 RECID=0 STAMP=0
channel ORA_DISK_3: datafile copy complete, elapsed time: 00:02:05
channel ORA_DISK_3: starting datafile copy
input datafile file number=00003 name=/u01/app/oracle/oradata/orcl11g/undotbs01.dbf
output file name=/u01/app/oracle/oradata/orclstdb/undotbs01.dbf tag=TAG20110912T094549 RECID=0 STAMP=0
channel ORA_DISK_3: datafile copy complete, elapsed time: 00:02:56
channel ORA_DISK_3: starting datafile copy
input datafile file number=00004 name=/u01/app/oracle/oradata/orcl11g/users01.dbf
output file name=/u01/app/oracle/oradata/orclstdb/users01.dbf tag=TAG20110912T094549 RECID=0 STAMP=0
channel ORA_DISK_3: datafile copy complete, elapsed time: 00:00:25
output file name=/u01/app/oracle/oradata/orclstdb/sysaux01.dbf tag=TAG20110912T094549 RECID=0 STAMP=0
channel ORA_DISK_2: datafile copy complete, elapsed time: 00:08:16
output file name=/u01/app/oracle/oradata/orclstdb/system01.dbf tag=TAG20110912T094549 RECID=0 STAMP=0
channel ORA_DISK_1: datafile copy complete, elapsed time: 00:08:26
Finished backup at 12-SEP-11

sql statement: alter system archive log current

contents of Memory Script:
{
switch clone datafile all;
}
executing Memory Script

datafile 1 switched to datafile copy
input datafile copy RECID=2 STAMP=761651617 file name=/u01/app/oracle/oradata/orclstdb/system01.dbf
datafile 2 switched to datafile copy
input datafile copy RECID=3 STAMP=761651617 file name=/u01/app/oracle/oradata/orclstdb/sysaux01.dbf
datafile 3 switched to datafile copy
input datafile copy RECID=4 STAMP=761651617 file name=/u01/app/oracle/oradata/orclstdb/undotbs01.dbf
datafile 4 switched to datafile copy
input datafile copy RECID=5 STAMP=761651618 file name=/u01/app/oracle/oradata/orclstdb/users01.dbf
datafile 5 switched to datafile copy
input datafile copy RECID=6 STAMP=761651618 file name=/u01/app/oracle/oradata/orclstdb/example01.dbf
Finished Duplicate Db at 12-SEP-11

RMAN> exit;


7. Now do a log switch in the primary and check whether the logs are applied correctly.






B) Active Datagurad:-

Prior to 11g the logs will not be applied in physical standby database if it is open in readonly mode, but from 11g the logs will get applied even when the standby database is in read only mode.

Eg:-

SQL> select sequence#, archived, applied from V$archived_log;

SEQUENCE# ARC APP
---------- --- ---
12 YES YES
8 YES YES
11 YES YES
9 YES YES
10 YES YES
13 YES YES
14 YES YES
15 YES YES
18 YES YES
17 YES YES
16 YES YES
19 YES YES
20 YES YES
21 YES YES
22 YES YES
23 YES YES
24 YES YES
25 YES YES
26 YES YES
27 YES YES
28 YES YES
29 YES YES

22 rows selected.

SQL> alter database recover managed standby database cancel;

Database altered.

SQL> alter database open read only;

Database altered.

SQL> alter database recover managed standby database disconnect from session;

Database altered.

Now do some logswith in the priarmy database....and the check whether the logs are applied in the standby databse.

SQL> select sequence#, archived, applied from V$archived_log;

SEQUENCE# ARC APP
---------- --- ---
12 YES YES
8 YES YES
11 YES YES
9 YES YES
10 YES YES
13 YES YES
14 YES YES
15 YES YES
18 YES YES
17 YES YES
16 YES YES
19 YES YES
20 YES YES
21 YES YES
22 YES YES
23 YES YES
24 YES YES
25 YES YES
26 YES YES
27 YES YES
28 YES YES
29 YES YES
30 YES YES
31 YES YES

24 rows selected.

We can see that the logs are getting applied even when the physical standby database
in the read only mode.

C) Snap shot standby:-


Introduced in 11g, snapshot standby allows the standby database to be opened in read-write mode. When switched back into standby mode, all changes made whilst in read-write mode are lost. This is achieved using flashback database, but the standby database does not need to have flashback database explicitly enabled to take advantage of this feature, thought it works just the same if it is.

stop the mrp process

SQL> alter database recover managed standby database cancel;

Database altered.

SQL> alter database convert to snapshot standby;

Database altered.

SQL> shut immediate;
ORA-01507: database not mounted
ORACLE instance shut down.

SQL> startup
ORACLE instance started.

Total System Global Area 422670336 bytes
Fixed Size 1300352 bytes
Variable Size 360712320 bytes
Database Buffers 54525952 bytes
Redo Buffers 6131712 bytes
Database mounted.
Database opened.

SQL> select flashback_on from V$database;

FLASHBACK_ON
------------------
RESTORE POINT ONLY

--- Do any transaction as per requirement.........

SQL> create user layana identified by fathima;

User created.

---
---

once the transactions are completed shut down the database and convert that to
physical standby database, once you shutdown the database all the transaction
will be lost.

SQL> shut immediate;
Database closed.
Database dismounted.
ORACLE instance shut down.

SQL> startup mount;
ORACLE instance started.

Total System Global Area 422670336 bytes
Fixed Size 1300352 bytes
Variable Size 360712320 bytes
Database Buffers 54525952 bytes
Redo Buffers 6131712 bytes
Database mounted.
SQL> alter database convert to physical standby;

Database altered.

--Once the above commands executes the database will be automatically dismounted and instance
will be in start state.

SQL> select status from V$instance;

STATUS
------------
STARTED

SQL> shut immediate;
ORA-01507: database not mounted


ORACLE instance shut down.
SQL> startup mount;
ORACLE instance started.

Total System Global Area 422670336 bytes
Fixed Size 1300352 bytes
Variable Size 360712320 bytes
Database Buffers 54525952 bytes
Redo Buffers 6131712 bytes
Database mounted.
SQL> alter database recover managed standby database disconnect from session;

Database altered.