Criei alguns novos usuários no Oracle. No entanto, ao executar o sqlplus, todos precisam qualificar totalmente os nomes das tabelas na consulta. Qual é a melhor maneira de definir um esquema padrão para esses novos usuários?
Não há nada como o PostgreSQL set search_path
no Oracle.
A coisa mais próxima que consigo pensar seria um gatilho de logon para o usuário que executa uma ALTER SESSION SET CURRENT_SCHEMA ...
CREATE OR REPLACE TRIGGER LOGON_TRG
AFTER LOGON ON SCHEMA
BEGIN
EXECUTE IMMEDIATE 'ALTER SESSION SET CURRENT_SCHEMA = foobar';
EXCEPTION
when others
then null; -- prevent a login failure due to an exception
END;
/
Se a lista de usuários não for muito longa, você poderá criar um gatilho de logon no banco de dados para não precisar criar esse gatilho para cada usuário:
CREATE OR REPLACE TRIGGER LOGON_TRG
AFTER LOGON ON DATABASE
BEGIN
if (user in ('TOM', 'DICK', 'HARRY')) then
EXECUTE IMMEDIATE 'ALTER SESSION SET CURRENT_SCHEMA = foobar';
end if;
exception
when others
then null; -- prevent a login failure due to an exception
END logon_trg;
/
Obviamente, a lista de usuários em que você deseja alterar o esquema padrão também pode ser obtida de uma tabela. Nesse caso, você só precisa inserir ou excluir linhas de lá para "ativar" esse recurso (em vez de recriar o gatilho toda vez).
Outra opção seria criar sinônimos sempre que você criar um usuário que aponte para as tabelas reais. Você pode automatizar isso usando um procedimento armazenado que percorre todas as tabelas em um esquema e cria os sinônimos para eles no outro esquema.
A menos que todos os usuários do Oracle trabalhem nas mesmas tabelas, eu não recomendaria o uso de sinônimos públicos que você precisaria criar apenas uma vez - eles podem causar muitos problemas se existirem diferentes usuários de aplicativos em sua instalação.
Editar :
Seguindo a sugestão de Alex, aqui está um gatilho de logon que verifica a função em vez de um nome de usuário:
CREATE OR REPLACE TRIGGER LOGON_TRG
AFTER LOGON ON DATABASE
declare
has_role boolean;
BEGIN
has_role := dbms_session.is_role_enabled('FOOBAR_ROLE');
if (has_role) then
EXECUTE IMMEDIATE 'ALTER SESSION SET CURRENT_SCHEMA = foobar';
end if;
exception
when others
then null; -- prevent a login failure due to an exception
END logon_trg;
/
when others then null;
é um exemplo, complicará a solução de problemas, pois torna qualquer erro invisível. Talvez remova completamente a manipulação de exceções ou registre o erro no servidor em uma transação AUTÔNOMO e depois a RAISE novamente .Eu não acho que existe uma maneira de definir um. O usuário é o esquema. AFAIK, você pode definir apenas o espaço de tabela padrão.
fonte