5.8. Esquemas

PostgreSQL 14.5: Esquemas

Um agrupamento de bancos de dados do PostgreSQL contém um ou mais bancos de dados com nome. Os usuários e os grupos de usuários são compartilhados por todo o agrupamento, mas nenhum outro dado é compartilhado entre os bancos de dados. Todas as conexões dos clientes com o servidor podem acessar somente os dados de um único banco de dados, àquele que foi especificado no pedido de conexão.

Nota: Os usuários de um agrupamento de bancos de dados não possuem, necessariamente, o privilégio de acessar todos os bancos de dados do agrupamento. O compartilhamento de nomes de usuários significa que não pode haver, em dois bancos de dados do mesmo agrupamento, mais de um usuário com o mesmo nome como, por exemplo, joel; mas o sistema pode ser configurado para permitir que o usuário joel acesse apenas determinados bancos de dados.

Um banco de dados contém um ou mais esquemas com nome, os quais por sua vez contêm tabelas. Os esquemas também contêm outros tipos de objetos com nome, incluindo tipos de dado, funções e operadores. O mesmo nome de objeto pode ser utilizado em esquemas diferentes sem conflito; por exemplo, tanto o esquema_1 quanto o meu_esquema podem conter uma tabela chamada minha_tabela. Diferentemente dos bancos de dados, os esquemas não são separados rigidamente: um usuário pode acessar objetos de vários esquemas no banco de dados em que está conectado, caso possua os privilégios necessários para fazê-lo.

Existem diversas razões pelas quais pode-se desejar utilizar esquemas:

Os esquemas são análogos a diretórios no nível do sistema operacional, exceto que os esquemas não podem ser aninhados.

5.8.1. Criação de esquema

Para criar um esquema utiliza-se o comando CREATE SCHEMA. O nome do esquema é escolhido livremente pelo usuário. Por exemplo:

CREATE SCHEMA meu_esquema;

Para criar ou acessar objetos em um esquema deve ser escrito um nome qualificado, formado pelo nome do esquema e pelo nome da tabela separados por um ponto:

nome_do_esquema.nome_da_tabela

Esta forma funciona em qualquer local onde é esperado o nome de uma tabela, inclusive nos comandos de modificação de tabela e nos comandos de acesso a dado mostrados nos próximos capítulos (Para abreviar falaremos apenas das tabelas, mas a mesma idéia se aplica a outros tipos de objetos com nome, tais como tipos e funções).

Na verdade, também pode ser utilizada a sintaxe mais geral

nome_do_banco_de_dados.nome_do_esquema.nome_da_tabela

mas atualmente esta sintaxe é apenas uma simples formalidade para manter a conformidade com o padrão SQL; se for escrito o nome do banco de dados, este deverá ser idêntico ao nome do banco de dados que se está conectado.

Portanto, para criar uma tabela no novo esquema utiliza-se:

CREATE TABLE meu_esquema.minha_tabela (
 ...
);

Para remover um esquema vazio (todos os seus objetos já foram removidos), utiliza-se:

DROP SCHEMA meu_esquema;

Para remover um esquema junto com todos os objetos que este contém, utiliza-se:

DROP SCHEMA meu_esquema CASCADE;

Consulte a Seção 5.10 para ver a descrição do mecanismo geral por trás desta operação.

Muitas vezes deseja-se criar um esquema cujo dono é outro usuário (porque este é um dos modos utilizados para restringir as atividades dos usuários a espaços de nomes bem definidos). A sintaxe para esta operação é:

CREATE SCHEMA nome_do_esquema AUTHORIZATION nome_do_usuário;

Inclusive, o nome do esquema pode ser omitido e, neste caso, o nome do esquema será idêntico ao nome do usuário. Consulte a Seção 5.8.6 para ver como pode ser útil.

Os nomes de esquemas começando por pg_ são reservados para uso pelo sistema, não devendo ser criados pelos usuários.

5.8.2. O esquema público

Nas seções anteriores foram criadas tabelas sem que fosse especificado nenhum nome de esquema. Por padrão, estas tabelas (e outros objetos) são colocadas automaticamente no esquema chamado "public". Todo banco de dados novo possui este esquema. Portanto, as duas formas abaixo são equivalentes:

CREATE TABLE produtos ( ... );

e

CREATE TABLE public.produtos ( ... );

5.8.3. O caminho de procura do esquema

Os nomes qualificados são desagradáveis de escrever, sendo geralmente melhor não ligar o aplicativo a um esquema específico. Por isso, geralmente as tabelas são referenciadas por meio de nomes não qualificados, formados apenas pelo nome da tabela. O sistema determina qual tabela está sendo referenciada seguindo o caminho de procura, o qual é uma lista de esquemas para procura. A primeira tabela correspondente encontrada no caminho de procura é assumida como sendo a desejada. Não havendo nenhuma correspondência no caminho de procura é relatado um erro, mesmo que uma tabela correspondendo ao nome exista em outro esquema no banco de dados.

O primeiro nome de esquema no caminho de procura é chamado de esquema corrente. Além de ser o primeiro esquema a ser procurado, também é o esquema onde as novas tabelas são criadas quando o comando CREATE TABLE não especifica o nome do esquema.

Para mostrar o caminho de procura corrente, utiliza-se:

SHOW search_path;

Na configuração padrão este comando retorna:

 search_path
--------------
 $user,public

O primeiro elemento especifica que deve ser procurado o esquema com o mesmo nome do usuário corrente. Se este esquema não existir, esta entrada será ignorada. O segundo elemento se refere ao esquema público visto anteriormente.

O primeiro esquema existente do caminho de procura é o local padrão para a criação dos novos objetos. Esta é a razão pela qual, por padrão, os objetos são criados no esquema público. Quando os objetos são referenciados em qualquer outro contexto sem qualificação pelo esquema (comandos de modificação de tabelas, modificação de dados ou consultas) o caminho de procura é percorrido até que o objeto correspondente seja encontrado. Portanto, na configuração padrão, qualquer acesso não qualificado somente pode fazer referência ao esquema público.

Para incluir um novo esquema no caminho, utiliza-se:

SET search_path TO meu_esquema,public;

(O esquema $user foi omitido, porque não há necessidade imediata dele). Dessa forma, a tabela pode ser acessada sem ser qualificada pelo esquema:

DROP TABLE minha_tabela;

Também, como meu_esquema é o primeiro elemento do caminho, os novos objetos serão criados neste esquema por padrão.

Também poderia ter sido escrito

SET search_path TO meu_esquema;

para retirar o acesso ao esquema público sem uma qualificação explícita. Não existe nada especial com relação ao esquema público, a não ser que existe por padrão. Também pode ser excluído.

Consulte também a Seção 9.19 para conhecer outras formas de manipular o caminho de procura de esquema.

O caminho de procura funciona para nomes de tipos de dado, nomes de funções e nomes de operadores, da mesma maneira que funciona para nomes de tabelas. Os nomes dos tipos de dado e das funções podem ser qualificados exatamente da mesma maneira que os nomes das tabelas. Se for necessário escrever um nome de operador qualificado em uma expressão, existe uma maneira especial de fazê-lo, deve ser escrito:

OPERATOR(nome_do_esquema.nome_do_operador)

Isto é necessário para evitar uma ambigüidade de sintaxe. Por exemplo:

SELECT 3 OPERATOR(pg_catalog.+) 4;

Na prática geralmente confia-se no caminho de procura para os operadores, não sendo necessário escrever algo tão horrível assim.

5.8.4. Esquemas e privilégios

Por padrão, os usuários não podem acessar objetos em esquemas que não são seus. Para poderem acessar, o dono do esquema precisa conceder o privilégio USAGE para o esquema. Para permitir os usuários utilizarem os objetos do esquema é necessário conceder privilégios adicionais, conforme seja apropriado para cada objeto.

Pode ser permitido, também, que um usuário crie objetos no esquema de outro usuário. Para permitir que isto seja feito, deve ser concedido o privilégio CREATE para o esquema. Deve ser observado que, por padrão, todos os usuários possuem o privilégio CREATE e USAGE para o esquema public. Isto permite a todos os usuários que podem se conectar ao banco de dados criar objetos no esquema public. Se isto não for desejado, este privilégio poderá ser revogado:

REVOKE CREATE ON SCHEMA public FROM PUBLIC;

O primeiro "public" no comando acima é o nome do esquema, enquanto o segundo "public" significa "todos os usuários". Na primeira ocorrência é um identificador, enquanto na segunda ocorrência é uma palavra chave; por isso, na primeira vez está escrito em minúsculas enquanto na segunda vez está em maiúsculas; lembre-se da convenção da Seção 4.1.1.

5.8.5. O esquema do catálogo do sistema

Além do esquema public e dos esquemas criados pelos usuários, cada banco de dados contém o esquema pg_catalog, contendo as tabelas do sistema e todos os tipos de dado, funções e operadores nativos. O pg_catalog é sempre parte efetiva do caminho de procura. Se não for colocado explicitamente no caminho de procura, então será procurado implicitamente antes dos esquemas do caminho de procura. Isto garante que os nomes nativos sempre podem ser encontrados. Entretanto, é possível colocar explicitamente o pg_catalog no final do caminho de procura, se for desejado que os nomes definidos pelo usuário substituam os nomes nativos.

Nas versões do PostgreSQL anteriores a 7.3, os nomes de tabela começando por pg_ eram reservados. Isto não é mais verdade: podem ser criadas tabelas com este nome, se for desejado, em qualquer esquema que não seja o do sistema. Entretanto, é melhor continuar evitando estes nomes, para garantir que não haverá conflito caso alguma versão futura defina uma tabela do sistema com o mesmo nome da tabela criada (com o caminho de procura padrão, uma referência não qualificada à tabela criada será resolvida com a tabela do sistema). As tabelas do sistema vão continuar seguindo a convenção de possuir nomes começando por pg_, não conflitando com os nomes não qualificados das tabelas dos usuários, desde que os usuários evitem utilizar o prefixo pg_.

5.8.6. Modelos de utilização

Os esquemas podem ser utilizados para organizar os dados de várias maneiras. Existem uns poucos modelos de utilização recomendados, facilmente suportados pela configuração padrão:

5.8.7. Portabilidade

No padrão SQL, não existe a noção de objetos no mesmo esquema pertencendo a usuários diferentes. Além disso, algumas implementações não permitem criar esquemas com nome diferente do nome de seu dono. Na verdade, os conceitos de esquema e de usuário são praticamente equivalentes em sistemas de banco de dados que implementam somente o suporte básico a esquemas especificado no padrão. Portanto, muitos usuários consideram os nomes qualificados na verdade formados por nome_do_usuário.nome_da_tabela. Esta é a forma como o PostgreSQL se comportará efetivamente, se for criado um esquema por usuário para todos os usuários.

Além disso, não existe o conceito do esquema public no padrão SQL. Para máxima conformidade com o padrão, o esquema public não deve ser utilizado (talvez deva até ser removido).

Obviamente, alguns sistemas de banco de dados SQL podem não implementar esquemas de nenhuma maneira, ou oferecer suporte a espaços de nomes permitindo apenas acesso entre bancos de dados (possivelmente limitado). Se for necessário trabalhar com estes sistemas, será obtido o máximo de portabilidade não utilizando nada relacionado a esquemas. [1] [2] [3] [4]

5.8.8. Exemplos

Nota: Seção escrita pelo tradutor, não fazendo parte do manual original.

Exemplo 5-5. Informações sobre esquema

Este exemplo mostra a utilização do comando \dn do psql e das funções current_schema() e current_schemas() para obter informações sobre esquema.

=>  \dn

       Lista de esquemas
        Nome        |   Dono
--------------------+----------
 information_schema | postgres
 pg_catalog         | postgres
 pg_toast           | postgres
 public             | postgres
(4 linhas)

=>  \df current_schema*

                                    Lista de funções
   Esquema  |      Nome       | Tipo de dado do resultado | Tipo de dado dos argumentos
------------+-----------------+---------------------------+-----------------------------
 pg_catalog | current_schema  | name                      |
 pg_catalog | current_schemas | name[]                    | boolean
(2 linhas)

=>  SELECT current_schema();

 current_schema
----------------
 public
(1 linha)

=>  SELECT current_schemas(true);

   current_schemas
---------------------
 {pg_catalog,public}
(1 linha)

=>  SELECT current_schemas(false);

 current_schemas
-----------------
 {public}
(1 linha)

Notas

[1]

OracleEsquema é uma coleção de objetos de banco de dados. O esquema pertence ao usuário do banco de dados e possui o mesmo nome do usuário. Os objetos do esquema são estruturas lógicas que fazem referência direta aos dados do banco de dados. Os objetos do esquema incluem estruturas como tabelas, visões e índices (Não existe relacionamento entre espaço de tabelas e esquema; objetos do mesmo esquema podem estar em espaços de tabelas diferentes, e espaços de tabelas podem conter objetos de esquemas diferentes). Oracle® Database Concepts 10g Release 1 (10.1) Part Number B10743-01 (N. do T.)

[2]

SQL Server — O comportamento dos esquemas mudou no SQL Server 2005. Os esquemas não são mais equivalentes a usuários do banco de dados; agora cada esquema é um espaço de nomes distinto que existe independentemente do usuário de banco de dados que o criou. Em outras palavras, o esquema é simplesmente um recipiente (container) de objetos. O esquema pode pertencer a qualquer usuário, e sua posse é transferível. É utilizado um esquema padrão para resolver os nomes dos securables referenciados sem o nome inteiramente qualificado. No SQL Server 2000, a resolução de nomes verifica primeiro o esquema pertencente ao usuário de banco de dados que está fazendo a chamada, seguida do esquema pertencente ao dbo. No SQL Server 2005, cada usuário possui um esquema padrão. O esquema padrão pode ser definido e alterado utilizando a opção DEFAULT_SCHEMA dos comandos CREATE USER e ALTER USER. Se DEFAULT_SCHEMA for deixado sem definição, o usuário do banco de dados terá dbo como seu esquema padrão. SQL Server 2005 Books Online — User-Schema Separation (N. do T.)

[3]

SQL Server — A menos que seja especificada outra maneira, todas as referências Transact-SQL ao nome de um objeto de banco de dados podem ser um nome de quatro partes com a seguinte forma:

      nome_do_servidor.[nome_do_banco_de_dados].[nome_do_esquema].nome_do_objeto
      | nome_do_banco_de_dados.[nome_do_esquema].nome_do_objeto
      | nome_do_esquema.nome_do_objeto
      | nome_do_objeto
     

SQL Server 2005 Books Online — Transact-SQL Syntax Conventions (N. do T.)

[4]

DB2Esquema é uma coleção de objetos com nome; fornece uma maneira de agrupar os objetos logicamente. Esquema também é um qualificador de nomes; fornece uma maneira de utilizar o mesmo nome natural para vários objetos, e de evitar referências ambíguas a estes objetos; por exemplo, os nomes de esquema 'INTERNA' e 'EXTERNA' fazem com que seja fácil distinguir duas tabelas VENDAS diferentes (INTERNA.VENDAS, EXTERNA.VENDAS). Os esquemas também permitem que vários aplicativos armazenem dados no mesmo banco de dados, sem ocorrência de colisões no espaço de nomes. DB2 Version 9 for Linux, UNIX, and Windows (N. do T.)

SourceForge.net Logo CSS válido!