Poupe até 53% em Servidores VPS, escolha agora. Oferta limitada.

Passo a passo para transferir PostgreSQL entre servidores preservando encoding

16 min de leitura  ·  Guia técnico

Transferir PostgreSQL entre servidores preservando encoding é o processo de exportar um banco de dados com pg_dump e restaurá-lo em outro servidor garantindo que o charset, collation e locale permaneçam idênticos ao ambiente de origem. Para executar a migração com segurança, siga estes passos:

  1. Verifique o encoding, LC_COLLATE e LC_CTYPE do banco de origem com \l no psql.
  2. Exporte o banco com pg_dump -Fc no servidor de origem.
  3. Transfira o arquivo de dump para o servidor de destino via SCP ou rsync.
  4. Crie o banco de destino com os mesmos parâmetros de encoding e collation.
  5. Restaure o dump com pg_restore e verifique a integridade dos dados.
  6. Confirme o encoding no destino executando novamente \l no psql.

Pré-requisitos para migrar PostgreSQL preservando encoding

  • Acesso root ou sudo nos dois servidores (origem e destino).
  • PostgreSQL instalado no servidor de destino — versão 14, 15 ou 16 (compatível com o dump lógico da origem).
  • pg_dump e pg_restore disponíveis nos dois ambientes (pacote postgresql-client no Debian 12 ou AlmaLinux 9).
  • Espaço em disco suficiente para o arquivo de dump — verifique com df -h antes de iniciar.
  • Acesso SSH entre os servidores ou permissão para transferir arquivos via SCP/rsync.
  • Locale do sistema operacional de destino compatível com o encoding do banco (ex.: pt_BR.UTF-8 gerado no sistema).
  • Usuário PostgreSQL com permissão de leitura no banco de origem e permissão de criação de banco no destino.

Passo 1 — Verificar encoding e collation do banco de origem

Antes de qualquer exportação, é essencial registrar os parâmetros exatos de encoding do banco PostgreSQL de origem. Conecte-se ao servidor de origem como usuário postgres e acesse o psql:

sudo -u postgres psql

Dentro do psql, liste todos os bancos com seus encodings:

\l
                                  List of databases
   Name    |  Owner   | Encoding |   Collate   |    Ctype    |   Access privileges
-----------+----------+----------+-------------+-------------+-----------------------
 meu_banco | postgres | UTF8     | pt_BR.UTF-8 | pt_BR.UTF-8 |
 postgres  | postgres | UTF8     | en_US.UTF-8 | en_US.UTF-8 |

Anote os valores de Encoding, Collate e Ctype do banco que será migrado. Esses três parâmetros precisam ser replicados exatamente no servidor de destino. Para confirmar com uma query SQL mais precisa:

SELECT pg_encoding_to_char(encoding), datcollate, datctype
FROM pg_database
WHERE datname = 'meu_banco';
 pg_encoding_to_char | datcollate  |   datctype
---------------------+-------------+-------------
 UTF8                | pt_BR.UTF-8 | pt_BR.UTF-8

Passo 2 — Exportar o banco com pg_dump em formato custom

A exportação lógica com pg_dump é o método recomendado para migração de banco PostgreSQL entre servidores, pois gera um arquivo portável e compatível entre versões diferentes do PostgreSQL. Use o formato custom (-Fc) para habilitar compressão e restauração seletiva:

Atenção: o comando abaixo irá bloquear brevemente escritas no banco durante o dump em ambientes com alta concorrência. Prefira executar em janela de manutenção ou use a flag --snapshot se disponível.

sudo -u postgres pg_dump -Fc --no-owner --no-acl -d meu_banco -f /tmp/meu_banco.dump

Explicação das flags:

  • -Fc: formato custom comprimido, compatível com pg_restore.
  • --no-owner: remove instruções de ownership, evitando erros se o usuário de destino tiver nome diferente.
  • --no-acl: remove permissões de acesso específicas do ambiente de origem.
  • -d meu_banco: especifica o banco a ser exportado.
  • -f /tmp/meu_banco.dump: caminho do arquivo de saída.

Verifique o tamanho do arquivo gerado:

ls -lh /tmp/meu_banco.dump
-rw-r--r-- 1 postgres postgres 142M jan 15 10:23 /tmp/meu_banco.dump

Passo 3 — Transferir o dump para o servidor de destino

Com o arquivo de dump gerado, transfira-o com segurança para o servidor de destino usando SCP. Substitua usuario e IP_DESTINO pelos dados reais do seu ambiente:

scp /tmp/meu_banco.dump usuario@IP_DESTINO:/tmp/meu_banco.dump

Se preferir rsync para transferências maiores com suporte a retomada:

rsync -avz --progress /tmp/meu_banco.dump usuario@IP_DESTINO:/tmp/meu_banco.dump

Após a transferência, verifique a integridade do arquivo no destino comparando o checksum MD5:

md5sum /tmp/meu_banco.dump

Execute o mesmo comando no servidor de destino e confirme que os hashes são idênticos. Para mais detalhes sobre acesso remoto a servidores Linux, consulte o guia Acessando servidores VPS Linux da AviraHost.

Passo 4 — Preparar o ambiente de destino e criar o banco com encoding correto

No servidor de destino, antes de restaurar o dump, é necessário garantir que o locale do sistema operacional suporte o encoding desejado. Em AlmaLinux 9 ou Debian 12, verifique os locales disponíveis:

locale -a | grep pt_BR
pt_BR.utf8

Se o locale não estiver disponível, gere-o (Debian 12):

sudo locale-gen pt_BR.UTF-8
sudo update-locale

Em AlmaLinux 9 ou Rocky Linux 9:

sudo dnf install -y glibc-langpack-pt
sudo localectl set-locale LANG=pt_BR.UTF-8

Agora crie o banco de destino com os parâmetros exatos coletados no Passo 1. Conecte-se ao psql do servidor de destino:

sudo -u postgres psql

Atenção: o comando abaixo cria um banco novo. Se já existir um banco com o mesmo nome, exclua-o antes com DROP DATABASE meu_banco; — essa ação é irreversível.

CREATE DATABASE meu_banco
  ENCODING 'UTF8'
  LC_COLLATE 'pt_BR.UTF-8'
  LC_CTYPE 'pt_BR.UTF-8'
  TEMPLATE template0;
CREATE DATABASE

O uso de TEMPLATE template0 é obrigatório quando se especifica encoding ou collation diferente do padrão do cluster, pois o template0 não possui objetos que possam conflitar com as configurações de locale.

Passo 5 — Restaurar o dump com pg_restore

Com o banco de destino criado corretamente, execute a restauração usando pg_restore. O formato custom permite restauração paralela com a flag -j, acelerando o processo em bancos grandes:

sudo -u postgres pg_restore \
  --no-owner \
  --no-acl \
  -d meu_banco \
  -j 4 \
  -v \
  /tmp/meu_banco.dump

Explicação das flags adicionais:

  • -j 4: usa 4 workers paralelos para restauração (ajuste conforme os CPUs disponíveis).
  • -v: modo verbose, exibe cada objeto restaurado — útil para identificar erros.

Ao rodar este comando, você verá uma saída semelhante a:

pg_restore: creating TABLE "public.usuarios"
pg_restore: creating TABLE "public.pedidos"
pg_restore: creating INDEX "usuarios_email_idx"
pg_restore: creating CONSTRAINT "pedidos_pkey"
pg_restore: finished main parallel loop

Erros do tipo pg_restore: error: could not execute query devem ser analisados individualmente — muitos são avisos não críticos relacionados a extensões ou roles inexistentes no destino.

Passo 6 — Verificar encoding e integridade após a migração

Após a restauração, confirme que o encoding foi preservado corretamente. Conecte-se ao psql do servidor de destino e execute:

sudo -u postgres psql -d meu_banco
\l meu_banco
                                List of databases
   Name    |  Owner   | Encoding |   Collate   |    Ctype
-----------+----------+----------+-------------+-------------
 meu_banco | postgres | UTF8     | pt_BR.UTF-8 | pt_BR.UTF-8

Verifique também a contagem de registros nas tabelas principais para confirmar que os dados foram restaurados completamente:

SELECT schemaname, tablename, n_live_tup
FROM pg_stat_user_tables
ORDER BY n_live_tup DESC
LIMIT 10;

Compare os valores com os do banco de origem. Para verificar se caracteres especiais (acentos, cedilha) foram preservados, execute uma query de amostragem em uma tabela com dados textuais:

SELECT nome FROM usuarios LIMIT 5;
     nome
--------------
 João Silva
 Maria Ângela
 Luís Araújo

Se os caracteres aparecerem corretamente, a migração preservou o encoding UTF-8 com sucesso. Para referência sobre conexões remotas ao PostgreSQL, veja o artigo Conectando remotamente ao PostgreSQL - cPanel.

Migração entre versões diferentes do PostgreSQL (14 para 16)

A compatibilidade entre versões é um ponto crítico na migração de banco de dados PostgreSQL. O dump lógico gerado pelo pg_dump é compatível entre versões, mas existem cuidados específicos ao migrar do PostgreSQL 14 para o 16, por exemplo.

Sempre use o binário pg_dump da versão mais recente entre origem e destino para garantir compatibilidade máxima. No servidor de destino com PostgreSQL 16, você pode usar o pg_dump remoto diretamente:

sudo -u postgres pg_dump \
  -h IP_ORIGEM \
  -U postgres \
  -Fc \
  --no-owner \
  -d meu_banco \
  -f /tmp/meu_banco_v14.dump

Antes de restaurar em produção, verifique extensões instaladas na origem:

SELECT name, default_version, installed_version
FROM pg_available_extensions
WHERE installed_version IS NOT NULL;

Extensões como pg_trgm, uuid-ossp e postgis precisam estar instaladas no servidor de destino antes da restauração. Instale-as no banco de destino:

sudo -u postgres psql -d meu_banco -c "CREATE EXTENSION IF NOT EXISTS pg_trgm;"
sudo -u postgres psql -d meu_banco -c "CREATE EXTENSION IF NOT EXISTS \"uuid-ossp\";"

Funções e tipos de dados específicos de versão podem gerar erros durante o pg_restore. Sempre teste a restauração completa em um ambiente de homologação antes de executar em produção.

Problemas comuns e como resolver

Sintoma: pg_restore retorna "invalid encoding name" ou erros de collation

Causa: O banco de destino foi criado com encoding ou collation diferente do dump, ou o locale especificado não existe no sistema operacional de destino.
Solução: Exclua o banco de destino com DROP DATABASE meu_banco;, verifique os locales disponíveis com locale -a, gere o locale necessário e recrie o banco com os parâmetros corretos usando TEMPLATE template0. Execute o pg_restore novamente após recriar o banco.

Sintoma: Caracteres especiais aparecem como "?" ou símbolos estranhos após a migração

Causa: O cliente psql ou a aplicação está se conectando com um encoding diferente do banco. Isso ocorre quando a variável client_encoding não está configurada corretamente.
Solução: Defina explicitamente o encoding do cliente ao conectar: psql -d meu_banco --set=client_encoding=UTF8. Verifique também o parâmetro client_encoding no arquivo postgresql.conf e nas strings de conexão da aplicação. Execute SHOW client_encoding; dentro do psql para confirmar.

Sintoma: pg_dump falha com "permission denied" ao exportar

Causa: O usuário PostgreSQL utilizado não tem permissão de leitura em todos os schemas ou tabelas do banco de origem.
Solução: Use o usuário postgres (superusuário) para o dump: sudo -u postgres pg_dump .... Se precisar usar outro usuário, conceda as permissões necessárias: GRANT SELECT ON ALL TABLES IN SCHEMA public TO usuario_dump;

Sintoma: pg_restore muito lento em bancos grandes

Causa: A restauração está sendo executada em modo single-thread, sem paralelismo, e os índices estão sendo criados durante a restauração de cada tabela.
Solução: Use a flag -j com o número de CPUs disponíveis (ex.: -j 8). Considere também desabilitar temporariamente os índices e constraints antes da restauração e recriá-los ao final. Aumente o parâmetro maintenance_work_mem no PostgreSQL de destino para acelerar a criação de índices: SET maintenance_work_mem = '1GB';

Sintoma: Erro "role does not exist" durante pg_restore

Causa: O dump contém referências a roles (usuários) que existem na origem mas não foram criados no servidor de destino.
Solução: Use as flags --no-owner e --no-acl no pg_restore para ignorar ownership e permissões. Se os roles forem necessários, crie-os manualmente no destino antes da restauração ou use pg_dumpall para exportar também as definições de roles da origem.

Perguntas frequentes sobre transferência de PostgreSQL preservando encoding

Como preservar o encoding UTF-8 ao transferir um banco PostgreSQL entre servidores?

Ao criar o banco de destino, especifique explicitamente ENCODING 'UTF8', LC_COLLATE e LC_CTYPE correspondentes ao banco de origem. Use pg_dump com a flag --no-owner e pg_restore ou psql para restaurar. Verifique o encoding com \l no psql antes e depois da migração para confirmar que os parâmetros foram preservados corretamente.

Qual a diferença entre pg_dump e pg_dumpall para migração de PostgreSQL?

pg_dump exporta um único banco de dados, incluindo esquema e dados, e é ideal para migrações pontuais. pg_dumpall exporta todos os bancos, roles e configurações globais do cluster, sendo necessário quando você quer replicar o ambiente completo. Para preservar encoding de um banco específico, pg_dump com formato custom (-Fc) é a opção mais segura e flexível, pois permite restauração paralela e seletiva de objetos.

É possível migrar PostgreSQL entre versões diferentes (ex: 14 para 16) preservando os dados?

Sim, usando pg_dump na versão de origem e pg_restore na versão de destino. O formato lógico do pg_dump é compatível entre versões. Porém, verifique incompatibilidades de extensões e funções específicas de versão antes de restaurar. Sempre teste a restauração em ambiente de homologação antes de aplicar em produção para evitar surpresas com comportamentos diferentes entre versões.

Como verificar o encoding e collation de um banco PostgreSQL após a migração?

Conecte ao banco via psql e execute \l para listar todos os bancos com encoding, LC_COLLATE e LC_CTYPE. Para verificar de forma mais precisa, use SELECT pg_encoding_to_char(encoding), datcollate, datctype FROM pg_database WHERE datname = 'nome_do_banco';. Os valores retornados devem ser idênticos aos do banco de origem coletados antes da migração.

O que fazer se o pg_restore retornar erros de encoding durante a migração?

Erros de encoding geralmente ocorrem quando o banco de destino foi criado com collation diferente do dump. Exclua o banco de destino, recrie-o com os parâmetros corretos (ENCODING, LC_COLLATE, LC_CTYPE) usando TEMPLATE template0 e execute o pg_restore novamente. Certifique-se também de que o locale do sistema operacional de destino suporta o encoding desejado, gerando-o com locale-gen se necessário.

Conclusão

  • Documente os parâmetros de encoding antes de iniciar: registre Encoding, LC_COLLATE e LC_CTYPE do banco de origem com \l e guarde esses valores para replicar exatamente no destino.
  • Use pg_dump -Fc com --no-owner: o formato custom garante compressão, compatibilidade entre versões e restauração paralela, enquanto --no-owner evita erros de roles inexistentes no destino.
  • Sempre crie o banco de destino com TEMPLATE template0: é o único template que permite especificar encoding e collation customizados sem conflitos, sendo obrigatório para migrações que preservam charset específico.

Leia também

Precisa de ajuda com migração de PostgreSQL?

Migrar bancos de dados entre servidores exige atenção a detalhes que podem impactar a integridade dos dados em produção. Um servidor VPS com recursos dedicados e suporte técnico especializado pode facilitar esse processo, oferecendo ambiente controlado para testes e execução da migração com segurança.

Conheça os planos de VPS da AviraHost e migre seu PostgreSQL com tranquilidade

  • 0 Os usuários acharam isso útil
  • PostgreSQL, migração, banco-de-dados, pg_dump, Linux, AviraHost, servidor-dedicado
Esta resposta foi útil?

Artigos Relacionados

Otimizar cache Redis para aplicações PHP no Ubuntu 22.04

Para otimizar o cache Redis para aplicações PHP no Ubuntu 22.04, instale e configure o Redis,...

Configurar Alertas Automáticos com Zabbix no Ubuntu

Para configurar alertas automáticos com Zabbix no Ubuntu, instale o Zabbix Server, configure...

Otimizar MySQL: como reduzir uso de memória e acelerar consultas

Otimizar MySQL é o processo de ajustar configurações e consultas para reduzir o consumo de...

Entenda o que é Swap no Linux: como funciona e quando usar

Swap no Linux é um espaço em disco usado como extensão da memória RAM quando esta se esgota. O...

Guia Definitivo: Configurar Nginx como Proxy Reverso

Para configurar o Nginx como proxy reverso, instale o Nginx, crie um arquivo de configuração de...