22.3. Bancos de dados modelo #

O comando CREATE DATABASE realmente funciona copiando um banco de dados existente. Por padrão, copia o banco de dados padrão do sistema chamado template1. Assim, este banco de dados é o modelo a partir do qual os novos bancos de dados são criados. Se forem adicionados objetos ao banco de dados template1, estes objetos serão copiados para os bancos de dados do usuário criados posteriormente. Este comportamento permite modificações locais da instalação no conjunto padrão de objetos nos bancos de dados. Por exemplo, se for instalada a linguagem procedural PL/Perl no banco de dados template1, esta linguagem estará automaticamente disponível nos bancos de dados do usuário, sem que nenhuma ação extra precise ser executada quando estes bancos de dados forem criados.

Entretanto, o comando CREATE DATABASE não copia as permissões GRANT no nível de banco de dados associadas ao banco de dados de origem. O novo banco de dados possui as permissões padrão no nível de banco de dados.

Existe também um segundo banco de dados padrão do sistema chamado template0. Este banco de dados contém os mesmos dados do conteúdo inicial do banco de dados template1, ou seja, apenas os objetos padrão predefinidos pela versão corrente do PostgreSQL. O banco de dados template0 nunca deve ser alterado após a inicialização da instância. Ao instruir o comando CREATE DATABASE para copiar o banco de dados template0, em vez de copiar o banco de dados template1 pode-se criar um banco de dados de usuário prístino (aquele onde não existem objetos definidos pelo usuário, e onde os objetos do sistema não foram alterados), que não contém nenhuma das adições locais da instalação feitas no banco de dados template1. É particularmente útil ao recuperar uma cópia de segurança feita pelo pg_dump: o script da cópia de segurança deve ser recuperado em um banco de dados original, para garantir que o conteúdo correto do banco de dados salvo seja recriado, sem entrar em conflito com objetos que possam ter sido adicionados ao banco de dados template1 posteriormente.

Outro motivo comum para se copiar o banco de dados template0 em vez do banco de dados template1, é que podem ser especificadas novas configurações de codificação e localidade ao copiar o banco de dados template0, enquanto uma cópia do banco de dados template1 deve usar as mesmas configurações que ele usa. Isto ocorre porque o banco de dados template1 pode conter dados específicos de codificação ou localidade, enquanto o banco de dados template0 é conhecido por não os conter.

Para criar um banco de dados copiando o banco de dados template0, deve-se usar o comando

CREATE DATABASE nome_do_banco_de_dados TEMPLATE template0;

a partir do ambiente SQL, ou

createdb -T template0 nome_do_banco_de_dados

a partir do interpretador de comandos.

É possível criar bancos de dados modelo adicionais e, de fato, pode-se copiar qualquer banco de dados de uma instância especificando seu nome como modelo para o comando CREATE DATABASE. Porém, é importante notar que este comando não foi (ainda) planejado como uma ferramenta tipo COPY DATABASE de propósito geral. A principal limitação é que nenhuma outra sessão pode ser conectada ao banco de dados de origem enquanto ele está sendo copiado. O comando CREATE DATABASE irá falhar se qualquer outra conexão existir ao iniciar; durante a operação de cópia, são impedidas novas conexões com o banco de dados de origem.

Existem dois sinalizadores úteis para cada banco de dados no catálogo do sistema pg_database: as colunas datistemplate e datallowconn. A coluna datistemplate pode ser definida indicando que o banco de dados é um modelo para o comando CREATE DATABASE. Se este sinalizador estiver definido, o banco de dados pode ser clonado por qualquer usuário com o privilégio CREATEDB; se não estiver definido, apenas os superusuários e o dono do banco de dados poderão cloná-lo. Se a coluna dataallowconn for definida como falso, nenhuma nova conexão com este banco de dados será permitida (mas as sessões existentes não são terminadas simplesmente definindo este sinalizador como falso). O banco de dados template0 é normalmente marcado com dataallowconn = false, para impedir a sua modificação. Tanto template0 quanto template1 devem sempre ser marcados com datistemplate = true.

Nota

Os nomes template1 e template0 não possuem nenhum status especial, além do fato do nome template1 ser o nome do banco de dados de origem padrão para o comando CREATE DATABASE. Por exemplo, pode-se remover template1 e recriá-lo a partir de template0, sem nenhum efeito nocivo. Este tipo de ação pode ser aconselhável se for adicionado descuidadamente um monte de lixo no template1. (Para remover o banco de dados template1, ele deve estar com pg_database.datistemplate = false.)

Também é criado o banco de dados postgres quando a instância é inicializada. Este banco de dados é um banco de dados padrão para os usuários e aplicações se conectarem. É simplesmente uma cópia do banco de dados template1, podendo ser removido e recriado se necessário.