Guia de Recuperação para InterBase e Firebird
NOTICE: Este documento é o capítulo do livro “The InterBase World” que foi escrito por Alexey Kovyazin e Serg Vostrikov.
O capítulo do livro “The InterBase World” dedicado à reparação de bancos de dados.
1. A história deste guia
O livro russo “The InterBase World” foi publicado em setembro de 2002.
Sua tiragem foi de 3000 cópias. Após 3 meses, esgotou-se e a segunda edição melhorada foi publicada em abril de 2003 com tiragem de 5000 cópias.
Agora está no topo das maiores livrarias online russas e pretendemos que se esgote muito em breve.
Os autores do livro são Alexey Kovyazin, desenvolvedor do IBSurgeon e
conhecido especialista russo em InterBase, e Serg Vostrikov, CEO da Devrace
empresa www.devrace.com
É uma coisa engraçada, nem um único livro dedicado ao InterBase foi publicado em inglês!
Milhares e milhares de desenvolvedores usam InterBase e Firebird, discutem o
assunto em várias conferências (dê uma olhada aqui: Links).
A comunidade de desenvolvedores InterBase tem em média dezenas de milhares de
pessoas. A forte demanda pelos livros sobre InterBase em vários países prova que a comunidade InterBase é realmente grande.
Podemos apostar uma caixa de cerveja no fato de que a edição de 10000 cópias será varrida da Amazon.com em um mês. Mas as pessoas nas empresas editoras
“sabem de tudo” e têm certeza de que ninguém compra um livro sobre InterBase. É uma pena real.
Aqui gostaríamos de oferecer a você o rascunho de um capítulo deste livro dedicado à recuperação de bancos de dados InterBase/Firebird.
2. Como recuperar banco de dados InterBase/Firebird
2.1. Revisão das principais causas de corrupção de banco de dados
Infelizmente, sempre há uma probabilidade de que qualquer armazenamento de informações seja
corrompido e algumas informações dele sejam perdidas. O banco de dados não é uma exceção a esta regra. Neste capítulo, consideraremos as principais causas que levam à corrupção do banco de dados InterBase, alguns métodos de reparação de bancos de dados e extração de informações deles. Também conheceremos as recomendações e precauções que minimizarão a probabilidade de perda de informações do banco de dados.
Primeiro de tudo, se falamos sobre reparação de banco de dados, devemos esclarecer uma noção de “corrupção de banco de dados”. Um banco de dados é geralmente chamado de danificado se ao tentar extrair ou modificar algumas informações aparecem erros e/ou as informações extraídas se revelam perdidas, incompletas ou não corretas. Há casos em que as corrupções de banco de dados estão ocultas e são encontradas apenas por testes com ferramentas especiais, mas também há corrupções reais de banco de dados quando é impossível conectar-se ao banco de dados, quando programas-clientes ajustados mostram erros estranhos (quando nenhuma manipulação foi executada com o banco de dados), ou quando é impossível restaurar o banco de dados a partir de uma cópia de backup.
2.2. As principais causas de corrupção de banco de dados são:
- Término anormal do computador servidor, especialmente interrupção de energia elétrica. Para a indústria de TI, isso é um verdadeiro flagelo e, por isso, esperamos que não haja necessidade de lembrá-lo mais uma vez sobre a necessidade de ter uma fonte de alimentação ininterrupta no servidor.
- Defeitos e falhas do computador servidor, especialmente HDD (disco rígido), controladores de disco, memória principal do computador e memória cache dos controladores Raid.
- String de conexão incorreta com um banco de dados multi-cliente de um ou mais usuários (em versões anteriores a 6.x). Ao conectar via TCP/IP, o caminho para o banco de dados deve apontar nome do servidor: unidade:/caminho/nomedobanco /para servidores na plataforma UNIX nomedoservidor: /caminho/nomedobanco /, de acordo com o protocolo NETBEUI \\nomedoservidor\unidade:\caminho\nomedobanco. Mesmo ao conectar o banco de dados a partir do computador, no qual o banco de dados está localizado e o servidor está em execução, deve-se usar a mesma linha renomeando nomedoservidor para localhost. Não se pode usar unidade mapeada na linha de conexão. Se você quebrar uma dessas regras, o servidor considera que está trabalhando com bancos de dados diferentes e a corrupção do banco de dados é garantida.
- Cópia de arquivo ou outro acesso a arquivos do banco de dados quando o servidor está em execução. A execução do comando “shut-down” ou a desconexão dos usuários da maneira usual não é uma garantia de que o servidor não está fazendo nada com o banco de dados, se o intervalo de sweep não estiver definido como “0”, a coleta de lixo pode ser executada. Geralmente, a coleta de lixo é executada imediatamente após o último usuário se desconectar do banco de dados. Normalmente, leva alguns segundos, mas se antes muitas operações DELETE ou UPDATE foram confirmadas, o processo pode ser mais longo.
- Uso de versões instáveis do servidor InterBase 5.1-.5.5. A empresa Borland admitiu oficialmente que havia vários erros nesses servidores e uma atualização estável 5.6 foi removida somente após a saída do InterBase 6 certificado em modo de execução livre para todos os clientes dos servidores 5.1-5.5 em seu site.
- Exceder o limite de tamanho do arquivo de banco de dados (não um banco de dados!). Para versões pré-InterBase 6 e alguns InterBase 6 beta, o limite do arquivo de banco de dados é 4Gb, para InterBase 6.5 e todas as versões do Firebird (1.0, 1.5, 2.0, 2.1) - 32Tb. Ao se aproximar do tamanho do banco de dados de um valor limite, um arquivo adicional deve ser criado.
- Esgotamento do espaço livre em disco ao trabalhar com o banco de dados.
- Para servidores Borland InterBase versões abaixo de 6.0.1.6 - exceder o limite do número de geradores de acordo com a Borland InterBase R & D definido da seguinte forma (veja tabela 1).
| Versão | Tamanho da página=1024 | Tamanho da página=2048 | Tamanho da página=4096 | Tamanho da página=8192 |
| Pré 6 | 248 | 504 | 1016 | 2040 |
| 6.0.x | 124 | 257 | 508 | 102 |
Tabela 1: Número crítico de geradores nas primeiras versões do InterBase
• Para todos os servidores Borland InterBase - exceder o número permitido de
transações sem executar backup/restore. Pode-se saber o número de
transações ocorridas no banco de dados desde a última criação invocando o utilitário gstat com uma chave - h- o parâmetro NEXT TRANSACTION ID será a quantidade desejada
de transações. De acordo com Ann W.Harrison, o número crítico de
transações depende do tamanho da página e tem os seguintes valores (veja tabela 2):
| Tamanho da página do banco de dados | Número crítico de transações |
| 1024 bytes | 131 596 287 |
| 2048 bytes | 265 814 016 |
| 4096 bytes | 534 249 472 |
| 8192 bytes | 1 071 120 384 |
Tabela 2: Número crítico de transações nos servidores Borland InterBase
As restrições dos servidores Borland InterBase enumeradas acima não se aplicam aos
servidores Firebird, exceto as primeiras versões 0.x., cuja existência já se tornou história. Se você usar a versão final Firebird 1.0 ou InterBase 6.5-7.x, não deve se preocupar com os pontos 5, 6, 8 e 9 e deve concentrar seus esforços em outras causas. Agora consideraremos as mais frequentes delas em detalhe.
2.3. Falha no fornecimento de energia
Ao desligar a energia no servidor, todas as atividades de processamento de dados são
interrompidas nos lugares mais inesperados e (de acordo com a lei de Murphy) perigosos. Como resultado disso, as informações no banco de dados podem ser distorcidas ou perdidas. O caso mais simples é quando todos os dados não confirmados dos aplicativos dos clientes foram perdidos como resultado do desligamento de emergência do servidor. Após o reinício após a falha de energia, o servidor analisa os dados, percebe transações incompletas relacionadas a nenhum dos clientes e cancela todas as modificações feitas dentro dos limites dessas transações “mortas”. Na verdade, esse comportamento é normal e previsto desde o início pelos desenvolvedores do InterBase.
No entanto, a interrupção do fornecimento de energia nem sempre é seguida apenas por perdas tão insignificantes. Se o servidor estava executando a extensão do banco de dados no momento da interrupção do fornecimento de energia, há uma grande probabilidade de ter páginas órfãs no arquivo de banco de dados (páginas que são fisicamente alocadas e registradas na página de inventário de páginas (PIP), cuja gravação de dados é impossível). Se você quiser saber mais sobre páginas órfãs, veja o capítulo «A estrutura do banco de dados InterBase».
Apenas a ferramenta de reparação e modificação gfix (que consideraremos abaixo) é capaz de lutar com páginas órfãs no arquivo de banco de dados. Na verdade, as páginas órfãs levam a despesas desnecessárias de espaço em disco e, como tal, não são a causa de perda de dados ou corrupção.
A perda de energia leva a danos mais sérios. Por exemplo, após desligar a
energia e reiniciar, uma grande quantidade de dados, incluindo confirmados, pode ser perdida (após adição ou modificação dos quais um comando «commit transaction» foi executado). Isso acontece porque os dados confirmados não são escritos diretamente no arquivo de banco de dados no disco. E o cache de arquivos do sistema operacional (SO) é usado para esse fim. O processo do servidor deu o comando de gravação de dados ao SO. Então o SO assegurou ao servidor que todos os dados foram salvos no disco e, na realidade, os dados foram armazenados no cache de arquivos. O SO não tem pressa para liberar esses dados para o disco, porque considera que há muita memória principal restante e adia as operações lentas de gravação no disco até que a memória principal esteja cheia.
2.4. Gravações forçadas - faca de dois gumes
Para afetar a situação, o ajuste do modo de gravação de dados é fornecido no InterBase 6. Este parâmetro é chamado forced writes (FW) e tem 2 modos - ON (síncrono) e OFF (assíncrono). Os modos FW definem como o InterBase se comunica com o disco. Se FW estiver ativado, a configuração de gravações síncronas no disco é ativada, quando os dados confirmados são gravados no disco logo após o comando commit, o servidor espera a conclusão da gravação e só então continua o processamento. Se FW estiver desativado, o InterBase não tem pressa para gravar dados no disco após o comando de confirmação de transação e delega essa tarefa a um thread paralelo enquanto o thread principal continua o processamento de dados sem esperar que as gravações sejam concluídas no disco. O modo de gravações síncronas é um dos mais cuidadosos e minimiza qualquer possível perda de dados, no entanto, pode causar alguma perda de desempenho. O modo de gravações assíncronas aumenta a probabilidade de perda de um grande número de dados. Para alcançar o máximo desempenho, o modo FW Off é geralmente definido. Mas como resultado da interrupção de energia, muito mais dados são perdidos durante as gravações assíncronas do que nas síncronas. Ao definir o modo de gravação, você deve decidir se alguns por cento de desempenho são mais significativos do que algumas horas de trabalho se a interrupção de energia acontecer inesperadamente.
Muitas vezes os usuários são descuidados com o InterBase. Pequenas organizações economizam em qualquer ninharia, muitas vezes no computador-servidor onde o servidor de SGBD e diferentes programas de servidor (e não apenas servidor) são instalados também. Se eles travam, as pessoas pensando por não muito tempo pressionam RESET (isso acontece várias vezes ao dia). Embora o InterBase seja muito estável a tais atividades em comparação com outros SGBDs e permita começar a trabalhar com o banco de dados logo após o reinício de emergência, tal uso não é desejado. O número de páginas órfãs aumenta e os dados perdem conexões entre si como resultado de reinícios com falhas.
Isso pode continuar por muito tempo, mas mais cedo ou mais tarde chegará ao fim. Quando páginas danificadas aparecem entre as páginas PIP ou páginas de geradores, ou se a página de cabeçalho do banco de dados estiver corrompida, o banco de dados pode nunca mais abrir e se tornar um grande pedaço de dados separados dos quais não se pode extrair um único byte de informação útil.
2.5. Corrupção do disco rígido
Corrupções do disco rígido levam à perda de páginas importantes do sistema do banco de dados e/ou corrupção de links entre as páginas restantes. Tais corrupções são um dos casos mais difíceis, porque quase sempre exigem interferência de baixo nível para restaurar o banco de dados.
2.6. Erros de design de banco de dados
É necessário que você saiba sobre alguns erros cometidos pelos desenvolvedores de banco de dados
que podem levar à impossibilidade de recuperação do banco de dados a partir de uma cópia de backup (*.gbk arquivos criados pelo programa gbak). Primeiro de tudo, isso é um uso descuidado de restrições no nível do banco de dados. Exemplo típico são restrições NOT NULL. Vamos supor que temos uma tabela preenchida com um número de registros. Agora adicionaremos a esta tabela usando o comando ALTER TABLE mais uma coluna e indicaremos que ela não deve conter valores não definidos NULL. Algo assim:
ALTER TABLE sometable Field/INTEGER NOT NULL
E neste caso não haverá erro do servidor, como seria de se esperar. Esta
modificação de metadados será confirmada e não receberemos nenhuma mensagem de erro ou aviso, o que cria uma ilusão de normalidade nesta situação.
No entanto, se fizermos backup do banco de dados e tentarmos restaurá-lo a partir de uma cópia de backup, receberemos uma mensagem de erro na fase de restauração (porque valores NULL são inseridos na coluna que possui a restrição NOT NULL, e o processo de restauração será interrompido. (Nota importante fornecida por Craig Stuntz - com a versão InterBase 7.1, as restrições são ignoradas por padrão durante a restauração (isso pode ser controlado por um parâmetro de linha de comando) e quase qualquer backup não corrompido pode ser restaurado. É sempre uma boa ideia fazer uma restauração de teste após criar um backup, mas esse problema deve praticamente desaparecer na versão 7.1.) Esta cópia de backup não pode ser restaurada. Se a restauração foi direcionada para um arquivo com o mesmo nome do banco de dados existente (durante a restauração, o arquivo de trabalho do banco de dados existente estava sendo sobrescrito), perderemos todas as informações.
Isso está relacionado ao fato de que as restrições NOT NULL são implementadas por triggers do sistema que verificam apenas os dados recebidos. Durante a restauração, os dados da cópia de backup são inseridos nas tabelas vazias recém-criadas - aqui podemos encontrar valores NULL inadmissíveis na coluna com a restrição NOT NULL.
Alguns desenvolvedores consideram que esse comportamento do InterBase é incorreto, mas outros não conseguirão adicionar um campo com a restrição NOT NULL à tabela do banco de dados.
A questão sobre o valor padrão obrigatório e seu preenchimento no momento da
criação foi amplamente discutida pelos arquitetos do Firebird, mas não foi aceita porque o programador obviamente irá preenchê-lo de acordo com um algoritmo bastante complexo e possivelmente iterativo. Mas não há garantia se ele conseguirá distinguir os registros ignorados pela iteração anterior dos registros não preenchidos ou não.
O problema semelhante pode ser causado por falha na coleta de lixo devido à definição de um caminho incorreto para o banco de dados (causa da corrupção 3) no momento da conexão e acesso a arquivos do banco de dados quando o servidor está trabalhando com ele (causa da corrupção 4), e registros totalmente preenchidos com NULL podem aparecer em algumas tabelas. É muito difícil detectar esses registros, porque eles não correspondem às restrições de controle de integridade, e o operador SELECT simplesmente não os vê, embora eles entrem na cópia de backup. Se for impossível restaurar por esse motivo, deve-se executar o programa gfix (veja abaixo), encontrar e excluir esses registros usando campos não indexados como condições de busca, e depois tentar novamente fazer uma cópia de backup e restaurar o banco de dados a partir dela. Em conclusão, podemos dizer que há um grande número de causas de corrupção de banco de dados e você deve estar sempre preparado para o pior - que seu banco de dados seja danificado por um motivo ou outro. Você também deve estar pronto para restaurar e salvar informações valiosas. E agora consideraremos as precauções que garantem a segurança do banco de dados InterBase, bem como os métodos de reparo de bancos de dados danificados.
2.7. Precauções contra corrupção do banco de dados InterBase
Para prevenir a corrupção do banco de dados, deve-se sempre criar cópias de backup (se quiser saber mais sobre backup, consulte o capítulo “Backup e restauração”). É a forma mais confiável contra a corrupção do banco de dados. Somente o backup dá 100% de garantia de segurança do banco de dados. Como descrito acima, como resultado do backup podemos obter uma cópia inútil (uma cópia que não pode ser restaurada), por isso a restauração de um banco de dados a partir da cópia não deve ser feita sobrescrevendo o script, e o backup deve ser feito de acordo com regras definidas. Primeiramente, o backup deve ser executado com a maior frequência possível; em segundo lugar, deve ser sequencial; e em terceiro lugar, as cópias de backup devem ser verificadas quanto à capacidade de restauração.
Frequentemente, backup significa que é necessário fazer uma cópia de backup com bastante regularidade, por exemplo, uma vez a cada vinte e quatro horas. Quanto menor o período entre os backups do banco de dados, menos dados serão perdidos como resultado de uma falha. A sequência de backup significa que o número de backups deve aumentar e ser armazenado por pelo menos uma semana. Se houver possibilidade, é necessário gravar os backups em dispositivos especiais como streamer, mas se não houver - basta copiá-los para outro computador. O histórico de cópias de backup ajudará a descobrir corrupções ocultas e lidar com o erro que surgiu há muito tempo e se manifestou inesperadamente. É necessário verificar se é possível restaurar o backup recebido sem erros ou não. Isso só pode ser verificado de uma maneira - através do processo de restauração de teste. Deve-se dizer que o processo de restauração leva 3 vezes mais tempo que o backup, e é difícil executar a validação de restauração todos os dias para bancos de dados grandes, porque pode interromper o trabalho dos usuários por algumas horas (a pausa noturna pode não ser suficiente).
Seria melhor se grandes organizações não economizassem em “fósforos” e deixassem um computador para esses fins.
Neste caso, se o servidor precisa trabalhar com carga pesada 24 horas por dia, 7 dias por semana, podemos usar o mecanismo SHADOW para tirar snapshots do banco de dados e operações de backup posteriores a partir da cópia imediata. O processo de backup e restauração do banco de dados é descrito em detalhes no capítulo “Backup e restauração”. Ao criar um backup e depois restaurar o banco de dados a partir dele, ocorre a recriação de todos os dados no banco de dados. Este processo (backup/restauração ou b/r) contribui para a correção da maioria dos erros não fatais no banco de dados, relacionados a corrupções do disco rígido, detecção de problemas de integridade no banco de dados, limpeza do banco de dados de lixo (versões antigas e fragmentos de registros, transações incompletas), diminuindo consideravelmente o tamanho do banco de dados.
O b/r regular é uma garantia de segurança do banco de dados InterBase. Se o banco de dados está funcionando, é recomendado executar o b/r toda semana. Para ser sincero, existem alguns exemplos de bancos de dados InterBase que são intensivamente usados por anos sem backup/restauração.
No entanto, para estar seguro, é desejável realizar esse procedimento, especialmente porque pode ser facilmente automatizado (veja o capítulo “Backup”).
Se for impossível realizar backup/restauração com frequência por alguns motivos, pode-se usar a ferramenta gfix para verificar e restaurar o banco de dados. O gfix permite verificar e remover muitos erros sem b/r.
2.8. Ferramenta de linha de comando gfix
A ferramenta de linha de comando gfix é usada para verificar e restaurar o banco de dados. Além disso, o gfix também pode executar várias atividades de controle do banco de dados: alterar o dialeto do banco de dados, definir e cancelar o modo “somente leitura”, definir o tamanho do cache para um banco de dados específico e também algumas funções importantes (você pode conhecê-las no InterBase 6 Operations Guide [4.) O gfix é executado em modo de linha de comando e tem a seguinte sintaxe:
Gfix [opções] nome_do_banco
Opções - é um conjunto de opções para executar o gfix; nome_do_banco é o nome do banco de dados sobre o qual as operações serão realizadas, definido pelo conjunto de opções. A Tabela 3 representa as opções do gfix relacionadas ao reparo do banco de dados:
| Opção | Descrição |
| -f[ull] | Esta opção é usada em combinação com -v e significa que é hora de verificar todos os fragmentos de registros |
| -i[gnore] | A opção faz o gfix ignorar erros de checksum no momento da validação ou limpeza do banco de dados |
| -m[end] | Marca registros danificados como indisponíveis, como resultado do que eles serão excluídos durante o backup/restauração seguinte. A opção é usada no momento de preparar o banco de dados corrompido para b/r. |
| -n[o_update] | A opção é usada em combinação com -v para validação somente leitura do banco de dados sem corrigir corrupções |
| -pas[sword] | A opção permite definir a senha ao conectar ao banco de dados. (Observe que é um erro na documentação do InterBase -pa[ssword], mas o atalho “-pa” não funcionará - use “-pas”) |
| -user | A opção permite definir o nome do usuário ao conectar ao banco de dados |
| -v[alidate] | Opção que define a validação do banco de dados, na forma da qual erros são descobertos |
| -m[ode] | Opção que define o modo de gravação do banco de dados - para somente leitura ou leitura/gravação. Este parâmetro pode aceitar 2 valores - read write ou read only. |
| -w[rite] {sync | async} | Opção que ativa e desativa o modo síncrono/assíncrono de gravações forçadas no banco de dados. sync - para ativar gravações síncronas (FW ON); async - para ativar gravações assíncronas (FW OFF); |
Tabela 1: Opções da ferramenta gfix para restauração do banco de dados
Existem alguns exemplos típicos de uso do gfix:
gfix -w sync -user SYSDBA -pass masterkey firstbase.gdb
Neste exemplo, definimos para nosso banco de dados de teste firstbase.gdb o modo de gravações síncronas (FW ON). (Claro, é útil antes que a corrupção ocorra). E abaixo está o primeiro comando que você deve usar para verificar o banco de dados após a corrupção ocorrer:
gfix -v -full -user SYSDBA -pass masterkey firstbase.gdb
Neste exemplo, começamos a verificar nosso banco de dados de teste (opção -v) e indicamos que os fragmentos de registros também devem ser verificados (opção -full). Claro, é mais conveniente definir várias opções para o processo de verificação e restauração por qualquer GUI, mas consideraremos as funções de recuperação do banco de dados usando ferramentas de linha de comando. Essas ferramentas estão incluídas no InterBase e você pode ter certeza de que seu comportamento será o mesmo em todos os SO que executam o InterBase. É muito importante que elas estejam sempre por perto.
Além disso, as ferramentas existentes que permitem executar a administração do banco de dados a partir de um computador cliente usam a Services API para isso, que não é suportada pela arquitetura Classic do servidor InterBase. Isso significa que você pode usar produtos de terceiros com a arquitetura de servidor SuperServer.
2.9. O reparo de banco de dados corrompido
Vamos supor que existam alguns erros em nosso banco de dados. Primeiramente, temos que verificar a existência desses erros; em segundo lugar, temos que tentar corrigir esses erros. Você deve seguir as seguintes instruções.
Você deve parar o servidor InterBase se ele ainda estiver funcionando e fazer uma cópia do arquivo ou dos arquivos do banco de dados. Todas as atividades de restauração devem ser realizadas apenas com a cópia do banco de dados, porque o caminho escolhido pode levar a um resultado infeliz, e você terá que reiniciar o procedimento de restauração (a partir de um ponto inicial). Após criar a cópia, realizaremos a validação completa do banco de dados (verificação de fragmentos de registros).
Devemos executar o seguinte comando para isso:
gfix -v - full corruptbase gdb -user SYSDBA - password
Neste caso, corruptbase.gdb - é uma cópia do banco de dados danificado. Um comando verificará o banco de dados quanto a qualquer corrupção de estrutura e dará a lista de problemas não resolvidos. Se tais erros forem detectados, teremos que excluir os dados danificados e nos preparar para backup/restauração usando o seguinte comando:
gfix -mend -user SYSDBA -password your_masterkey corruptbase gdb
Após executar o comando, você deve verificar se ainda existem alguns erros no banco de dados. Você deve executar o gfix com as opções -v -full para isso, e quando o processo terminar, realizar o backup do banco de dados:
gbak -b -v -ig -user SYSDBA -password corruptbase.gdb corruptbase.gbk
Este comando realizará o backup do banco de dados (a opção - b indica isso) e obteremos informações detalhadas sobre a execução do processo de backup (opção -v). Erros relacionados a checksums serão ignorados (opção - ig). Se quiser saber mais informações sobre as opções da ferramenta de linha de comando gbak, você pode encontrá-las no capítulo “Backup e restauração”. Se houver alguns erros com o backup, você deve iniciá-lo em outra configuração:
gbak -b -v -ig -g -user SYSDBA -password corruptbase.gdb
corruptbase.gbk
Onde a opção - g desativará a coleta de lixo durante o backup. Isso muitas vezes ajuda a resolver um problema com o backup.
Também pode ser possível fazer um backup do banco de dados se, antes disso, definirmos o banco de dados em modo somente leitura. Este modo impede a gravação de qualquer modificação no banco de dados e às vezes ajuda a realizar o backup de um banco de dados danificado. Para definir o banco de dados em modo somente leitura, você deve usar o seguinte comando: gfix -m read_only
-user SYSDATA -password masterkey Disk:\Path\file.gdb
Depois disso, você deve tentar novamente realizar o backup do banco de dados usando os parâmetros fornecidos acima.
Se o backup foi concluído com sucesso, você deve restaurar o banco de dados a partir da cópia de backup. Você deve usar o seguinte comando:
gbak -c -user SYSDATA -password masterkey Disk:\Path\backup.gbk
Disk:\Path\newbase,gdb
Ao restaurar o banco de dados, você pode ter alguns problemas, especialmente ao criar os índices. Nesse caso, as opções -inactive e -one_at_a_time devem ser adicionadas ao comando de restauração. Essas opções desativam os índices criados a partir do backup do banco de dados e confirmam os dados para cada tabela.
2.10. Como você pode tentar extrair os dados de um banco de dados corrompido
É possível que as operações acima não levem à recuperação do banco de dados. Isso significa que o banco de dados está seriamente danificado ou não pode ser restaurado como um todo, ou que muitos esforços devem ser feitos para sua recuperação. Por exemplo, pode-se executar uma modificação dos metadados do sistema, usar funções não documentadas e assim por diante. É um trabalho muito difícil, demorado e ingrato, com chances duvidosas de sucesso. E, se possível, tente evitá-lo e use outros métodos. Se um banco de dados danificado abrir e permitir operações de leitura e modificação com alguns dados, você deve usar essa possibilidade e salvar os dados copiando-os para um novo banco, e “dizer adeus” ao antigo de vez.
Portanto, antes de transferir os dados do banco de dados antigo, é necessário criar um banco de dados de destino. Se o banco de dados não foi alterado por um longo tempo, você pode usar o backup antigo, do qual os metadados podem ser extraídos para criar um banco de dados de destino. Com base nesses metadados, deve-se criar um banco de dados de destino e começar a copiar os dados. A principal tarefa é extrair os dados de um banco de dados danificado. Depois, teremos que alocar os dados em um novo banco, mas isso não é muito difícil, mesmo que tenhamos que restaurar a estrutura do banco de dados de memória. Ao extrair dados de tabelas, você deve usar o seguinte algoritmo de operações:
- Primeiro, você deve tentar executar SELECT* da tabela N. Se isso ocorrer normalmente, você pode salvar os dados obtidos na fonte externa. É melhor armazenar os dados em script (quase todas as interfaces gráficas oferecem essa função), desde que a tabela não contenha campos BLOB. Se houver campos BLOB na tabela, os dados deles devem ser salvos em outro banco de dados por um programa cliente que atuará como mediador. Talvez você precise escrever esse programa trivial especialmente para fins de recuperação de dados.
- Se você não conseguir recuperar todos os dados, deve excluir todos os índices e tentar novamente. Praticamente, os índices podem ser excluídos de todas as tabelas desde o início da restauração, pois não serão mais necessários. Claro, se você não tiver uma estrutura de metadados igual à corrompida, é necessário registrar um protocolo de todas as operações que você está realizando com o banco de dados-fonte danificado.
- Se você não conseguir ler todos os dados da tabela após excluir os índices, pode-se tentar fazer uma consulta por intervalo usando a chave primária. Isso significa escolher um intervalo definido de dados. Por exemplo:
SELECT * FROM table N WHERE field_PK >=0 and field_PK <=10000 Field_PK
aqui está uma chave primária. O InterBase tem organização de dados por páginas e, por isso, consultas por intervalo de valores podem ser bastante eficazes, embora pareça algo como xamanismo. No entanto, funciona porque podemos expulsar dados da consulta de páginas danificadas e ler, felizmente, as outras. Você pode lembrar de nossa tese de que não há uma ordem definida de armazenamento de registros em SQL. Realmente, ninguém garante que uma consulta não ordenada durante reinicializações retornará os registros na mesma ordem, mas, no entanto, os registros físicos são armazenados dentro do banco de dados em uma ordem interna definida. É óbvio que o servidor não misturará os registros apenas para cumprir o padrão SQL. Pode-se tentar usar essa ordem interna para extrair dados de um banco de dados danificado (se você quiser saber mais informações sobre páginas de dados e suas correlações, consulte o capítulo “Estrutura do banco de dados InterBase”).
Vitaliy Barmin, um dos experientes desenvolvedores russos de InterBase, relatou que dessa forma ele conseguiu restaurar até 98% das informações de um banco de dados irrecuperável (havia um grande número de páginas danificadas). Assim, os dados de um banco de dados danificado devem ser movidos para um novo banco de dados ou para fontes externas, como scripts SQL. Ao copiar os dados, preste atenção aos valores dos geradores no banco de dados danificado (eles devem ser salvos para reiniciar um trabalho adequado no novo banco de dados. Se você não tiver uma cópia completa dos metadados, deve extrair os textos de procedimentos armazenados, gatilhos, restrições e definições de índices.
2.11. Restauração de banco de dados sem esperança
Em geral, a restauração de um banco de dados pode ser muito problemática e difícil, e por isso é melhor fazer uma cópia de backup do banco de dados do que restaurar os dados danificados e, aconteça o que acontecer, você não deve se desesperar, pois uma solução pode ser encontrada nas situações mais difíceis. E agora consideraremos 2 casos.
O primeiro caso (um problema clássico). Um backup que não pode ser restaurado devido à presença de valores NULL na coluna com restrição NOT NULL (o processo de restauração foi executado sobre o arquivo de trabalho). O arquivo de trabalho foi apagado e o processo de restauração foi interrompido devido a um erro. E, como resultado de ações impensadas, obtivemos um grande número de dados inúteis (que não podem ser restaurados) em vez da cópia de backup. Mas a solução foi encontrada. O programador conseguiu lembrar qual tabela e qual coluna tinham restrição NOT NULL. O arquivo de backup foi carregado em um editor hexadecimal. E uma combinação de bytes, correspondente à definição dessa coluna, foi encontrada lá por busca. Após inúmeros experimentos, descobriu-se que a restrição NOT NULL adiciona 1 em algum lugar próximo ao nome da coluna. No editor HEX, esse “1” foi corrigido para “0” e a cópia de backup foi restaurada. Depois desse caso, o programador memorizou de uma vez por todas como executar o processo de backup e restauração.
O segundo caso. A situação foi catastrófica. Banco de dados corrompido na fase de extensão devido à falta de espaço em disco. Ao aumentar o tamanho do banco de dados, o servidor cria uma série de páginas criticamente importantes (por exemplo, página de inventário de transações e página de inventário de páginas, páginas adicionais para a relação RDB$Pages) e as grava no final do banco de dados. Como resultado, o banco de dados não abriu nem pelas ferramentas de administração nem pelo utilitário GBAK. E quando tentamos conectar ao banco de dados, apareceu uma mensagem de erro (“Unexpected end of file”).
Quando executamos o utilitário gfix, coisas estranhas aconteceram: o programa estava funcionando em um ciclo infinito. Quando o gfix estava trabalhando, o servidor gravava erros no log (arquivo InterBase log) em alta velocidade (cerca de 100 Kb por segundo). Como resultado, o arquivo de log encheu todo o espaço livre em disco muito rapidamente. Tivemos até que escrever um programa que apagava esse log por temporizador. Esse processo durou muito tempo - o gfix funcionou por mais de 16 horas sem nenhum resultado. O log foi preenchido com erros do seguinte tipo: “Page XXX doubly allocated”. Nos códigos-fonte iniciais do InterBase (no arquivo val.#), há uma breve descrição desse erro. Diz que esse erro aparece quando a mesma página de dados é usada duas vezes. É óbvio que esse erro é resultado da corrupção de páginas criticamente importantes.
Como resultado, após vários dias de experimentos infelizes, as tentativas de restaurar os dados de maneiras padrão foram abandonadas. E por isso tivemos que usar análise de baixo nível dos dados armazenados no banco de dados danificado.
Alexander Kozelskiy, chefe do departamento de tecnologias da informação da East View Publications Inc, é o autor da ideia de como extrair informações de bancos de dados irrecuperáveis semelhantes.
O método de restauração que obtivemos como resultado das pesquisas baseou-se no fato de que o banco de dados tem organização por páginas e os dados de cada tabela são coletados em páginas de dados. Cada página de dados contém o identificador da tabela para a qual armazena dados. Foi especialmente importante restaurar dados de várias tabelas críticas. Havia dados de tabelas semelhantes, recebidos de uma cópia de backup antiga que funcionava perfeitamente e poderia servir como modelo. O banco de dados-modelo foi carregado em um editor de fontes hexadecimais e então procuramos pelos padrões desses dados que nos interessavam. Esses dados foram copiados para o buffer em formato hexadecimal e, em seguida, os restos do banco de dados danificado foram carregados no editor. Uma sequência de bytes correspondente ao padrão foi encontrada no banco de dados danificado, e a página (na qual essa sequência foi encontrada) foi analisada.
Primeiro, definimos a página inicial, mas isso não foi difícil porque o tamanho do arquivo do banco de dados é divisível pelo tamanho da página de dados. Um número do byte atual dividido pelo tamanho da página - 8192 bytes, aproxima o resultado para um inteiro (e obtém o número da página atual). Em seguida, multiplicamos o número da página atual pelo tamanho da página e obtivemos o número do byte correspondente ao início da página atual. Após analisar o cabeçalho, definimos o tipo de página (para páginas com dados, o tipo é 5 - veja o arquivo ods.h do conjunto de códigos-fonte iniciais do InterBase e também o capítulo “A estrutura do banco de dados InterBase”), bem como o identificador da tabela necessária.
Então, um programa foi escrito, que analisou todo o banco de dados, coletou todas as páginas da tabela necessária em um único bloco e o moveu para um arquivo.
Assim, quando obtivemos os dados que precisávamos em primeiro lugar, começamos a analisar o conteúdo das páginas selecionadas. O InterBase usa amplamente a compactação de dados para economizar espaço. Por exemplo, uma string como VARCHAR contendo a string “ABC” armazena a seguinte sequência de valores: comprimento da string (2 bytes), no nosso caso é 0003, e depois os próprios símbolos e, em seguida, a soma de verificação. Tivemos que escrever um analisador de strings, bem como de outros tipos de dados do banco de dados, que convertia dados do formato hexadecimal para a visão comum. Conseguimos extrair até 80% das informações de várias tabelas críticas usando um método “manual” de análise do conteúdo do banco de dados. Mais tarde, com base na experiência, Oleg Kulkov e Alexey Kovyazin, um dos autores deste livro, desenvolveram o utilitário InterBase Surgeon que realiza acesso direto ao banco de dados, contornando o mecanismo InterBase e permite ler diretamente e interpretar os dados dentro do banco de dados InterBase de maneira adequada.
Usando o InterBase Surgeon, conseguimos detectar causas de corrupção e restaurar até 90% de bancos de dados absolutamente irrecuperáveis que não podem ser abertos pelo InterBase e restaurados por métodos padrão.
Você pode baixar este programa no site oficial do programa www.ib-aid.com.
3. Agradecimentos
Gostaria de agradecer a todos que me ajudaram a criar este guia:
Craig Stuntz, Alexander Nevsky, Konstantin Sipachev, Tatjana Sipacheva e todas as outras pessoas gentis e conhecedoras da comunidade InterBase e Firebird.
Se você tiver alguma sugestão ou pergunta sobre este capítulo, sinta-se à vontade para enviar um e-mail.
© 2002 AIexey Kovyazin, Serge Vostrikov.
Copyright © 2004 IBSurgeon Team. Todos os direitos reservados.