Corrigindo dependências quebradas e pacotes retidos no apt
Qual a diferença entre pacotes retidos e dependências quebradas?
Conclusão: São problemas diferentes. Retido (held) significa que um pacote foi intencionalmente excluído de atualizações - não é um erro. Dependências quebradas significa que uma dependência necessária não pode ser satisfeita, então instalações ou atualizações não podem ser concluídas. O primeiro é tratado com
apt-mark, o segundo comapt --fix-broken install.
As pessoas tendem a agrupar esses dois sintomas como "um problema de dependência", mas as causas e correções diferem.
# (A) retido: uma atualizacao foi simplesmente mantida de lado. Nao e um erro. $ sudo apt upgrade The following packages have been kept back: linux-generic nvidia-driver-535
# (B) quebrado: uma dependencia nao pode ser satisfeita e a operacao para. Isso e anormal. $ sudo apt install some-package The following packages have unmet dependencies: some-package : Depends: libfoo (>= 2.0) but 1.8 is to be installed E: Unable to correct problems, you have held broken packages.
(A) é o apt deliberadamente recusando uma atualização; o sistema está saudável. (B) é uma incompatibilidade de versão em uma biblioteca necessária, e se deixado assim vai bloquear outras instalações também. Identificar qual sintoma você tem é o primeiro passo.
Premissas (ambiente alvo)
- SO: Ubuntu / distribuições baseadas em Debian (qualquer uma usando apt / dpkg)
- Você pode usar
sudo - (B) é mais comum logo após adicionar um PPA de terceiros ou um
.debmanual
Por que um pacote fica "kept back"?
Conclusão:
apt upgradeé conservador - ele não realiza uma atualização que requer remover um pacote existente (ele vai instalar novos pacotes quando necessário para satisfazer dependências). Então metapacotes e kernels cuja atualização precisa de uma remoção ficam "kept back". As phased updates do Ubuntu também retém atualizações temporariamente.
Há duas razões principais para "kept back" aparecer com apt upgrade.
| Razão | Pacotes típicos | Como resolver |
|---|---|---|
| Atualização requer uma remoção | Metapacotes / transicionais / kernel | apt full-upgrade |
| Phased updates em andamento | Qualquer um (apenas Ubuntu) | Aguardar / verificar |
Para se manter seguro, apt upgrade vai adicionar novos pacotes quando necessário para satisfazer dependências, mas nunca remove um pacote que você já tem. Se uma atualização requer remover um pacote instalado, essa atualização é pulada e mantida de lado (kept back). Atualizações de metapacotes de kernel podem cair nessa regra.
Para permitir remoções e atualizar todo o sistema junto, use full-upgrade (dist-upgrade com apt-get).
$ sudo apt full-upgrade
As phased updates do Ubuntu são distribuídas ao longo de vários dias em vez de todas de uma vez. Se sua máquina ainda não está na porcentagem de distribuição, aquela atualização fica mantida de lado. Nesse caso, ela chega por conta própria em alguns dias. Para verificar agora, inspecione o candidato:
$ apt-cache policy <package-name>
Como verificar e liberar pacotes explicitamente retidos?
Conclusão: Alguém (talvez você) pode ter executado
apt-mark holdpara fixar intencionalmente um pacote. Liste-os comapt-mark showhold, e libere comapt-mark unhold <pkg>se não for mais necessário.dpkg --get-selectionstambém mostra.
Se um pacote ainda não atualiza mesmo após full-upgrade, provavelmente está retido (pinned). Um hold significa "não atualize isso", usado para travar uma versão conhecida como boa (kernels, drivers, etc.).
Primeiro, liste os pacotes retidos.
$ apt-mark showhold
nvidia-driver-535 linux-image-generic
Esses nomes estão excluídos de atualizações. dpkg mostra a mesma coisa.
$ dpkg --get-selections | grep hold
nvidia-driver-535 hold
Quando o pin não é mais necessário, libere o hold. Depois disso o pacote volta ao tratamento normal de atualizações.
# Liberar o hold $ sudo apt-mark unhold nvidia-driver-535 # Para fixar em vez disso $ sudo apt-mark hold nvidia-driver-535
Liberar descuidadamente um hold de um pacote intencionalmente retido (ex.: um driver verificado) pode alterar o comportamento na próxima atualização. Não libere um hold até saber por que ele existe. Se não tiver certeza, descubra quem definiu e quando (política da equipe, um script de provisionamento) primeiro.
Por que dependências não satisfeitas acontecem?
Conclusão:
unmet dependenciessignifica que uma versão de dependência necessária não pode ser obtida ou reconciliada. As causas se resumem a repositórios misturados (PPAs,.debmanual), umapt updatedesatualizado, uma instalação interrompida ou pinning. A linhaDepends:no erro é sua pista direta.
Quando você encontra unmet dependencies, leia o corpo do erro primeiro. Ele indica qual dependência, sob qual restrição de versão, não pode ser satisfeita.
The following packages have unmet dependencies:
packageA : Depends: libbar (>= 3.0) but it is not going to be installed
Depends: libbaz (= 1.2) but 1.4 is to be installed
Depends: libbar (>= 3.0) but ... significa "libbar 3.0 ou mais novo é necessário, mas não pode ser instalado / uma versão diferente está prestes a ser instalada". As causas se dividem em quatro categorias.
| Causa | Situação típica | Direção |
|---|---|---|
| Repositórios misturados | PPA / .deb manual / releases Ubuntu mistos |
Remover o PPA / --fix-broken |
apt update desatualizado |
apt não conhece a nova versão da dependência | apt update, depois tente novamente |
| Instalação anterior interrompida | Queda de energia / kill encerrou apt no meio |
dpkg --configure -a |
| Pinning do apt (prioridades) | Uma versão fixada em /etc/apt/preferences |
Revisar o pin |
A primeira domina: um PPA externo ou .deb avulso demanda uma versão de dependência que conflita com o repositório oficial. apt-cache policy mostra de qual repositório uma dependência vem.
$ apt-cache policy libbar
libbar:
Installed: 2.8-1
Candidate: 2.8-1
Version table:
3.0-1 500 500 https://ppa.example/ubuntu jammy/main amd64 Packages
*** 2.8-1 500 500 http://archive.ubuntu.com/ubuntu jammy/main amd64 Packages
Ver de qual repositório o candidato e a versão necessária vêm indica se a mistura é a causa.
Como reparar dependências quebradas?
Conclusão: O padrão é
sudo apt --fix-broken install(anteriormenteapt-get -f install), que tenta resolver dependências incompletas. Se uma interrupção é a causa, executedpkg --configure -aprimeiro. Se os dados do repositório estão apenas desatualizados,apt updatefrequentemente resolve.
Repare na ordem de menor impacto. Não force-remova pacotes de início - deixe o apt resolver.
Primeiro atualize as listas, depois tente o reparo automático.
$ sudo apt update $ sudo apt --fix-broken install
--fix-broken (-f) detecta pacotes com dependências quebradas e propõe/aplica as adições faltantes ou remoções desnecessárias. Se um apt anterior parou no meio da operação, configure os pacotes "descompactados mas não configurados" primeiro.
$ sudo dpkg --configure -a $ sudo apt --fix-broken install
Quando o apt propõe remover um pacote, sempre leia o que será removido. Se a proposta envolve remover pacotes importantes que você não esperava, pare antes de responder yes.
O amplamente compartilhado sudo dpkg -i --force-depends *.deb e --force-all ignoram verificações de dependência e instalam mesmo assim - pode passar agora mas quebra pior depois. As opções --force-* são último recurso; corrija a causa raiz (repos misturados, pinning) primeiro.
A sequência padrão de recuperação, em ordem:
sudo apt update sudo dpkg --configure -a sudo apt --fix-broken install sudo apt full-upgrade
Como obter opções de resolução do aptitude?
Conclusão: Para conflitos complexos que
apt --fix-broken installnão consegue resolver,aptitudepropõe múltiplas soluções interativamente. Você pode rejeitar opções que não gosta, então ele encontra um meio-termo de forma mais flexível que o apt.
Mesmo quando o apt desiste de um conflito, aptitude percorre soluções em etapas (o que manter, o que fazer downgrade, etc.). Normalmente não está instalado por padrão, então adicione-o.
$ sudo apt install aptitude $ sudo aptitude install <package-name>
Quando uma dependência não pode ser satisfeita, aptitude oferece soluções como Accept this solution? [Y/n/q/?]. Pressione n para a próxima opção, y para aceitar - assim você escolhe uma solução com a qual está confortável. O controle mais fino sobre o "tudo ou nada" do apt é a vantagem.
Propostas do aptitude também podem incluir soluções "remover uma pilha de pacotes". Sempre revise as remoções e downgrades de uma solução proposta antes de aceitar. Aceitar cegamente a primeira opção não é melhor do que forçar com o apt.
Checklist quando ainda não resolve
Conclusão: Diferencie retido de quebrado, e para quebrado aplique "update -> configure -> fix-broken" em ordem. Se você suspeita de repositórios misturados, remover aquele PPA e reavaliar é o caminho mais curto.
- [ ] Determinou se o sintoma é "kept back" (retido) ou "unmet dependencies" (quebrado)?
- [ ] Se kept back, tentou
apt full-upgrade(e aguardou se é phased updates)? - [ ] Verificou
apt-mark showholdpara um hold intencional? - [ ] Leu a linha
Depends:no erro deunmet dependencies? - [ ] Tentou
sudo apt update->dpkg --configure -a->apt --fix-broken installem ordem? - [ ] Usou
apt-cache policy <dep>para identificar repos misturados (PPA / .deb manual)? - [ ] Corrigiu a causa raiz (pinning / mistura) antes de forçar com
--force-*? - [ ] Revisou soluções do
aptitudepara conflitos complexos?