ORA-01031: insufficient privileges
Got the ORA error when I try to run a procedure.
There is create table SQL in the procedure.
This needs to be granted the privileges explicitly.
Just because The Roles are disabled inside stored procedures. For example, if the CREATE TABLE privilege is granted to you via a role, and you use the DBMS_SQL package to create a table, you will receive the Oracle error 'ORA-01031: insufficient privileges'.
The solution is to grant the required privileges to the owner of the subprogram.
The reason for this is, unlike other Oracle supplied packages, the dbms_sql package, when used inside a stored subprogram, executes with the privileges of the owner of the subprogram, and not with the privileges of the caller.
Oracle 8i introduces invoker-rights for named PL/SQL. Therefore, roles are enabled for procedures created with AUTHID CURRENT_USER (i.e. Oracle supplied packages DBMS_SQL and DBMS_SYS_SQL). Thus, in Oracle 8i, the required privilege(s) can either be granted directly to the user or to the user via a role, including PUBLIC. Since Oracle supplied packages (i.e. DBMS_SQL and DBMS_SYS_SQL) are created with invoker-rights in 8i,roles can be granted the associated privileges.
EG:
I output the SQL embeded in the procedure.
SQL> exec PROC_AM_MIG('ipaddress_type','ipaddress','ipaddress_type_id','ipaddress_type_id','ipaddress_id','sp_id','ipaddress_type')
CREATE TABLE ipaddress_type_temp as select * from (select
ipaddress_type_id,ipaddress_type, dense_rank() over ( partition by
ipaddress_type order by sp_id) as rank from ipaddress_type ) where rank = 1
CREATE TABLE ipaddress_temp as (select a.*,c.ipaddress_type_id
ipaddress_type_id_temp from ipaddress a inner join ipaddress_type b on
a.ipaddress_type_id=b.ipaddress_type_id inner join ipaddress_type_temp c on
c.ipaddress_type=b.ipaddress_type)
alter table ipaddress_temp set unused (ipaddress_type_id)
alter table ipaddress_temp rename column ipaddress_type_id_temp to
ipaddress_type_id
RENAME ipaddress_type TO ipaddress_type_bak
RENAME ipaddress_type_temp TO ipaddress_type
RENAME ipaddress TO ipaddress_bak
RENAME ipaddress_temp TO ipaddress
ALTER TABLE ipaddress_type ADD PRIMARY KEY (ipaddress_type_id)
ALTER TABLE ipaddress ADD FOREIGN KEY (ipaddress_type_id) REFERENCES
ipaddress_type (ipaddress_type_id )
ORA-01031: insufficient privileges
PL/SQL procedure successfully completed.
Thre is no change in the tables.
SQL> select * from ipaddress;
IPADDRESS_ID NAME IPADDRESS_TYPE_ID
------------ ---------- -----------------
1 a 1
2 b 2
3 v 3
4 n 1
SQL> select * from ipaddress_type;
IPADDRESS_TYPE_ID IPADDRESS_ SP_ID
----------------- ---------- ----------
1 typeA 1
2 typeB 2
3 typeA 3
SQL> grant create any table to public;
Grant succeeded.
SQL> exec PROC_AM_MIG('ipaddress_type','ipaddress','ipaddress_type_id','ipaddress_type_id','ipaddress_id','sp_id','ipaddress_type')
CREATE TABLE ipaddress_type_temp as select * from (select
ipaddress_type_id,ipaddress_type, dense_rank() over ( partition by
ipaddress_type order by sp_id) as rank from ipaddress_type ) where rank = 1
CREATE TABLE ipaddress_temp as (select a.*,c.ipaddress_type_id
ipaddress_type_id_temp from ipaddress a inner join ipaddress_type b on
a.ipaddress_type_id=b.ipaddress_type_id inner join ipaddress_type_temp c on
c.ipaddress_type=b.ipaddress_type)
alter table ipaddress_temp set unused (ipaddress_type_id)
alter table ipaddress_temp rename column ipaddress_type_id_temp to
ipaddress_type_id
RENAME ipaddress_type TO ipaddress_type_bak
RENAME ipaddress_type_temp TO ipaddress_type
RENAME ipaddress TO ipaddress_bak
RENAME ipaddress_temp TO ipaddress
ALTER TABLE ipaddress_type ADD PRIMARY KEY (ipaddress_type_id)
ALTER TABLE ipaddress ADD FOREIGN KEY (ipaddress_type_id) REFERENCES
ipaddress_type (ipaddress_type_id )
PL/SQL procedure successfully completed.
SQL> select * from ipaddress;
IPADDRESS_ID NAME IPADDRESS_TYPE_ID
------------ ---------- -----------------
4 n 1
3 v 1
1 a 1
2 b 2
SQL> select * from ipaddress_type;
IPADDRESS_TYPE_ID IPADDRESS_ RANK
----------------- ---------- ----------
1 typeA 1
2 typeB 1