Capítulo 10. Gestão de dados

# Capítulo 10. Gestão de dados

São descritas ferramentas e dicas para gerir dados binários e de texto no sistema Debian.

## 10.1. Partilhar, copiar e arquivar

| Atenção
O acesso de escrita descoordenado a aparelhos acedidos activamente e a ficheiros a partir de múltiplos processos não deve ser feito para evitar a condição de competição. Devem ser usados mecanismos de bloqueio de ficheiro que usem o flock(1) para o evitar.

A segurança dos dados e a partilha controlada dele têm vários aspectos.

- A criação de um arquivo de dados

- O acesso a armazenamento remoto

- A duplicação

- O acompanhar do histórico de modificação

- A facilitação da partilha de dados

- A prevenção de acessos não autorizados a ficheiros

- A detecção de modificação não autorizada de ficheiros

Estas podem ser realizadas a usar a combinação de algumas ferramentas.

- Ferramentas de arquivo e compressão

- Ferramentas de cópia de sincronização

- Sistemas de ficheiros de rede

- Media de armazenamento amovível

- A shell segura

- O sistema de autenticação

- Ferramentas de sistema de controle de versão

- Ferramentas de hash e encriptação criptográfica

### 10.1.1. Ferramentas de arquivo e compressão

Aqui está um sumário das ferramentas de arquivo e compressão disponíveis no sistema Debian.

Tabela 10.1. Lista de ferramentas de arquivo e compressão

pacote | popcon | tamanho | extensão | comando | comentário
--- | --- | --- | --- | --- | ---
`tar` | V:906, I:1000 | 3101 | `.tar` | tar(1) | o arquivador standard (de facto standard)
`cpio` | V:354, I:999 | 1201 | `.cpio` | cpio(1) | arquivador estilo Unix System V, usar com o find(1)
`binutils` | V:190, I:637 | 1119 | `.ar` | ar(1) | arquivador para a criação de bibliotecas estáticas
`fastjar` | V:0.9, I:9.8 | 182 | `.jar` | fastjar(1) | arquivador para Java (estilo zip)
`pax` | V:5.4, I:9.5 | 167 | `.pax` | pax(1) | novo arquivador standard do POSIX, um compromisso entre `tar` e `cpio`
`gzip` | V:902, I:1000 | 256 | `.gz` | gzip(1), zcat(1), … | LZ77 utilitário de compressão do GNU (o standard de facto)
`bzip2` | V:159, I:972 | 113 | `.bz2` | bzip2(1), bzcat(1), … | Compressão de organização de blocos de Burrows-Wheeler utilitário com um rácio de compressão mais alto que o gzip(1) (mais lento que o `gzip` com sintaxe semelhante)
`lzma` | V:1, I:10 | 349 | `.lzma` | lzma(1) | LZMA utilitário de compressão com rácio de compressão mais alto que o gzip(1) (descontinuado)
`xz-utils` | V:309, I:981 | 1520 | `.xz` | xz(1), xzdec(1), … | XZ utilitário de compressão com rácio de compressão mais alto que o bzip2(1) (mais lento que o `gzip` mas mais rápido que o `bzip2`; substituto para o utilitário de compressão LZMA)
`zstd` | V:319, I:814 | 2308 | `.zstd` | zstd(1), zstdcat(1), … | Utilitário de compressão rápida sem perdas Zstandard
`p7zip` | V:5, I:184 | 8 | `.7z` | 7zr(1), p7zip(1) | 7-Zip arquivador de arquivos com alta taxa de compressão (compressão LZMA)
`p7zip-full` | V:15, I:210 | 12 | `.7z` | 7z(1), 7za(1) | 7-Zip arquivador de ficheiros com rácio de compressão alto (LZMA compressão e outros)
`lzop` | V:12, I:132 | 164 | `.lzo` | lzop(1) | LZO utilitário de compressão com mais alta compressão e mais rápida descompressão que o gzip(1) (rácio de compressão mais baixo que o `gzip` com sintaxe semelhante)
`zip` | V:48, I:360 | 635 | `.zip` | zip(1) | InfoZIP: ferramenta de compressão e arquivo do DOS
`unzip` | V:109, I:747 | 399 | `.zip` | unzip(1) | InfoZIP: ferramenta de descompressão e de de-arquivar do DOS

| Atenção
Não defina a variável "`$TAPE`" a menos que saiba com o que esperar. Altera o comportamento do tar(1).

- O arquivo tar(1) gzipado usa a extensão de ficheiro "`.tgz`" ou "`.tar.gz`".

- O arquivo tar(1) comprimido em xz usa a extensão de ficheiro "`.txz`" ou "`.tar.xz`".

- Método de compressão popular em ferramentas FOSS tal como o tar(1) têm se movido como a seguir: `gzip` → `bzip2` → `xz`

- cp(1), scp(1) e tar(1) podem ter algumas limitações para ficheiros especiais. cpio(1) é o mais versátil.

- O cpio(1) é desenhado para ser utilizado com o find(1) e outros comandos e apropriado para criar scripts de backup pois a parte de seleção de ficheiros do script pode ser testada independentemente.

- A estrutura interna dos ficheiros de dados do Libreoffice são ficheiros "`.jar`" que também podem ser abertos pelo `unzip`.

- A ferramenta de arquivo que é "de-facto" multi-plataforma é o `zip`. Use-o como "`zip -rX`" para obter o máximo de compatibilidade. Use também a opção "`-s`", se o tamanho máximo de ficheiro for importante.

### 10.1.2. Ferramentas de cópia de sincronização

Aqui está um sumário de ferramentas de cópia simples e salvaguarda disponíveis no sistema Debian.

Tabela 10.2. Lista de ferramentas de cópia e sincronização

pacote | popcon | tamanho | ferramenta | função
--- | --- | --- | --- | ---
`coreutils` | V:910, I:1000 | 17994 | GNU cp | copia localmente ficheiros e diretórios ("-a" para ser recursivo)
`openssh-client` | V:657, I:996 | 3521 | scp | copia remotamente ficheiros e diretórios (cliente, "`-r`" para ser recursivo)
`openssh-server` | V:772, I:820 | 3594 | sshd | copia ficheiros e diretórios remotamente (servidor remoto)
`rsync` | V:196, I:542 | 835 |  | sincronização remota a salvaguarda de 1 via
`unison` | V:2, I:11 | 14 |  | sincronização remota a salvaguarda de 2 vias

Copiar ficheiros com o rsync(8) oferece funcionalidades mais ricas que os outros.

- algoritmo de transferência delta que envia apenas as diferenças entre os ficheiros da fonte e os ficheiros existentes no destino

- algoritmo de verificação rápida (predefinido) que procura ficheiros que alteraram no tamanho ou hora da última modificação

- opções "`--exclude`" e "`--exclude-from`" semelhantes ao tar(1)

- sintaxe de "uma barra final no diretório fonte" que evita a criação de um nível de diretório adicional no destino.

| Dica
Ferramentas de sistema de controlo de versão (VCS) em Tabela 10.14, “Lista de outras ferramentas de sistemas de controlo de versões” podem funcionar como a copia de multi-modos e ferramentas de sincronização.

### 10.1.3. Idiomas para o arquivo

Aqui estão várias maneiras de arquivar e "desarquivar" o conteúdo completo do diretório "`./source`" a usar diferentes ferramentas.

GNU tar(1):

    $ tar -cvJf archive.tar.xz ./source
    $ tar -xvJf archive.tar.xz

Alternativamente, pelo seguinte.

    $ find ./source -xdev -print0 | tar -cvJf archive.tar.xz --null -T -

cpio(1):

    $ find ./source -xdev -print0 | cpio -ov --null > archive.cpio; xz archive.cpio
    $ zcat archive.cpio.xz | cpio -i

### 10.1.4. Idiomas para a cópia

Aqui estão algumas maneiras de copiar o conteúdo inteiro do diretório "`./source`" a usar diferentes ferramentas.

- Cópia local: diretório "`./source`" → diretório "`/dest`"

- Cópia remota: diretório "`./source`" em máquina local → diretório "`/dest`" na máquina "`utilizador@máquina.domínio`"

rsync(8):

    # cd ./source; rsync -aHAXSv . /dest
    # cd ./source; rsync -aHAXSv . user@host.dom:/dest

Pode alternativamente usar a sintaxe de "uma barra à direita no diretório fonte".

    # rsync -aHAXSv ./source/ /dest
    # rsync -aHAXSv ./source/ user@host.dom:/dest

Alternativamente, pelo seguinte.

    # cd ./source; find . -print0 | rsync -aHAXSv0 --files-from=- . /dest
    # cd ./source; find . -print0 | rsync -aHAXSv0 --files-from=- . user@host.dom:/dest

cp(1) de GNU e scp(1) de openSSH:

    # cd ./source; cp -a . /dest
    # cd ./source; scp -pr . user@host.dom:/dest

GNU tar(1):

    # (cd ./source && tar cf - . ) | (cd /dest && tar xvfp - )
    # (cd ./source && tar cf - . ) | ssh user@host.dom '(cd /dest && tar xvfp - )'

cpio(1):

    # cd ./source; find . -print0 | cpio -pvdm --null --sparse /dest

Pode substituir "`.`" por "`foo`" para todos os exemplos que contenham "`.`" para copiar ficheiros do diretório "`./source/foo`" ao diretório "`/dest/foo`".

Pode substituir "`.`" pelo caminho absoluto "`/caminho/para/fonte/foo`" para todos os exemplos que contenham "`.`" para abandonar "`cd ./source;`". Estes copiam ficheiros para localizações diferentes a depender das ferramentas utilizadas conforme a seguir.

- "`/dest/foo`": rsync(8), cp(1) do GNU e scp(1)

- "`/dest/path/to/source/foo`": GNU tar(1) e cpio(1)

| Dica
rsync(8) e cp(1) do GNU têm a opção "`-u`" para saltar ficheiros que são mais recentes no receptor.

### 10.1.5. Idiomas para a seleção de ficheiros

O find(1) é usado para selecionar ficheiros para o arquivo e copiar comandos (veja Seção 10.1.3, “Idiomas para o arquivo” e Seção 10.1.4, “Idiomas para a cópia”) ou para xargs(1) (veja Seção 9.4.9, “Repetir um ciclo de comandos sobre ficheiros”). Isto pode ser melhorado ao usar os seus argumentos de comando.

A sintaxe básica de find(1) pode ser sumariada no seguinte.

- Os seus argumentos condicionais são avaliados da esquerda à direita.

- Esta avaliação pára assim que o resultado dele é determinado.

- O "OU lógico" (especificado por "`-o`" entre condicionais) tem precedência mais baixa que o "E lógico" (especificado por "`-a`" ou nada entre condicionais).

- O "NÃO lógico" (especificado por "`!`" antes duma condicional) tem precedência mas alta que o "E lógico".

- "`-prune`" retorna sempre o VERDADEIRO lógico e, se for um diretório, a busca de ficheiro é parada para além deste ponto.

- "`-name`" corresponde à base do nome de ficheiro com glob de shell (veja Seção 1.5.6, “Glob da shell”) mas também corresponde ao "`.`" inicial dele com meta-caracteres como o "`*`" e o "`?`". (Nova funcionalidade do POSIX)

- "`-regex`" corresponde ao caminho completo com estilo emacs BRE (veja Seção 1.6.2, “Expressões regulares”) como predefinição.

- "`-size`" corresponde ao ficheiro baseado no tamanho do ficheiro (valor precedido de "`+`" para maior, precedido de "`-`" para menor)

- "`-newer`" corresponde ao ficheiro mais recente que aquele especificado no argumento dele.

- "`-print0`" retorna sempre o TRUE lógico e escreve o nome de ficheiro completo (terminado em nulo) na saída standard.

O find(1) é usado geralmente com um estilo idiomático como a seguir.

    # find /path/to \
        -xdev -regextype posix-extended \
        -type f -regex ".*\.cpio|.*~" -prune -o \
        -type d -regex ".*/\.git" -prune -o \
        -type f -size +99M -prune -o \
        -type f -newer /path/to/timestamp -print0

Isto significa fazer as seguintes acções.

1. Procurar todos os ficheiros que começam por "`/caminho/para`"

2. Limitar globalmente a busca para dentro do sistema de ficheiros inicial e usa ERE (ao inves veja Seção 1.6.2, “Expressões regulares”)

3. Excluir da busca os ficheiros que correspondem à expressão regular "`.*\.cpio`" ou "`.*~`" ao parar o processamento

4. Excluir da busca os diretórios que correspondem à expressão regular "`.*/\.git`" ao parar o processamento

5. Exclui da busca os ficheiros maiores que 99 Mb (unidades de 1048576 bytes) ao parar o processamento

6. Escrever os nomes de ficheiros que satisfazem as condições de busca em cima e são mais recentes que "`/caminho/para/timestamp`"

Por favor note a utilização idiomática de "`-prune -o`" para excluir ficheiros no exemplo em cima.

| Nota
Para um sistema não-Debian tipo Unix, algumas opções podem não ser suportadas pelo find(1). Em tal caso, por favor considere ajustar os métodos de correspondência e substitua "`-print0`" por "`-print`". Poderá ter que ajustar também os comandos relacionados.

### 10.1.6. Meio de arquivo

Quando escolher o meio de armazenamento de dados de computador para arquivar dados importantes, deverá ter cuidado com as suas limitações. Para os pequenos backups de dados pessoais uso CD-Rs e DVD-Rs de uma boa marca e guardo-os num ambiente fresco, à sombra, seco e limpo. (O meio de cassete de fita magnética parece ser popular para uso profissional.)

| Nota
A segurança de resistência ao fogo destina-se a documentos de papel. A maioria dos meios de armazenamento de dados de computador têm menos tolerância à temperatura que o papel. Geralmente Confio em múltiplas cópias de segurança encriptadas em múltiplas localizações seguras.

A duração de vida optimista de meios de arquivo vista na net (a maioria é informação do fabricante).

- + de 100 anos : Papel livre de ácidos com tinta

- 100 anos : Armazenamento óptico (CD/DVD, CD/DVD-R)

- 30 anos : Armazenamento magnético (fita, disquete)

- 20 anos : Armazenamento óptico de mudança de fase (CD-RW)

Estes não contam com falhas mecânicas devido a manuseamento e etc.

Ciclos de escrita optimistas dos meios de arquivo vistos na net (a maioria é informação do fabricante).

- + de 250,000 ciclos : Disco rígido

- + de 10,000 ciclos : Memória Flash

- 1,000 ciclos : CD/DVD-RW

- 1 ciclo : CD/DVD-R, papel

| Cuidado
As figuras de vida de armazenamento e ciclos de escrita mostradas aqui não devem ser usadas para decisões em qualquer armazenamento de dados crítico. Por favor consulte a informação específica do produto disponibilizada pelo fabricante.

| Dica
Como os CD/DVD-R e o papel têm apenas 1 ciclo de escrita, eles previnem perdas de dados acidentais ao sobrescrever. Isto é uma vantagem!

| Dica
Se precisa de um backup rápido e frequente de grandes quantidades de dados, um disco rígido numa máquina remota ligada por uma ligação de rede rápida, pode ser a única opção realista.

| Dica
Se utilizar suportes regraváveis para as suas cópias de segurança, a utilização de um sistema de ficheiros como o btrfs ou zfs, que suportam instantâneos apenas de leitura, pode ser uma boa ideia.

### 10.1.7. Aparelho de armazenamento amovível

Aparelhos de armazenamento amovível podem ser qualquer um dos seguintes.

- Pen USB

- Disco Rígido

- Leitor de disco óptico

- Câmara digital

- Leitor digital de música

Eles podem ser conectados por qualquer um dos seguintes:

- USB

- IEEE 1394 / FireWire

- PC Card

Os ambientes de trabalho modernos tais como o GNOME e KDE podem montar automaticamente estes aparelhos amovíveis sem uma entrada correspondente no "`/etc/fstab`".

- O pacote `udisks2` disponibiliza um daemon e utilitários associados para (des)montar esses dispositivos.

- D-bus cria eventos para iniciar processos automáticos.

- PolicyKit disponibiliza os privilégios necessários.

| Dica
Os aparelhos auto-montados podem ter a opção de montagem "`uhelper=`" que é utilizada por umount(8).

| Dica
A auto-montagem em ambientes de trabalho modernos apenas acontece quando esses aparelhos amovíveis não estão listados em "`/etc/fstab`".

O ponto de montagem no ambiente de trabalho moderno é escolhido como "`/media/nome-utilizador/etiqueta-disco`" que pode ser personalizado da seguinte forma.

- mlabel(1) para o sistema de ficheiros FAT

- genisoimage(1) com a opção "`-V`" para o sistema de ficheiros ISO9660

- tune2fs(1) com a opção "`-L`" para sistemas de ficheiros ext2/ext3/ext4

| Dica
A escolha de codificação pode necessitar de ser disponibilizada como opção de montagem (veja Seção 8.1.3, “Codificação de nomes de ficheiros”).

| Dica
A utilização do menu da GUI para desmontar um sistema de ficheiros pode remover o nó de aparelho dele gerado dinamicamente tal como "`/dev/sdc`". Se desejar manter o nó de aparelho dele, desmonte-o com o comando umount(8) na linha de comandos da shell.

### 10.1.8. Escolha de sistema de ficheiros para partilhar dados

Quando partilha dados com outros sistemas via aparelhos de armazenamento amovível, deve formatá-lo num sistema de ficheiros comum que seja suportado pelos dois sistemas. Aqui está uma lista de escolhas de sistemas de ficheiros.

| Nota
Declarações sobre disco rijo (HDD) são aplicáveis a outros dispositivos de armazenamento tais como SSD / Pen flash USB / Cartão de memória / ... . Substitua os nomes dos dispositivos nos exemplos como `/dev/sda` com nomes de dispositivos apropriados `/dev/nvme0`, `/dev/mmcblk0`, ... .

Tabela 10.3. Lista de hipóteses de sistemas de ficheiros para aparelhos de armazenamento amovíveis com cenários de utilização típica

nome do sistema de ficheiros | cenário de utilização típico
--- | ---
FAT12 | partilha de dados em várias plataformas em disquetes (<32MiB)
FAT16 | partilha de dados em várias plataformas em aparelhos como pequenos discos rígidos (<2GiB)
FAT32 | partilha de dados em várias plataformas em aparelhos como grandes discos rígidos (<8TiB, suportado por mais recente que MS Windows95 OSR2)
exFAT | partilha de dados entre plataformas no dispositivo semelhante a um disco rígido de grandes dimensões (<512TiB, suportado pelo WindowsXP, Mac OS X Snow Leopard 10.6.5 e kernel Linux desde a versão 5.4)
NTFS | partilha de dados em várias plataformas em aparelhos como grandes discos rígidos (suportado nativamente no MS Windows NT e versões posteriores e suportado pelo NTFS-3G via FUSE em Linux)
ISO9660 | partilha de dados estáticos em várias plataformas em CD-R e DVD+/-R
UDF | escrita de dados incremental em CD-R e DVD+/-R (novo)
MINIX | armazenamento de dados em ficheiros unix eficiente em espaço em disquetes
ext2 | partilha de dados em aparelhos tipo disco rígido com sistemas Linux mais antigos
ext3 | partilha de dados em aparelhos tipo disco rígido com sistemas Linux mais antigos
ext4 | partilha de dados em aparelhos de tipo disco rígido com sistemas Linux atuais
btrfs | partilha de dados em dispositivos de tipo disco rígido com sistemas Linux atuais com instantâneos só de leitura

| Dica
Veja Seção 9.9.1, “Encriptação de discos amovíveis com dm-crypt/LUKS” para partilha de dados em várias plataformas a usar encriptação ao nível do aparelho.

O sistema de ficheiros FAT é suportado pela maioria dos sistemas operativos modernos e é bastante útil para objetivos de trocas de dados via aparelhos tipo disco rígido.

Quando formatar aparelhos tipo disco rígido amovíveis para partilha de dados em multi-plataformas com o sistema de ficheiros FAT, as seguintes deverão ser escolhas seguras.

- Particioná-los com o fdisk(8), cfdisk(8) ou parted(8) (veja Seção 9.6.2, “Configuração das partições do disco”) numa única partição primária e marcá-la como a seguir.

  - Tipo "6" para FAT16 para médias inferiores a 2GB.

  - Tipo "c" para FAT32 (LBA) para médias maiores.

- Formatar a partição primária com o mkfs.vfat(8) com o seguinte.

  - Apenas o nome de aparelho dele, ex. "`/dev/sda1`" para FAT16

  - A opção explícita e o nome de aparelho dela, ex. "`-F 32 /dev/sda1`" para FAT32

Quando se usa sistemas de ficheiros FAT ou ISO9660 para partilhar dados, as considerações de segurança deverão ser as seguintes.

- Arquivar ficheiros para um ficheiro de arquivo primeiro a utilizar o tar(1), ou cpio(1) para reter o nome longo do ficheiro, a ligação simbólica, as permissões originais de ficheiro Unix e a informação do dono.

- Dividir o ficheiro de arquivo em fatias com menos de 2 GiB com o comando split(1) para o proteger contra limites de tamanho de ficheiro.

- Encriptar o ficheiro de arquivo para segurar o conteúdo dele contra acesso não autorizado.

| Nota
Para o sistema de ficheiros FAT pelo seu desenho, o tamanho máximo de ficheiro é `(2^32 - 1) bytes = (4GiB - 1 byte)`. Para algumas aplicações do antigo SO de 32 bits, o tamanho máximo de ficheiro é mais pequeno `(2^31 - 1) bytes = (2GiB - 1 byte)`. O Debian não sofre do segundo problema.

| Nota
A própria Microsoft não recomenda o uso de FAT para discos ou partições maiores que 200 MB. A Microsoft destaca as suas deficiências como a ser a utilização ineficiente do espaço do disco na "Visão geral dos sistemas de ficheiros FAT, HPFS e NTFS" dele. Claro que devemos normalmente usar o sistema de ficheiros ext4 para Linux.

| Dica
Para mais sistemas de ficheiros e acesso a sistemas de ficheiros, por favor leia "HOWTO dos Sistemas de Ficheiros".

### 10.1.9. Partilhar dados via a rede

Quando se partilha dados com outro sistema via rede, deve usar serviços comuns. Aqui estão algumas dicas.

Tabela 10.4. Lista de serviços de rede para escolher com o cenário de utilização típico

serviço de rede | descrição do cenário de utilização típico
--- | ---
SMB/CIFS sistema de ficheiros montado em rede com o Samba | partilha ficheiros via "Rede Microsoft Windows", veja smb.conf(5) e O HOWTO Oficial do Samba 3.x.x e Guia de Referência ou o pacote `samba-doc`
NFS sistema de ficheiros montado em rede com o kernel do Linux | partilhar ficheiros via "Rede Unix/Linux", veja exports(5) e Linux NFS-HOWTO
serviço HTTP | a partilhar ficheiros entre o servidor/cliente web
serviço HTTPS | partilhar ficheiros entre o servidor/cliente web com Secure Sockets Layer encriptado (SSL) ou Transport Layer Security (TLS)
serviço FTP | a partilhar ficheiros entre o servidor/cliente FTP

Apesar de estes sistemas de ficheiros montados sobre rede e métodos de transferência de ficheiros em rede serem bastante convenientes para partilhar dados, estes podem ser inseguros. A ligação de rede deles tem de ser segurada com o seguinte.

- Encriptar com SSL/TLS

- Ligue-o em túnel via SSH

- Ligue-o em túnel via VPN

- Limitar por detrás da firewall segura

Veja também Seção 6.5, “Outras aplicações de servidor de rede” e Seção 6.6, “Outros clientes de aplicação de rede”.

## 10.2. Salvaguarda (backup) e recuperação

Todos sabemos que os computadores avariam ou que erros humanos causam danos no sistema e nos dados. As operações de salvaguarda e recuperação são a parte essencial sucesso do administrador de sistemas. Todos os modos de falha possíveis irão atingi-lo um dia.

| Dica
Mantenha o seu sistema de backup simples e faça backups periódicos. Ter cópias de segurança dos dados é mais importante do que quão bom é tecnicamente o seu método de backup.

### 10.2.1. Política de cópia de segurança e recuperação

Existem 3 factores chave que determinam a política atual de salvaguarda e recuperação.

1. Saber o que salvaguardar e recuperar.

   - Ficheiros de dados criados directamente por si: dados em "`~/`"

   - Ficheiros de dados criados por aplicações usadas por si: dados em "`/var/`" (excepto "`/var/cache/`", "`/var/run/`" e "`/var/tmp/`")

   - Ficheiros de configuração do sistema: dados em "`/etc/`"

   - Programas locais: dados em "`/usr/local/`" ou "`/opt/`"

   - Informação da instalação do sistema: um memo em texto simples em passos chave (partição, ...)

   - Conjunto de dados de prova: confirmado com antecedência por operações de recuperação experimentais

     - Tarefa cron como um processo de utilizador: ficheiros no diretório "`/var/spool/cron/crontabs`" e reiniciar o cron(8). Veja Seção 9.4.14, “Agendar tarefas regularmente” para cron(8) e crontab(1).

     - Tarefas de temporizador do Systemd como processos de utilizador: ficheiros no diretório "`~/.config/systemd/user`". Veja systemd.timer(5) e systemd.service(5).

     - Trabalhos de arranque automático como processos do utilizador: ficheiros no diretório "`~/.config/autostart`". Consulte Especificação de Início Automático de Aplicações de Ambiente de Trabalho.

2. Saber como salvaguardar e recuperar.

   - Armazenamento de dados seguro: protecção contra reescrita e falha do sistema

   - Salvaguarda frequente: salvaguarda agendada

   - Backup redundante: usar mirror de dados

   - Processo à prova de tolos: backup fácil de comando único

3. Avaliar os riscos e custos envolvidos.

   - Risco de perda de dados

     - Os dados devem estar, pelo menos, em partições de disco diferentes, de preferência em discos e máquinas diferentes, para resistir à corrupção do sistema de ficheiros. É preferível armazenar os dados importantes num sistema de ficheiros só de leitura. [4]

   - Risco de violação de dados

     - Dados de identidade sensíveis, como "`/etc/ssh/ssh_host_*_key`", "`~/.gnupg/*`", "`~/.ssh/*`", "`~/.local/share/keyrings/*`", "`/etc/passwd`", "`/etc/shadow`", "`popularity-contest.conf`", "`/etc/ppp/pap-secrets`", e "`/etc/exim4/passwd.client`" devem ser copiados como encriptados. [5] (Ver Seção 9.9, “Dicas de encriptação de dados”.)

     - Nunca codifique a palavra-passe de início de sessão do sistema nem a frase-passe de desencriptação em qualquer script, mesmo em qualquer sistema fiável. (Ver Seção 10.3.6, “Gestor de palavras-passe”.)

   - Modo de falha e a possibilidade dele

     - O hardware (especialmente o disco rígido) avaria-se

     - O sistema de ficheiros pode estar corrompido e os dados nele contidos podem perder-se

     - O sistema de armazenamento remoto não é fiável em termos de violações de segurança

     - Uma proteção por palavra-passe fraca pode ser facilmente comprometida

     - O sistema de permissão de ficheiros pode estar comprometido

   - Recursos necessários para o backup: humano, hardware, software,…

     - Cópia de segurança automática agendada com a tarefa cron ou a tarefa de temporizador systemd

| Dica
Pode recuperar dados configuração debconf com "`debconf-set-selections debconf-selections`" e dados de seleção do dpkg com "`dpkg --set-selection <dpkg-selections.list`".

| Nota
Não faça salvaguarda aos conteúdos dos pseudo-sistemas de ficheiros encontrados em `/proc`, `/sys`, `/tmp` e `/run` (veja Seção 1.2.12, “procfs e sysfs” e Seção 1.2.13, “tmpfs”). A menos que saiba exatamente o que está a fazer, eles são enormes quantidades de dados desnecessários.

| Nota
Pode desejar parar alguns daemons de aplicação como o MTA (veja Seção 6.2.4, “Agente de transporte de mail (MTA)”) enquanto faz cópias de segurança (backups) dos dados.

### 10.2.2. Suites de utilitários de backup

Aqui está uma lista selcionada de suites de utilitários de backup notáveis disponíveis no sistema Debian.

Tabela 10.5. Lista de suites utilitárias de salvaguarda

pacote | popcon | tamanho | descrição
--- | --- | --- | ---
`bacula-common` | V:6.3, I:7.1 | 2501 | Bacula: salvaguarda, recuperação e verificação em rede - ficheiros de suporte comum
`bacula-client` | V:0.3, I:1.8 | 199 | Bacula: salvaguarda, recuperação e verificação em rede - meta-pacote cliente
`bacula-console` | V:0.6, I:2.1 | 112 | Bacula: salvaguarda, recuperação e verificação em rede - consola de texto
`bacula-server` | I:0.61 | 199 | Bacula: salvaguarda, recuperação e verificação em rede - meta-pacote servidor
`amanda-common` | V:0.6, I:2.2 | 9851 | Amanda: Advanced Maryland Automatic Network Disk Archiver (Bibliotecas)
`amanda-client` | V:0.6, I:2.2 | 1099 | Amanda: Advanced Maryland Automatic Network Disk Archiver (Cliente)
`amanda-server` | V:0.12, I:0.22 | 1093 | Amanda: Advanced Maryland Automatic Network Disk Archiver (Servidor)
`backuppc` | V:1.4, I:1.7 | 3088 | BackupPC é um sistema de grau empresarial de alta performance para fazer salvaguardas a PCs (baseado em disco)
`duplicity` | V:5, I:46 | 2679 | salvaguarda incremental (remoto)
`deja-dup` | V:28, I:42 | 5274 | Interface gráfica para duplicidade
`borgbackup` | V:13, I:28 | 3532 | Cópia de segurança com desduplicação (remota)
`borgmatic` | V:3.2, I:4.5 | 946 | auxiliar borgbackup
`rdiff-backup` | V:2.2, I:6.5 | 1207 | salvaguarda incremental (remoto)
`restic` | V:7, I:14 | 41617 | salvaguarda incremental (remoto)
`backupninja` | V:2.1, I:2.6 | 360 | sistema de meta-backup leve e extensível
`slbackup` | V:0.09, I:0.12 | 147 | salvaguarda incremental (remoto)
`backup-manager` | V:0.43, I:0.75 | 573 | ferramenta de salvaguarda de linha de comandos
`backup2l` | V:0.34, I:0.47 | 110 | ferramenta de baixa manutenção para salvaguarda/restauro para medias montáveis (baseado em disco)

As ferramentas de salvaguarda têm os seus objetivos especializados.

- Mondo Rescue é um sistema de backup para facilitar o restauro de um sistema completo rapidamente a partir de CD/DVD, etc de backup, sem se passar por todo o processo normal de instalação do sistema.

- Bacula, Amanda e BackupPC são suites utilitárias de salvaguarda cheias de funcionalidades que se destinam a salvaguardas regulares em rede.

- Duplicity, e Borg são utilitários de backup mais simples para estações de trabalho típicas.

### 10.2.3. Sugestões de cópia de segurança

Para uma estação de trabalho pessoal, os utilitários de backup completos concebidos para o ambiente de servidor podem não ser úteis. Ao mesmo tempo, os utilitários de backup existentes para estações de trabalho podem ter algumas deficiências.

Seguem-se algumas sugestões para facilitar a cópia de segurança com o mínimo de esforço do utilizador. Estas técnicas podem ser utilizadas com qualquer utilitário de cópia de segurança.

Para fins de demonstração, vamos assumir que o utilizador principal e o nome do grupo são `pinguim` e criar um exemplo de script de cópia de segurança e instantâneo "`/usr/local/bin/bkss.sh`" como:

    #!/bin/sh -e
    SRC="$1" # source data path
    DSTFS="$2" # backup destination filesystem path
    DSTSV="$3" # backup destination subvolume name
    DSTSS="${DSTFS}/${DSTSV}-snapshot" # snapshot destination path
    if [ "$(stat -f -c %T "$DSTFS")" != "btrfs" ]; then
      echo "E: $DESTFS needs to be formatted to btrfs" >&2 ; exit 1
    fi
    MSGID=$(notify-send -p "bkup.sh $DSTSV" "in progress ...")
    if [ ! -d "$DSTFS/$DSTSV" ]; then
      btrfs subvolume create "$DSTFS/$DSTSV"
      mkdir -p "$DSTSS"
    fi
    rsync -aHxS --delete --mkpath "${SRC}/" "${DSTFS}/${DSTSV}"
    btrfs subvolume snapshot -r "${DSTFS}/${DSTSV}" ${DSTSS}/$(date -u --iso=min)
    notify-send -r "$MSGID" "bkup.sh $DSTSV" "finished!"

Aqui, apenas a ferramenta básica rsync(1) é utilizada para facilitar a cópia de segurança do sistema e o espaço de armazenamento é utilizado de forma eficiente pelo Btrfs.

| Dica
Para sua informação: Este autor utiliza o seu próprio script de shell semelhante "bss: Btrfs Subvolume Snapshot Utility" para a sua estação de trabalho.

#### 10.2.3.1. Cópia de segurança GUI

Aqui está um exemplo para configurar a cópia de segurança de um único clique da GUI.

- Preparar um dispositivo de armazenamento USB para ser utilizado como cópia de segurança.

  - Formate um dispositivo de armazenamento USB com uma partição em btrfs com o seu nome de etiqueta como "`BKUP`". Isto pode ser encriptado (ver Seção 9.9.1, “Encriptação de discos amovíveis com dm-crypt/LUKS”).

  - Ligue-o ao seu sistema. O sistema da área de trabalho deve montá-lo automaticamente como "`/media/penguin/BKUP`".

  - Execute "`sudo chown penguin:penguin /media/penguin/BKUP`" para que o utilizador possa escrever nele.

- Crie "`~/.local/share/applications/BKUP.desktop`" seguindo as técnicas escritas Seção 9.4.10, “Arrancar um programa a partir da GUI” como:

      [Desktop Entry]
      Name=bkss
      Comment=Backup and snapshot of ~/Documents
      Exec=/usr/local/bin/bkss.sh /home/penguin/Documents /media/penguin/BKUP Documents
      Type=Application

Para cada clique na GUI, é feita uma cópia de segurança dos seus dados de "`~/Documents`" para um dispositivo de armazenamento USB e é criada uma imagem só de leitura.

#### 10.2.3.2. Cópia de segurança acionada por evento de montagem

Eis um exemplo de configuração para a cópia de segurança automática acionada pelo evento de montagem.

- Prepare um dispositivo de armazenamento USB para ser utilizado para a cópia de segurança, como em Seção 10.2.3.1, “Cópia de segurança GUI”.

- Crie um ficheiro de unidade de serviço systemd "`~/.config/systemd/user/back-BKUP.service`" como:

      [Unit]
      Description=USB Disk backup
      Requires=media-%u-BKUP.mount
      After=media-%u-BKUP.mount

      [Service]
      ExecStart=/usr/local/bin/bkss.sh %h/Documents /media/%u/BKUP Documents
      StandardOutput=append:%h/.cache/systemd-snap.log
      StandardError=append:%h/.cache/systemd-snap.log

      [Install]
      WantedBy=media-%u-BKUP.mount

- Ativar esta configuração da unidade systemd com o seguinte:

       $ systemctl --user enable bkup-BKUP.service

Para cada evento de montagem, é feita uma cópia de segurança dos seus dados de "`~/Documents`" para um dispositivo de armazenamento USB e é criada uma imagem só de leitura.

Aqui, os nomes das unidades montadas systemd, que o systemd tem atualmente em memória podem ser pedidos ao gestor de serviços do utilizador que os chama com "`systemctl --user list-units --type=mount`".

#### 10.2.3.3. Cópia de segurança acionada por um evento de temporizador

Eis um exemplo de configuração da cópia de segurança automática acionada pelo evento do temporizador.

- Prepare um dispositivo de armazenamento USB para ser utilizado para a cópia de segurança, como em Seção 10.2.3.1, “Cópia de segurança GUI”.

- Crie um ficheiro systemd de unidade temporizadora "`~/.config/systemd/user/snap-Documents.timer`" como:

      [Unit]
      Description=Run btrfs subvolume snapshot on timer
      Documentation=man:btrfs(1)

      [Timer]
      OnStartupSec=30
      OnUnitInactiveSec=900

      [Install]
      WantedBy=timers.target

- Crie um ficheiro systemd de unidade de serviço `"~/.config/systemd/user/snap-Documents.service`" como:

      [Unit]
      Description=Run btrfs subvolume snapshot
      Documentation=man:btrfs(1)

      [Service]
      Type=oneshot
      Nice=15
      ExecStart=/usr/local/bin/bkss.sh %h/Documents /media/%u/BKUP Documents
      IOSchedulingClass=idle
      CPUSchedulingPolicy=idle
      StandardOutput=append:%h/.cache/systemd-snap.log
      StandardError=append:%h/.cache/systemd-snap.log

- Ativar esta configuração da unidade systemd com o seguinte:

       $ systemctl --user enable snap-Documents.timer

Para cada evento do temporizador, é feita uma cópia de segurança dos seus dados de "`~/Documents`" para um dispositivo de armazenamento USB e é criada uma imagem só de leitura.

Aqui, os nomes das unidades temporizadoras de utilizador do systemd, que o systemd tem atualmente em memória podem ser perguntados ao gestor de serviços do utilizador que os chama com "`systemctl --user list-units --type=timer`".

Para o sistema de área de trabalho moderna, esta abordagem do systemd pode oferecer um controlo mais fino do que os tradicionais sistemas Unix que utilizam at(1), cron(8), ou anacron(8).

## 10.3. Infraestrutura da segurança de dados

A infraestrutura de segurança dos dados é disponibilizada pela combinação de uma ferramenta de encriptação de dados, ferramenta de resumo de mensagens e ferramenta de assinaturas.

Tabela 10.6. Lista de ferramentas de infraestrutura da segurança de dados

pacote | popcon | tamanho | comando | descrição
--- | --- | --- | --- | ---
`gnupg` | V:406, I:864 | 465 | gpg(1) | GNU Privacy Guard - ferramenta de encriptação e assinatura OpenPGP
`gpgv` | V:219, I:932 | 577 | gpgv(1) | GNU Privacy Guard - ferramenta de verificação de assinaturas OpenPGP
`sq` | V:1, I:30 | 23926 | sq(1) | Sequoia-PGP - ferramenta de encriptação e assinatura OpenPGP
`sqv` | V:443, I:518 | 1855 | sqv(1) | Sequoia-PGP - ferramenta de verificação de assinaturas OpenPGP
`paperkey` | V:1, I:11 | 58 | paperkey(1) | extrai apenas a informação secreta de chaves secretas OpenPGP
`cryptsetup` | V:35, I:80 | 465 | cryptsetup(8), … | utilitários para encriptação de dispositivos de bloco dm-crypt com suporte de LUKS
`coreutils` | V:910, I:1000 | 17994 | md5sum(1) | computa e verifica o resumo da mensagem MD5
`coreutils` | V:910, I:1000 | 17994 | sha1sum(1) | computa e verifica o resumo da mensagem SHA1
`openssl` | V:855, I:997 | 2532 | `openssl`(1ssl) | computa o resumo da mensagem com "`openssl dgst`" (OpenSSL)
`libsecret-tools` | V:1, I:12 | 45 | secret-tool(1) | guardar e recuperar palavras-passe (CLI)
`seahorse` | V:73, I:258 | 7999 | seahorse(1) | ferramenta de gestão de chaves (GNOME)

Veja Seção 9.9, “Dicas de encriptação de dados” em dm-crypt e fscrypt os quais implementam infraestruturas de encriptação de dados automática via módulos do kernel Linux.

### 10.3.1. Gestão de chaves para GnuPG

Aqui estão comandos do GNU Privacy Guard para gestão de chaves básica.

Tabela 10.7. Lista de comandos do GNU Privacy Guard para gestão de chaves

comando | descrição
--- | ---
`gpg --gen-key` | gerar uma chave nova
`gpg --gen-revoke my_user_ID` | gera chave de revogação para meu_ID_utilizador
`gpg --edit-key user_ID` | edita chave interativamente, "help" para ajuda
`gpg -o file --export` | exporta todas as chaves públicas para ficheiro
`gpg -o file --export-secret-keys` | exporta todas as chaves privadas para ficheiro
`gpg --import file` | importa todas as chaves de ficheiro
`gpg --send-keys user_ID` | envia chave de ID_utilizador para servidor de chaves
`gpg --recv-keys user_ID` | recupera chave de ID_utilizador do servidor de chaves
`gpg --list-keys user_ID` | lista chaves de ID_utilizador
`gpg --list-sigs user_ID` | lista assinaturas de ID_utilizador
`gpg --check-sigs user_ID` | verifica assinaturas de ID_utilizador
`gpg --fingerprint user_ID` | verifica a impressão digital de ID_utilizador
`gpg --refresh-keys` | atualiza o chaveiro local

Aqui está o significado do código de confiança.

Tabela 10.8. Lista do significado do código de confiança

código | descrição de confiança
--- | ---
`-` | nenhuma confiança de dono atribuída / ainda não calculado
`e` | falha no cálculo da confiança
`q` | não existe informação suficiente para o cálculo
`n` | nunca confiar nesta chave
`m` | marginalmente confiável
`f` | totalmente confiável
`u` | de confiança absoluta

O seguinte gera a minha chave "`9563FC29932C409F1A77F9C1AB8A1522D8234C6A`".

    $ gpg --gen-key
    gpg (GnuPG) 2.4.7; Copyright (C) 2024 g10 Code GmbH
    ...
    GnuPG needs to construct a user ID to identify your key.

    Real name: Osamu Aoki
    Email address: osamu@debian.org
    You selected this USER-ID:
        "Osamu Aoki <osamu@debian.org>"

    Change (N)ame, (E)mail, or (O)kay/(Q)uit? o
    ...
    public and secret key created and signed.

    pub   ed25519 2026-02-14 [SC] [expires: 2029-02-13]
          9563FC29932C409F1A77F9C1AB8A1522D8234C6A
    uid                      Osamu Aoki <osamu@debian.org>
    sub   cv25519 2026-02-14 [E] [expires: 2029-02-13]

O seguinte envia a minha chave "`9563FC29932C409F1A77F9C1AB8A1522D8234C6A`" para o popular servidor de chaves "`hkp://keys.gnupg.net`".

    $ gpg --keyserver hkp://keys.gnupg.net --send-keys 9563FC29932C409F1A77F9C1AB8A1522D8234C6A

Um bom servidor de chaves predefinido configurado em "`~/.gnupg/gpg.conf`" (ou na antiga localização "`~/.gnupg/options`") contém o seguinte.

    keyserver hkp://keys.gnupg.net

O seguinte obtém chaves desconhecidas do servidor de chaves.

    $ gpg --list-sigs --with-colons | grep '^sig.*\[User ID not found\]' |\
              cut -d ':' -f 5| sort | uniq | xargs gpg --recv-keys

Existiu um bug no OpenPGP Public Key Server (versão anterior a 0.9.6) que corrompeu as chaves com mais de 2 sub-chaves. O novo pacote `gnupg` (>1.2.1-2) consegue lidar com estas chaves corrompidas. Veja gpg(1) sob a opção "`--repair-pks-subkey-bug`".

O uso de SHA-1 para hash foi descontinuado. Se a sua chave OpenPGP antiga baseada em RSA usa SHA-1 para hash, correja-a usando FixKeyWithSha1.

| Dica
Os comandos sq(1) e sqv(1) são um conjunto alternativo de comandos openPGP. Veja documentação do utilizador do sq e Uma Introdução Prática para Usar sq, CLI do Sequoia PGP.

### 10.3.2. Usa GnuPG em ficheiros

Aqui estão exemplos para usar comandos do GNU Privacy Guard em ficheiros.

Tabela 10.9. Lista de comandos do GNU Privacy Guard em ficheiros

comando | descrição
--- | ---
`gpg -a -s file` | assina ficheiro em ficheiro.asc blindado de ASCII
`gpg --armor --sign file` | , ,
`gpg --clearsign file` | mensagem com assinatura clara
`gpg --clearsign file|mail foo@example.org` | envia por mail uma mensagem com assinatura clara para `foo@example.org`
`gpg --clearsign --not-dash-escaped patchfile` | ficheiro patch com assinatura clara
`gpg --verify file` | verifica ficheiro com assinatura clara
`gpg -o file.sig -b file` | cria assinatura separada
`gpg -o file.sig --detach-sign file` | , ,
`gpg --verify file.sig file` | verifica ficheiro com file.sig
`gpg -o crypt_file.gpg -r name -e file` | encriptação de chave pública destinada a nome a partir de ficheiro para crypt_file.gpg binário
`gpg -o crypt_file.gpg --recipient name --encrypt file` | , ,
`gpg -o crypt_file.asc -a -r name -e file` | encriptação de chave pública destinada a nome a partir de ficheiro para crypt_file.asc blindado de ASCII
`gpg -o crypt_file.gpg -c file` | encriptação simétrica a partir de ficheiro para crypt_file.gpg
`gpg -o crypt_file.gpg --symmetric file` | , ,
`gpg -o crypt_file.asc -a -c file` | encriptação simétrica destinada a nome a partir de ficheiro para crypt_file.asc blindado de ASCII
`gpg -o file -d crypt_file.gpg -r name` | desencriptação
`gpg -o file --decrypt crypt_file.gpg` | , ,

### 10.3.3. Usar GnuPG com o Mutt

Adicione o seguinte a "`~/.muttrc`" para impedir o GnuPG lento de arrancar automaticamente, enquanto permite que seja usado ao escrever "`S`" no menu de índice.

    macro index S ":toggle pgp_verify_sig\n"
    set pgp_verify_sig=no

### 10.3.4. Usar GnuPG com o Vim

O plugin `gnupg` permite correr GnuPG de forma transparente para ficheiros com extensão "`.gpg`", "`.asc`" e "`.pgp`".[6]

    $ sudo aptitude install vim-scripts
    $ echo "packadd! gnupg" >> ~/.vim/vimrc

### 10.3.5. O valor de controlo MD5

O md5sum(1) disponibiliza um utilitário para fazer um ficheiro de sumário a usar o método em rfc1321 e verificar cada ficheiro com ele.

    $ md5sum foo bar >baz.md5
    $ cat baz.md5
    d3b07384d113edec49eaa6238ad5ff00  foo
    c157a79031e1c40f85931829bc5fc552  bar
    $ md5sum -c baz.md5
    foo: OK
    bar: OK

| Nota
O cálculo do sumário MD5 é menos intensivo para a CPU que o da assinatura criptográfica do GNU Privacy Guard (GnuPG). Normalmente, apenas o ficheiro de digestão do nível de topo é assinado criptograficamente para assegurar a integridade dos dados.

### 10.3.6. Gestor de palavras-passe

No sistema GNOME, a ferramenta GUI seahorse(1) gere as palavras-passe e guarda-as de forma segura no chaveiro `~/.local/share/keyrings/*`.

secret-tool(1) pode armazenar a palavra-passe no chaveiro a partir da linha de comandos.

Vamos armazenar a frase-chave utilizada para a imagem de disco encriptada LUKS/dm-crypt

    $ secret-tool store --label='LUKS passphrase for disk.img' LUKS my_disk.img
    Password: ********

Esta palavra-passe armazenada pode ser recuperada e fornecida a outros programas, por exemplo, cryptsetup(8).

    $ secret-tool lookup LUKS my_disk.img | \
      cryptsetup open disk.img disk_img --type luks --keyring -
    $ sudo mount /dev/mapper/disk_img /mnt

| Dica
Sempre que precisar de fornecer uma palavra-passe num script, utilize a `ferramenta secreta` e evite codificar diretamente a palavra-passe no script.

## 10.4. Ferramentas de fusão de código fonte

Existem muitas ferramentas de fusão para código fonte. Os seguinte comandos chamaram a minha atenção.

Tabela 10.10. Lista de ferramentas de fusão de código fonte

pacote | popcon | tamanho | comando | descrição
--- | --- | --- | --- | ---
`patch` | V:107, I:729 | 242 | patch(1) | aplica ficheiro diff a um original
`vim` | V:81, I:342 | 4164 | vimdiff(1) | compara dois ficheiros lado a lado no vim
`imediff` | V:0.02, I:0.28 | 329 | imediff(1) | ferramenta de fusão de 2 ou 3 vias interactiva de écran completo
`meld` | V:5, I:24 | 3992 | meld(1) | compara e funde ficheiros (GTK)
`wiggle` | V:0.02, I:0.14 | 175 | wiggle(1) | aplica patches rejeitadas
`diffutils` | V:895, I:998 | 1768 | diff(1) | compara ficheiros linha a linha
`diffutils` | V:895, I:998 | 1768 | diff3(1) | compara e junta três ficheiros linha a linha
`quilt` | V:2, I:18 | 880 | quilt(1) | gere séries de patches
`wdiff` | V:6, I:40 | 651 | wdiff(1) | mostra diferenças de palavras entre ficheiros de texto
`diffstat` | V:9, I:97 | 79 | diffstat(1) | produz um histograma de alterações feitas pelo diff
`patchutils` | V:12, I:96 | 269 | combinediff(1) | cria uma patch cumulativa de duas patches incrementais
`patchutils` | V:12, I:96 | 269 | dehtmldiff(1) | extrai um diff de uma página HTML
`patchutils` | V:12, I:96 | 269 | filterdiff(1) | extrai ou executa diffs de um ficheiro diff
`patchutils` | V:12, I:96 | 269 | fixcvsdiff(1) | corrige ficheiros diff criados pelo CVS que o patch(1) interpreta mal
`patchutils` | V:12, I:96 | 269 | flipdiff(1) | troca a ordem de duas patches
`patchutils` | V:12, I:96 | 269 | grepdiff(1) | mostra que ficheiros são modificados por uma patch que corresponde a um regex
`patchutils` | V:12, I:96 | 269 | interdiff(1) | mostra as diferenças entre dois ficheiros diff unificados
`patchutils` | V:12, I:96 | 269 | lsdiff(1) | mostra quais ficheiros são modificados por uma patch
`patchutils` | V:12, I:96 | 269 | recountdiff(1) | recalcula contagens e offsets em diffs de contexto unificado
`patchutils` | V:12, I:96 | 269 | rediff(1) | corrige os offsets e as contagens de um diff editado manualmente
`patchutils` | V:12, I:96 | 269 | splitdiff(1) | separa patches incrementais
`patchutils` | V:12, I:96 | 269 | unwrapdiff(1) | desembaralha patches cujas linhas foram alteradas para arrumação de palavras
`dirdiff` | V:0.1, I:1.4 | 167 | dirdiff(1) | mostra diferenças e funde alterações entre árvores de diretórios
`docdiff` | V:0.02, I:0.19 | 554 | docdiff(1) | compara dois ficheiros palavra a palavra / caractere a caractere
`makepatch` | V:0.01, I:0.16 | 99 | makepatch(1) | gera ficheiros de patch extensos
`makepatch` | V:0.01, I:0.16 | 99 | applypatch(1) | aplica ficheiros de patch extensos

### 10.4.1. Extrair as diferenças para ficheiros fonte

Os seguintes procedimentos extraem as diferenças entre dois ficheiros de fonte e cria os ficheiros diff unificados "`file.patch0`" ou "`file.patch1`" a depender da localização do ficheiro.

    $ diff -u file.old file.new > file.patch0
    $ diff -u old/file new/file > file.patch1

### 10.4.2. Fundir atualizações para ficheiros de fonte

O ficheiro diff (alternativamente chamado ficheiro patch) é usado para enviar uma atualização de um programa. A parte receptora aplica esta atualização a outro ficheiro com o seguinte.

    $ patch -p0 file < file.patch0
    $ patch -p1 file < file.patch1

### 10.4.3. Integração interativa

Se tiver duas versões de um código fonte, pode executar uma fusão-de-2-vias efetiva a usar o imediff(1) com o seguinte.

    $ imediff -o file.merged file.old file.new

Se tiver três versões de um código fonte, pode executar uma fusão de 3-vias efetiva ao usar o imediff(1) com o seguinte.

    $ imediff -o file.merged file.yours file.base file.theirs

## 10.5. Git

Atualmente, o Git é a ferramenta de eleição para o sistema de controlo de versões (VCS), uma vez que o Git pode fazer tudo para a gestão local e remota do código-fonte.

O Debian disponibiliza serviços Git livres via Serviço Debian Salsa.. A sua documentação encontra-se em https://wiki.debian.org/Salsa .

Aqui estão alguns pacotes relacionados com o Git.

Tabela 10.11. Lista de pacotes e comandos relacionados com o git

pacote | popcon | tamanho | comando | descrição
--- | --- | --- | --- | ---
`git` | V:409, I:623 | 52512 | git(7) | Git, o sistema de controlo de revisão distribuído, rápido e escalável
`gitk` | V:4, I:26 | 2045 | gitk(1) | explorador GUI de repositórios Git com histórico
`qgit` | V:0.2, I:2.0 | 1431 | qgit(1) | explorador GUI de repositórios Git com histórico
`git-cola` | V:0.6, I:3.4 | 5129 | git-cola(1) | explorador GUI de repositórios Git com histórico
`tig` | V:2, I:11 | 1245 | tig(1) | explorador de repositórios Git de consola com histórico
`lazygit` | V:0.9, I:4.0 | 24167 | lazygit(1) | explorador de repositórios Git de consola com histórico
`git-gui` | V:2, I:16 | 2549 | git-gui(1) | GUI para Git (Nenhum histórico)
`git-email` | V:0.4, I:9.9 | 1229 | git-send-email(1) | envia uma colecção de patches como email a partir do Git
`git-buildpackage` | V:1.2, I:7.2 | 2027 | git-buildpackage(1) | automatiza o empacotamento Debian com o Git
`dgit` | V:0.1, I:1.0 | 755 | dgit(1) | interoperabilidade do git com o repositório Debian
`imediff` | V:0.02, I:0.28 | 329 | git-ime(1) | ferramenta auxiliar interativa de divisão de commits do git
`stgit` | V:0.07, I:0.49 | 6177 | stg(1) | quilt no topo do git (Python)
`git-doc` | I:11 | 15192 | N/D | documentação oficial para o Git
`gitmagic` | I:0.56 | 721 | N/D | "Magia do Git", guia fácil de compreender para o Git

### 10.5.1. Configuração do cliente Git

Pode desejar definir várias configurações globais em "`~/.gitconfig`" como o seu nome e endereço de mail usado pelo Git com o seguinte.

    $ git config --global user.name "Name Surname"
    $ git config --global user.email yourname@example.com

Também pode personalizar o comportamento predefinido do Git da seguinte forma.

    $ git config --global init.defaultBranch main
    $ git config --global pull.rebase true
    $ git config --global push.default current

Se está muito acostumado aos comandos do CVS ou Subversion, pode desejar definir nomes alternativos a vários comandos com o seguinte.

    $ git config --global alias.ci "commit -a"
    $ git config --global alias.co checkout

Pode verificar a sua configuração global com o seguinte.

    $ git config --global --list

### 10.5.2. Comandos básicos do Git

A operação Git envolve vários dados.

- A árvore de trabalho que contém os ficheiros que o utilizador enfrenta e nos quais faz alterações.

  - As alterações a serem registadas devem ser explicitamente selecionadas e colocadas no índice. Estes são os comandos `git add` e `git rm`.

- O índice que contém os ficheiros preparados.

  - Os ficheiros preparados serão confirmados para o repositório local após o pedido subsequente. Este é o comando `git commit`.

- O repositório local que contém os ficheiros confirmados.

  - O Git regista o histórico ligado dos dados confirmados e organiza-os como ramos no repositório.

  - O repositório local pode enviar dados para o repositório remoto através do comando `git push`.

  - O repositório local pode receber dados do repositório remoto através dos comandos `git fetch` e `git pull`.

    - O comando `git pull` executa o comando `git merge` ou `git rebase` após o comando `git fetch`.

    - Aqui, `git merge` combina dois ramos separados do histórico no final para um ponto. (Este é o padrão do `git pull` sem personalização e pode ser bom para as pessoas que publicam o ramo para muitas pessoas.)

    - Aqui, `git rebase` cria um único ramo do histórico sequencial do ramo remoto seguido pelo ramo local. (Este é o caso de personalização `pull.rebase true` e pode ser bom para o resto de nós.)

- O repositório remoto que contém os ficheiros confirmados.

  - A comunicação com o repositório remoto utiliza protocolos de comunicação seguros, como SSH ou HTTPS.

A árvore de trabalho são os arquivos fora do diretório `.git/`. Os ficheiros dentro do diretório `.git/` contêm o índice, os dados do repositório local e alguns ficheiros de texto de configuração do git.

Aqui está uma visão geral dos principais comandos do Git.

Tabela 10.12. Principais comandos do Git

Comando Git | função
--- | ---
`git init` | cria o repositório (local)
`git clone URL` | clonar o repositório remoto para um repositório local com a árvore de trabalho
`git pull origin main` | atualizar o ramo `main` local pela `origin` do repositório remoto
`git add .` | adicionar ficheiro(s) na árvore de trabalho ao índice para ficheiros pré-existentes apenas no índice
`git add -A .` | adicionar ficheiro(s) na árvore de trabalho ao índice para todos os ficheiros, incluindo remoções
`git rm filename` | remover ficheiro(s) da árvore de trabalho e do índice
`git commit` | confirmar as alterações preparadas no índice para o repositório local
`git commit -a` | adicionar todas as alterações da árvore de trabalho ao índice e submetê-las ao repositório local (adicionar + submeter)
`git push -u origin branch_name` | atualizar a `origem` do repositório remoto pelo ramo local `branch_name` (invocação inicial)
`git push origin branch_name` | atualizar a `origem` do repositório remoto pelo ramo local `branch_name` (invocação subsequente)
`git diff treeish1 treeish2` | mostrar a diferença entre o envio treeish1 e o envio treeish2
`gitk` | Exibição GUI da árvore de histórico de ramificações do repositório VCS

### 10.5.3. Dicas do Git

Eis algumas dicas do Git.

Tabela 10.13. Dicas do Git

Linha de comando do Git | função
--- | ---
`gitk --all` | ver o histórico completo do Git e operar sobre ele, como redefinir o HEAD para outro commit, escolher patches, criar tags e branches ...
`git stash` | obter a árvore de trabalho limpa sem perder dados
`git remote -v` | verificar as definições do controlo remoto
`git branch -vv` | verificar definições para o seu ramo
`git status` | mostrar o estado da árvore de trabalho
`git config -l` | listar definições git
`git reset --hard HEAD; git clean -x -d -f` | reverter todas as alterações da árvore de trabalho e limpá-las completamente
`git rm --cached filename` | reverte o índice de fases alterado pelo `git add filename`
`git reflog` | obter registo de referência (útil para recuperar commits do ramo removido)
`git branch new_branch_name HEAD@{6}` | criar um novo ramo a partir da informação do reflog
`git remote add new_remote URL` | adicionar um repositório remoto `new_remote` apontado pelo URL
`git remote rename origin upstream` | renomear o nome do repositório remoto de `origin` para `upstream`
`git branch -u upstream/branch_name` | defina o rastreio remoto para o repositório remoto `upstream` e o seu nome de ramo `branch_name`.
`git remote set-url origin https://foo/bar.git` | alterar URL de `origin`
`git remote set-url --push upstream DISABLED` | desativar o envio para `upstream` (Editar `.git/config` para voltar a ativar)
`git remote update upstream` | obter atualizações de todos os ramos remotos no repositório "`upstream`" a montante
`git fetch upstream foo:upstream-foo` | criar um ramo `upstream-foo` local (possivelmente órfão) como uma cópia do ramo `foo` no repositório `upstream`
`git checkout -b topic_branch ; git push -u topic_branch origin` | criar um novo `topic_branch` e enviá-lo para a `origem`
`git branch -m oldname newname` | renomear o nome do ramo local
`git push -d origin branch_to_be_removed` | remover o ramo remoto (novo método)
`git push origin :branch_to_be_removed` | remover o ramo remoto (método antigo)
`git checkout --orphan unconnected` | criar um novo ramo `unconnected`
`git rebase -i origin/main` | reorder/drop/squish commits de `origin/main` para limpar o histórico do ramo
`git reset HEAD^; git commit --amend` | squash os últimos 2 commits num só
`git checkout topic_branch ; git merge --squash topic_branch` | squash todo o `topic_branch` num commit
`git fetch --unshallow --update-head-ok origin '+refs/heads/*:refs/heads/*'` | converter um clone superficial num clone completo de todos os ramos
`git ime` | divide o último commit numa série de commits mais pequenos, ficheiro a ficheiro, etc. (é necessário o pacote `imediff` )
`git repack -a -d; git prune` | reempacotar o repositório local num único pacote (isto pode limitar a possibilidade de recuperação de dados perdidos a partir de um ramo apagado, etc.)

| Atenção
Não use a string de etiqueta (tag) com espaços nela, mesmo que algumas ferramentas como o gitk(1) o permitam. Pode estrangular outros comandos do `git`.

| Cuidado
Se um ramo local que foi enviado para o repositório remoto for rebaseado ou squashed, o envio deste ramo tem riscos e requer a opção `--force`. Isso geralmente não é aceitável para o ramo `principal`, mas pode ser aceitável para um ramo tópico antes de mesclar com o ramo `principal`.

| Cuidado
Invocar um sub-comando `git` directamente como "`git-xyz`" a partir da linha de comandos foi descontinuado desde o inicio de 2006.

| Dica
Se existir um ficheiro executável `git-foo` no caminho especificado por `$PATH`, inserir "`git foo`" sem hífen na linha de comandos invoca este `git-foo`. Isto é uma característica do comando `git`.

### 10.5.4. Referências do Git

Veja o seguinte.

- manual: git(1) (`/usr/share/doc/git-doc/git.html`)

- Manual do Utilizador do Git (`/usr/share/doc/git-doc/user-manual.html`)

- Um tutorial de introdução ao git (`/usr/share/doc/git-doc/gittutorial.html`)

- Um tutorial de introdução ao git: parte dois (`/usr/share/doc/git-doc/gittutorial-2.html`)

- GIT do Dia-a-Dia com cerca de 20 comandos (`/usr/share/doc/git-doc/giteveryday.html`)

- Magia do Git (`/usr/share/doc/gitmagic/html/index.html`)

### 10.5.5. Outros sistemas de controlo de versões

O sistema de controlo de versões (VCS) é por vezes conhecido como sistema de controlo de revisões (RCS) ou gestão da configuração do software (SCM).

Aqui está um sumário dos outros VCS não-Git notáveis no sistema Debian.

Tabela 10.14. Lista de outras ferramentas de sistemas de controlo de versões

pacote | popcon | tamanho | ferramenta | Tipo VCS | comentário
--- | --- | --- | --- | --- | ---
`mercurial` | V:4, I:23 | 2575 | Mercurial | distribuído | DVCS em Python e algum C
`darcs` | V:0.2, I:3.3 | 38856 | Darcs | distribuído | DVCS com álgebra inteligente de patches (lento)
`tla` | V:0.04, I:0.70 | 1022 | GNU arch | distribuído | DVCS principalmente por Tom Lord (histórico)
`bzr` | V:0.1, I:4.3 | 28 | GNU Bazaar | distribuído | DVCS influenciado pelo `tla` escrito em Python (histórico)
`subversion` | V:9, I:55 | 4848 | Subversion | remoto | "CVS feito corretamente", o mais recente VCS remoto padrão (histórico)
`cvs` | V:3, I:23 | 4835 | CVS | remoto | VCS remoto padrão anterior (histórico)
`tkcvs` | V:0.12, I:0.91 | 34 | CVS, … | remoto | ecrã GUI de árvores de repositório VCS (CVS, Subversion, RCS)
`rcs` | V:2.1, I:9.5 | 578 | RCS | local | "SCCS Unix bem feito" (histórico)
`cssc` | V:0.01, I:0.30 | 2044 | CSSC | local | clone do SCCS Unix (histórico)

[4] Uma média de escrita única como o CD/DVD-R pode evitar acidentes de sobreescrita. (Veja Seção 9.8, “Os dados binários” para saber como escrever para o suporte de armazenamento a partir da linha de comandos da shell. O ambiente GUI do ambiente de trabalho GNOME dá-lhe acesso fácil através do menu: "Locais→Criador de CD/DVD".)

[5] Alguns destes dados não podem ser gerados de novo introduzindo a mesma cadeia de entrada no sistema.

[6] Se utilizar "`~/.vimrc`" em vez de "`~/.vim/vimrc`", substitua-o em conformidade.

Capítulo 9. Dicas do sistema |  | Capítulo 11. Conversão de dados