Recebi a tarefa de migrar um banco de dados PostgreSQL 8.2.x para outro servidor. Para fazer isso estou usando o pgAdmin 1.12.2 (no Ubuntu 11.04 a propósito) e usando o Backup and Restore usando o formato custom/compress (.backup) e codificação UTF8.
O banco de dados original está em UTF8, assim:
-- Database: favela
-- DROP DATABASE favela;
CREATE DATABASE favela
WITH OWNER = favela
ENCODING = 'UTF8'
TABLESPACE = favela
CONNECTION LIMIT = -1;
Estou criando esse banco de dados exatamente assim no servidor de destino. Mas quando restauro o banco de dados do arquivo .backup usando a opção Restaurar, ele me apresenta alguns destes erros:
pg_restore: restoring data for table "arena"
pg_restore: [archiver (db)] Error while PROCESSING TOC:
pg_restore: [archiver (db)] Error from TOC entry 2173; 0 35500 TABLE DATA arena favela
pg_restore: [archiver (db)] COPY failed: ERROR: invalid byte sequence for encoding "UTF8": 0xe3a709
HINT: This error can also happen if the byte sequence does not match the encoding expected by the server, which is controlled by "client_encoding".
CONTEXT: COPY arena, line 62
Quando eu verifico qual registro acionou este erro de fato alguns campos vartext possuem caracteres diacríticos como ç (usado em português, por exemplo, "caça"), e quando eu os removo manualmente do texto nos registros o erro passa para o próximo registro que os possui - pois quando o copy apresenta um erro ele para de inserir dados nesta tabela. E eu não quero substituí-los manualmente um por um para conseguir isso.
Mas é meio estranho porque com UTF8 não deveria haver esse tipo de problema, certo?
Eu não sei como eles chegaram lá em primeiro lugar. Estou apenas migrando o banco de dados e suponho que de alguma forma o banco de dados estava como em LATIN1 e depois foi alterado indevidamente para UTF8.
Existe alguma maneira de verificar se uma tabela/banco de dados possui sequências UTF8 inválidas? Ou alguma maneira de impor/reconverter esses caracteres no UFT8 para não ter problemas ao executar a restauração?
Desde já, obrigado.
Pesquisando na internet, vi que esse é um problema bastante comum. A solução comum é usar o dump de formato de texto simples e alimentá-lo através do iconv para corrigir a codificação.
Aqui estão mais informações sobre isso.
Poderia ter acontecido conforme descrito aqui - embora isso gere um erro no 8.4:
Há um bom post neste excelente blog sobre os problemas gerais e algumas maneiras de lidar com eles
Eu não recomendo executar iconv cegamente no dump de texto simples porque ele pode converter caracteres válidos (por exemplo: caracteres chineses ) para alguns outros caracteres. É melhor encontrar o caractere UTF8 inválido executando o comando abaixo.
e, em seguida, execute iconv nos dados específicos. Verifique este documento para uma explicação detalhada passo a passo .
Provavelmente com a codificação padrão usada em seu ambiente Unix/Linux. Para verificar qual codificação é atualmente a padrão, execute o seguinte:
Nesse caso, podemos ver claramente que não é uma codificação UTF-8, aquela na qual o comando de cópia depende.
Então, para corrigir isso, apenas definimos a variável LANG no exemplo para o seguinte:
Observação: isso só estará disponível para a sessão atual. Adicione-o a ~/.bashrc ou similar para tê-lo disponível na inicialização de qualquer sessão de shell futura.
Referência
Referenciei o seguinte link que me deu pistas para determinar a codificação de origem e depois convertê-la na codificação UTF-8 desejada. Verifique e altere a codificação do Linux