viernes, 28 de agosto de 2009

Dar todos los privilegios a un usuario sobre un ROL

Por qué ??????? POR QUE NO PUEDO DARLE TODOS LOS PRIVILEGIOS A UN USUARIO DE UNA ?????????

Esto es una pregunta que pasa todo el tiempo!!!!

Es muy comun tener un usuario "aplicacion" donde creo todos los objetos.. es decir es el schema owner (o dueño de esquema) y luego querer que otros usuarios, usuarios de verdad, se conecten y puedan acceder a todos los objetos del usuario "aplicacion" !!!!!

Entonces porque no puedo hacer GRANT ALL schema_name TO pepe!!!!!!!

bueno... no entiendo porque pero la forma de hacerlo es darle los privs de a uno.. aca va una forma "FACIL" de hacerlo:


FOR x IN (SELECT table_name FROM dba_tables WHERE owner=<>)
LOOP
EXECUTE IMMEDIATE 'GRANT SELECT ON <>.' x.table_name ' TO <>';
END LOOP;

Luego que le dimos todos los privs a un rol...le damos ese rol al usuario que geremos
grant rol_name to usuer_name

y por utlimo.. para que el usuario no tenga que poner el nombre del esquema antes de cada tabla.. le podemos decir que el current_schema del usuario es el del usuario "aplicacion" para eso hacemos un trigger que ejecute luego que se conecte.. el famoso after_logon:

CREATE OR REPLACE TRIGGER app_user.after_logon_trg
AFTER LOGON ON app_user.SCHEMA
BEGIN
EXECUTE IMMEDIATE 'ALTER SESSION SET current_schema=SCHEMA_OWNER';
END;
/


obviamente hay gente que sabe y de alli sale la info:

http://forums.oracle.com/forums/thread.jspa?threadID=936165
http://www.oracle-base.com/articles/misc/SchemaOwnersAndApplicationUsers.php

jueves, 20 de agosto de 2009

ver script de creacion de un objeto -- dbms_metadata

Muchas veces necesitamos saber saber como crear un objeto.

Tipicamente las vistas es un objeto que comunmente queremos saber como fue creado, para saber cual es la sentencia sql que ejecuta.


para saber la sentencia ddl que permite crear un objeto se puede consular el paquete
dbms_metadata
principalmente el metodo
get_ddl. Que recibe 3 parametros (en una de sus invocaciones)

1 - tipo de objeto, en los ejemplos se muestra para los objetos TABLE y VIEW
2 - El nombre del objeto, en el ejemplo, TABLA1 y P (nombre de la vista)
3- El esquma donde se encuentra el objeto , en el ejemplo , SCOOT Y USUARIO

ES IMPORTANTE QUE TODOS LOS NOMBRES TIENEN QUE ESTAR EN MAYUSCULAS YA QUE SON STRING Y ORACLE LOS GUARDA CON MAYUSCULAS.


como es un paquete no se puede ejecutar asi nomas, hay 2 formas basicas:
cargar el resultado en la tabla DUAL:

select dbms_metadata.get_ddl('TABLE','TABLA1','SCOTT') from dual;

O hacer un script que escriba en la consola:

begin
dbms_output.put_line(dbms_metadata.get_ddl('VIEW','P','USUARIO'));
end;
/


miércoles, 15 de julio de 2009

ORA-01031: insufficient privileges - al conectarse o al levantar (startup) la Base

el error ORA-01031: insufficient privileges puede darse en 2 circunstancias principalmente,

Una, cuando queremos crear/consultar, etc un objeto, en ese caso deberemos darle permisos de para crear/consultar, etc. A través de la sentencias GRANT …..

Pero también nos puede dar problemas al tratar de conectarse a la base o al tratar de levantarla. Si pasa eso es posiblemente porque el usuario no pertenezca al grupo ora_dba si estamos trabajando en Windows o dba si estamos en LINUX.

En Windows se soluciona de la siguiente manera:

c:> net localgroup ora_dba JuanPerez /add

lunes, 22 de junio de 2009

¿Cuando fue la ultima vez que se realizo una operación de ddl sobre una tabla?

Recordemos que una operación de DLL o Data DefinitionLanguage es aquella que modifica la estructura, es decir:

CREATE
ALTER
DROP

Para saber cual el la fecha de creacion o cuando fue la ultima vez que se realizo una operación DDL sobre una tabla se puede realizar la siguente consulta.

select OBJECT_NAME, CREATED, LAST_DDL_TIME from user_objects where object_type='TABLE'

jueves, 21 de mayo de 2009

A que tablespace pertenece una tabla ???

Algo muy util cuando queremos achicar o reducir el espacio de nuetros datafiles o tablespaces es saber en que tablespace estan creados nuestros objetos,
es decir:
Las tablas (x ejemplo) se crean en un tablespace, el cual si no se especifica al momento de la creación se crearan en el tablespace que tiene por defecto el usuario, como es no pasa muchas veces, es bueno poder ubicar nuestros objetos.

para ello esta SQL es fundamental.


select tablespace_name,
owner ,
segment_name objeto,
file_id,
block_id,
CEIL(blocks*4/1024) MBytes
from dba_extents where owner='DOSNEW'

PD: cambiar DOSNEW por el nombre del usuario/esquema

ORA-00054: recurso ocupado y obtenido con NOWAIT especificado

Oracle nos devulve "ORA-00054: recurso ocupado y obtenido con NOWAIT especificado" cuando por ejemplo queremos modificar la estrucutra de una tabla y alguien esta modificandola y no ha realizado commit.

Solucion, matar la session que tiene loqueada la tabla!!! ojo! el usuario perdera todas sus modificaciones!!

La consulta que hay que ejecutar para saber quien esta loqueando tablas para luego hacerle un kill es:


select object_name, o.object_id, sid, serial#, username, machine,osuser, program from user_objects o, v$locked_object l, v$session s
where o.object_id = l.object_id and l.session_id=s.sid

martes, 14 de abril de 2009

Clonar esquemas

Porque no se puede hacer clonar un schema o cliente de forma facil en oracle ???
no se.. nunca lo enternderé. estimado Juan Oracle.. algo así como clon user to user1 estaria formdiable!!!!

como eso no existe..tenemos que exportar y luego importar...pero no esta taaaannn fácil..
Veamos los detalle:

primero creamos un directorio, esto es porque con Oracle Data Pump es necesario crear el directorio de salida.

conectados com sys


create directory mydir as 'c:\dpdump';
grant read,write on directory mydir to pepe;

luego desde la linea de comando ejecutamos el expdp


expdp asanga/asa directory=mydir dumpfile=salidapepe.dmp schemas=pepe logfile=salidapepe.log

luego como sys (que es mas facil)
importamos el esquema en otro esquema a traves de la maravillosa palabra clava: remap_schemas

impdp directory=mydir dumpfile=salidapepe.dmp logfile=import2pepenew.log remap_schema=pepe:pepenew

mmmm....bueno no es taaannnn fácil si tenemos algunos detalles..Veamos:
si tenemos tipos creados por el objeto pepe necesitamos agregar
transform=oid:n:type en la sentencia del import

impdp directory=mydir dumpfile=salidapepe.dmp logfile=import2pepenew.log remap_schema=pepe:pepenew transform=oid:n:type

obviamente esta es la forma CHANCHA... ya que es como tener 2 tipos number en nuestra base...lo que deberiamos hacer es crear un esquema que solo tenga los tipos..y darle permisos al resto de los esquemas para que lo puedan utilizar.. pero tá..por ahora nos quedamos con la forma chancha !! :D

otra cosa a tener en cuenta es si el usuario tiene privilegios sobre todo si utilizamos STORE PROCEDURES que hacen uso de esos privilegios..
en ese caso.. antes de hacer el import...hay que CREAR EL USUARIO A MANO !!!!

create user pepenew identified by pepenew

Y DARLE LOS PRIVILEGIOS
para obtener los privilegios de pepe.. hay un montón de scripts en la vuelta... yo uso el del gran gurú y mentor pete finnigan que está muy bueno.

grant ...... to pepenew

y después ...solo después... hacemos el import.

y si... ....algo que tienen que ser....
clon user pepe pepenew
se transforma en un dolor de kbza!!! ponete las pilas Juan !!!



lunes, 13 de abril de 2009

Crear Tablas en un Store procedure PL/SQL - ORA-01031: insufficient privileges

Bueno... aquí hay un poblemita, que si bien es muy facil de solucionar es "raro" que luego de tantas versiones siga pasando.... :D

el tema es el siguiente.. Crear un tabla dentro de un Porcedimiento.
si ejecutamos CREATE TABLE pepe (....... desde linea de comando funciona perfectamente...pero si lo hacemos :

script_crear := 'CREATE TABLE PEPE (NUM NUMBER ,DATOS VARCHAR2(50))';
EXECUTE IMMEDIATE script_crear;

Nos devuleve el error:
ORA-01031: insufficient privileges

Solucion: Dar los permisos de forma directa, es decir.

grant create table to usuario.


Por que pasa esto?? bueno el "problemita" se da porque los ROLES no son tomados en los procedimientos PLSQL, es decir si tenemos un permiso obtenido a través de un ROL, este permiso no lo tendremos dentro de los procedimientos o funciones PL/SQL, mmmm bueno, en si... si lo ejecutamos en un bloque anonimo funcionaria pero.. más facil es darle el permiso de forma directa y problema solucionado.

Como siempre hay un buen link, con comentarios de gente que sabe :D

http://forums.oracle.com

miércoles, 1 de abril de 2009

ORA-02449 Cuando queremos borrar o truncar una tabla

ORA-02449: claves únicas/primarias en la tabla referidas por claves ajenas


Para saber cueles son FK que apuntan a mi tabla se puede ejecutar la siguiente consulta:


SELECT A.CONSTRAINT_NAME, A.TABLE_NAME, B.COLUMN_NAME,
B.COLUMN_NAME AS REFERENCED_COLUMN_NAME,
B.TABLE_NAME AS REFERENCED_TABLE_NAME
FROM USER_CONSTRAINTS A, USER_CONS_COLUMNS B
WHERE A.CONSTRAINT_TYPE = 'R' AND A.R_CONSTRAINT_NAME = B.CONSTRAINT_NAME AND B.TABLE_NAME = 'CUSTOMERS'

pd: cambiar 'CUSTOMERS' por el nombre de la tabla

martes, 31 de marzo de 2009

Reducir el tamaño de los datafiles

Antes que nada hablemos porque quicieramos reducir el tamaño, pueden pasar 2 cosas:
a) creamos el datafile de un tamaño que nunca vamos a llegar y por eso lo queremos reducir
b) lo creamos autoextend y por lo tanto cuando insertamos aumenta su tamaño, pero luego al borrar las filas o tablas .....NO RECUERA EL TAMAÑO !!!!

Para reducir el tamaño ORACLE proporciona el comando RESIZE, pero ya veremos que no es "muy inteligente".

Para saber cuanto espacio tenemos disponible y candidato a achicar se puede ejecutar la siguiente cosulta:

select dba_data_files.file_id, dba_data_files.file_name , sum(dba_free_space.bytes)/1024/1024 mega
from dba_free_space, dba_data_files
where dba_free_space.file_id = dba_data_files.file_id
group by dba_data_files.file_id, dba_data_files.file_nam
e

y por ejemplo da el siguiente resultado:

3 C:\ORACLE\ORADATA\ORCL\SYSAUX01.DBF 10
5 C:\ORACLE\ORADATA\ORCL\EXAMPLE01.DBF 20
1 C:\ORACLE\ORADATA\ORCL\SYSTEM01.DBF 6,01
2 C:\ORACLE\ORADATA\ORCL\UNDOTBS01.DBF 150.3
4 C:\ORACLE\ORADATA\ORCL\USERS01.DBF 100.7


Esta consulta devuleve el espacio libre que hay, por lo que como máximo podrías bajar 100 Mg. y monedas, del datafile users01.dbf

OJO!!!!
En REALIDAD, lo que te devuelve el tamaño libre a partir de todas las HWM (high water mark) de las tablas, es decir el tamaño máximo que tuvieron alguna vez.


Por ejemplo la tabla t tiene 10m de datos y 10mg de “huecos” el espacio libre se calcula como si la tabla tuviera 20m. se entiende?

En otras palabras, se podría bajar 100mg de tu datafile USERS01.DBF. si tener que lidiar con los huecos.

Bueno.. esto es util si NO TENEMOS HUECOS.... cosa que NUNCA PASA !!!!! la vida no puede ser tan sensilla :D

Entonces que hacemos:
Bueno.. existen 2 opciones:

a) el magico "SHRINK" que por desgracia solo aplica a tablas y tablespaces temporales. no a los de datos :(

b) mover los datos a un nuevo datafile y borrar el anterior.

veamos cada una de las opciones


Nota: Si tenes metalink y queres algo más de info, podes ver las siguientes notas de nuestros amigos de ORACLE:

Nota: 1029252.6 - How to Resize a Datafile
Nota: 130866.1 - How to Resolve ORA-03297 When Resizing a Datafile by Finding the Table Highwatermark
Nota: 237654.1 - Resizing a Datafile Returns Error ORA-03297