Создание списка установленных вручную пакетов и запрос отдельных пакетов

183

Я хотел бы получить список пакетов, установленных вручную aptили, aptitudeи иметь возможность узнать, был ли foobarпакет установлен вручную или автоматически. Есть ли какой-нибудь аккуратный способ сделать это из командной строки?

Umang
источник
Посмотрите этот ответ на unix.stackexchange.com для решения, которое отфильтровывает стоковые пакеты.
Дирк Бергстрем
Возможный дубликат? - askubuntu.com/questions/365
jrg
Действительно хорошее решение, исключающее пакеты, установленные по умолчанию: список явно установленных пакетов в Ubuntu
pcworld,
Внимательно ответьте на комментарии здесь. Люди не говорят, как появляется больше пакетов, но они забывают, что существуют пакеты зависимостей, установленные из установленного руководства.
Андре Фигейредо

Ответы:

206

Вы можете использовать любой из этих двух однострочников. Оба дают одинаковый результат на моей машине и более точны, чем все решения, предложенные до сих пор (6 июля 2014 г.) в этом вопросе.

Использование apt-mark:

comm -23 <(apt-mark showmanual | sort -u) <(gzip -dc /var/log/installer/initial-status.gz | sed -n 's/^Package: //p' | sort -u)

Использование aptitude:

comm -23 <(aptitude search '~i !~M' -F '%p' | sed "s/ *$//" | sort -u) <(gzip -dc /var/log/installer/initial-status.gz | sed -n 's/^Package: //p' | sort -u)

Очень немногие пакеты по-прежнему попадают в трещины, хотя я подозреваю, что они на самом деле устанавливаются пользователем, либо сразу после установки через настройку языковой локализации, либо, например, через установщик кодеков Totem. Кроме того, версии заголовков linux также накапливаются, хотя я установил только не зависящий от версии метапакет. Примеры:

libreoffice-help-en-gb
openoffice.org-hyphenation
gstreamer0.10-fluendo-mp3
linux-headers-3.13.0-29    

Как это работает:

  1. Получить список установленных вручную пакетов. Для способности, дополнительные sedудаляют оставшиеся пробелы в конце строки.
  2. Получите список установленных пакетов сразу после новой установки.
  3. Сравните файлы, выведите только те строки в файле 1, которых нет в файле 2.

Другие возможности не работают так же хорошо:

  • Использование ubuntu-14.04-desktop-amd64.manifestфайла ( здесь для Ubuntu 14.04) вместо /var/log/installer/initial-status.gz. Дополнительные пакеты отображаются как установленные вручную, хотя это не так.
  • Использование apt-mark showautoвместо /var/log/installer/initial-status.gz. apt-markнапример, не включает пакет xserver-xorg, в то время как другой файл включает.

Я использовал различные другие сообщения StackExchange в качестве ссылок, однако ни одна из них не работает так же хорошо, как приведенное выше решение:

Оба перечисляют больше пакетов, чем приведенное выше решение.

РЕДАКТИРОВАТЬ: Что делать, если вы обновились с предыдущего выпуска:

Если вы обновили Ubuntu с одного выпуска на другой, вам, вероятно, придется настроить этот процесс. В этом случае я бы проверил файл манифеста более новой версии (см. Выше) в дополнение к файлу initial-status.gz из текущей версии. Вы можете легко сделать это, просто добавив еще одно сравнение. Использование только файла манифеста не будет работать, так как, к сожалению, файл манифеста не содержит всего, что делает файл initial_status.gz (я проверял).

jmiserez
источник
7
Это не сработало для меня, потому что /var/log/installer/initial-status.gzотсутствует. Также я хочу знать, зависит ли это от маркировки apts manualили нет?
Анвар
1
Увы, нет манифеста для серверных версий.
Антти Хаапала
Я выполнил showmanualкоманду (ниже). И используйте commдля сравнения двух (отсортированных) списков. showmanualРезультат дал мне 1840 более уникальные пакеты из apt-mark showmanualне показанных этого метода. НИКАКИЕ пакеты не были уникальными для вывода этой comm-команды. Я думаю, что более интересно записать, что для моего ПК в обоих результатах указано 894 пакета. Не уверен, почему есть такое огромное несоответствие. Некоторые (многие?) Пакеты, похоже, зависят от версии. Другие, такие как XOrg, компоненты GTK и другие, lib*могут быть обновлениями. В любом случае, этот ответ - очень хорошее начало.
будет
Я просто сравнил ваши решения с apt-mark showmanual. Интересно, сколько различий видно. Ваш список содержит 238 пакетов, а showmanual возвращает 1717 пакетов. Из 2179 установленных пакетов только 223 в обоих списках, 15 только в вашем (примеры: nodejs, lightdm) и 223 только в showmanual (примеры: xserver-xorg, ubuntu-desktop). Такое ощущение, что ваш список более полезен, но, не зная, откуда эти различия, нелегко решить ... (но я совершенно уверен, что я вручную установил nginx и lightdm ...) [извините, я только что написал то же самое;)]
Даниэль Олдер
64

В более новых версиях пакета apt есть также команда apt-mark

apt-mark showmanual
Даниэль Алдер
источник
35
Это показывает гораздо больше пакетов, чем я установил вручную.
Уманг
1
@ Umang Вы правы. Я бы сказал, что это не так, когда я написал этот ответ. В моей системе нет причин рассматривать и linux-image-3.11.0-*-genericт.д. как руководство
Даниэль Алдер
1
@Umang, может быть, это поможет вам askubuntu.com/questions/432743/… , но ответ не принят. Фактом является то, что многие пакеты новой установки уже помечены как ручные. Но есть еще некоторые странные вещи. Чтобы остаться с моим примером: linux-image-3.13.0-24-genericвручную, а ток linux-image-3.13.0-27-genericавтоматически. Похоже, что при обновлении ссылочного пакета (в данном случае linux-image-genericизменились зависимости) автоматически устанавливается ручная отметка
Даниэль Алдер
5
@DanielAlder некоторые пакеты новой установки должны быть помечены как ручные. Если нет пакетов, помеченных как ручные, всю систему можно удалить с помощью apt-get autoremove. Это определенно не то, что вы хотите.
Антон К
2
Если «установлен вручную» означает «установлен пользователем после первоначальной установки ОС», это неверный ответ.
Симус
21

Для Ubuntu 16.04 проверьте файл журнала /var/log/apt/history.log.

Например:

zgrep 'Commandline: apt' /var/log/apt/history.log /var/log/apt/history.log.*.gz

Он не идеален, но он довольно хорош, чтобы прояснить, что именно я установил вручную. Положите -B 1на grep, чтобы увидеть, когда он был установлен.

Пример вывода

Commandline: apt install postgresql-9.5-plv8
Commandline: aptdaemon role='role-install-file' sender=':1.85'
Commandline: apt install task
Commandline: apt autoremove
Commandline: apt install atom
Commandline: apt upgrade
Commandline: apt-get install asciinema
Commandline: apt install iperf3
Commandline: apt upgrade
Commandline: apt-get install chromium-browser
Commandline: apt install joe cpanminus build-essential postgresql libdbd-pg-perl libcrypt-openssl-bignum-perl libcrypt-openssl-rsa-perl libio-socket-ssl-perl libnet-ssleay-perl libssl-dev
Commandline: aptdaemon role='role-commit-packages' sender=':1.2314'
Commandline: apt install git
Commandline: apt install sqlite
Commandline: apt install whois
Commandline: apt install libdbd-pg-perl
Commandline: apt install perl-doc
Commandline: apt upgrade

Не уверен, что это подхватит aptitudeили нет. Похоже, он не забирает установки из настольного приложения Ubuntu Software.

s1037989
источник
1
Из всех ответов за эти годы это единственный, который даже близко подходит к серверу 18.04.
Квентин Скоусен
20

apt-mark showauto | grep -iE '^foobar$' выведет «foobar», если пакет был установлен автоматически, иначе ничего.

aptitude search '!~M ~i'перечислит пакеты, которые не были установлены автоматически. Жаль, что способность не будет частью установки по умолчанию на Ubuntu Desktop, начиная с 10.10.

Ли Ло
источник
aptitude searchпоказывает ВСЕ пакеты, а не только те, которые установлены вручную (я полагаю, это то, что хотел ОП)
Oli
1
@Oli: посмотрите на шаблоны поиска способностей; шаблон, который я здесь использую, должен делать именно то, что хочет ОП.
Ли Ло
Я запустил это. Он показывает всю загрузку пакетов, которые не установлены.
Оли
7
Что-то не так с этим, я использую, aptitude search '!~M ~i'и он перечисляет 1043 пакетов. Я не могу установить столько пакетов вручную.
ThatGraemeGuy
Это определенно не работает, как требуется, печатает также предустановленные пакеты.
Ирфи
9

Следующий скрипт распечатает все пакеты, которые не установлены для автоматической установки и, следовательно, были установлены вручную:

#!/usr/bin/python

try:
    import apt_pkg
except ImportError:
    print "Error importing apt_pkg, is python-apt installed?"
    sys.exit(1)

apt_pkg.init()
STATE_FILE = apt_pkg.config.find_dir("Dir::State") + "extended_states"
auto = set()
tagfile = apt_pkg.TagFile(open(STATE_FILE))
while tagfile.step():
    pkgname = tagfile.section.get("Package")
    autoInst = tagfile.section.get("Auto-Installed")
    if not int(autoInst):
        auto.add(pkgname)
print "\n".join(sorted(auto))

это основано на том, как apt-mark распечатывает автоматически установленные пакеты.

txwikinger
источник
Слава вам хорошо, сэр. Это на самом деле работает, в отличие от принятого ответа.
Ирфи
покажи мне только пару посылок - определенно скучаю по многим из них.
Rmano
То же самое здесь, определенно отсутствуют установленные вручную пакеты, сразу после их установки.
Дэвид Люнг Мэдисон
Использование sys.exit(1)без import sysможет привести к ошибке в более новых версиях Python. Либо import sysили используй exit(1).
Видеонавт
7

Чтобы получить список всех пакетов (не установленных, установленных пользователем или установленных по умолчанию для всех PPA), aptиспользуется следующий метод:

apt list [option]

Возможные варианты, полезные для этого:

--installed отображать только те пакеты, которые установлены в системе (из примерно 50 000+)

--manual-installedперечислить пакеты, которые были явно установлены командой, либо напрямую, либо как зависимости.

В качестве альтернативы вы можете сделать:

apt list --manual-installed | grep -F \[installed\] получить список пакетов, полученных только из пользовательских команд и их зависимостей, и получить дополнительную информацию о них, такую ​​как поддерживаемая версия и архитектура (x86, x86_64, amd64, все и т. д.)

Aalok
источник
5

Как прокомментировали несколько человек, шоу apt-mark showmanual выглядит немного глючно (и я сообщил об этом как об ошибке 727799 ). Когда я его использую, он на самом деле сообщает о многих вещах, которые даже не зарегистрированы в / var / lib / apt / extended_states (где это должно храниться), и apt-get не регистрирует вещи как установленные в / var / lib / apt / extended_states (только в / var / lib / dpkg / status). Сценарий python от txwikinger, приведенный выше, напрямую обращается к / var / lib / apt / extended_states, но если вы используете его сегодня, синтаксис может не работать (мой только что начал генерировать ошибки с Kubuntu 13.10). Обновленный синтаксис:

#!/usr/bin/python
import sys

try:
    import apt_pkg
except ImportError:
    print "Error importing apt_pkg, is python-apt installed?"
    sys.exit(1)

apt_pkg.init()
STATE_FILE = apt_pkg.config.find_dir("Dir::State") + "extended_states"
auto = set()
tagfile = apt_pkg.TagFile(open(STATE_FILE))
while tagfile.step():
    pkgname = tagfile.section.get("Package")
    autoInst = tagfile.section.get("Auto-Installed")
    if not int(autoInst):
        auto.add(pkgname)
print "\n".join(sorted(auto))

Для меня это был очень короткий список из 5 пунктов, который тоже не совсем точен.

cluelesscoder
источник
1
Использование sys.exit(1)без import sysможет привести к ошибке в более новых версиях Python. Либо import sysили используй exit(1).
Видеонавт
4

Я хотел бы дать решение GUI.

введите описание изображения здесь

  1. открыто Synaptic Package Manager

  2. Перейти к Status

  3. Нажмите Installed (manual)

Он выдаст список пакетов, установленных вручную с помощью apt или aptitude.

К сожалению, я не смог найти никакой опции, Custom Filtersчтобы узнать, был ли foobarпакет установлен вручную или автоматически.

Если пакет находится под, Installedно не под, Installed (manual)то он был установлен автоматически. Если пакет находится под, Installed (manual)то он был установлен вручную.

блюрэй
источник
2

Если никто не дает вам хороший ответ с помощью команды apr-что-то, вы можете сделать это трудным путем . Apt-get хранит свою информацию в / var / lib / apt / extended_states. Любой файл, который устанавливается автоматически, будет добавлен в этот файл. Если вы устанавливаете пакет уже в этом файле вручную, пакет останется в этом файле, но с автоматически установленным: 0 во второй строке. Это не удалено.

Примечание. Как и ожидалось, лучше будут ответы, которые могут сработать, если появятся изменения размещения файлов. Я оставляю свои на всякий случай, если информация о расположении файла полезна.

Хавьер Ривера
источник
1
Я быстро взглянул на этот файл и обнаружил, что liferea помечен как автоматически установленный. Я сделал, apt-get install lifereaи он не установился, но я получил вывод, который был чем-то вроде «помечен как установленный вручную». Теперь liferea все еще находится в файле, за исключением того, что в следующей строке 0вместо a 1. Кроме того, вы должны изменить свой шаблон регулярных выражений " foobar$"вместо просто foobar.
Уманг
Это правда. Моя ошибка, в моей системе нет строки с 0, но это должно случаться редко. Я обновляю ответ на всякий случай.
Хавьер Ривера
2

После долгих поисков, мне удалось собрать этот скрипт. Это работает хорошо для меня:

# List of all packages currently installed
current=$(dpkg -l | awk '{print $2}' | sort | uniq)

# List of all packages that were installed with the system
pre=$(gzip -dc /var/log/installer/initial-status.gz | sed -n 's/^Package: //p' | sort | uniq)

# List of packages that don't depend on any other package
manual=$(apt-mark showmanual | sort | uniq)

# (Current - Pre) ∩ (Manual)
packages=$(comm -12 <(comm -23 <(echo "$current") <(echo "$pre")) <(echo "$manual") )

for pack in $packages; do
    packname=$(echo $pack | cut -f 1 -d ":")
    desc=$(apt-cache search "^$packname$" | sed -E 's/.* - (.*)/\1/')
    date=$(date -r /var/lib/dpkg/info/$pack.list)

    echo "# $desc"
    echo "# $date"
    echo "sudo apt-get install $pack"
    echo -e ""
done
dufferZafar
источник
Вы могли бы использовать sort -uвместо sort | unique. Поскольку apt-markне отображает архитектуру, вы должны удалить ее из вывода dpkg перед выполнением операций set (или использованием dpkg-query -W -f='${Package}\n'). Кроме того, dpkg может перечислить некоторые пакеты, которые не установлены в настоящее время. Что касается "desc", вы можете использовать `dpkg-query -W -f = '# $ {binary: Summary} \ n' $ pack, что быстрее.
Ярно
Да, apt-markможет отображать архитектуру для некоторых пакетов, но не для многих dpkg -l.
Ярно
apt-cache searchмедленный. Заранее получить список установленных дат, используя что-то вроде help.ubuntu.com/community/ListInstalledPackagesByDate, может быть более эффективным
opticyclic
1

Как сказал Ли Ло, apt-mark showautoвы должны получить полный список автоматически установленных вещей.

Теперь, чтобы показать вещи, которые установлены вручную, оказалось, что есть замечательный простой модификатор поиска для aptitude. Но ты не хочешь этого делать. Вы хотите написать огромную команду bash, которая занимается ракетостроением.

Примечание. Это еще одна иллюстрация того, как здорово вы будете выглядеть, выполняя массовые команды bash всем своим друзьям.

comm -3  <(dpkg-query --show -f '${Package} ${Status}\n' | \n
grep "install ok installed" | cut --delimiter=' ' -f 1) <(apt-mark showauto)

Я разбил его на две строки для удобства чтения. Что это делает?

  • Сначала мы запрашиваем у dpkg список установленных пакетов.
  • Мы фильтруем те для тех, которые фактически установлены (не только остаточная конфигурация)
  • Отрубаем статус
  • Мы сравниваем этот список с автоматическим списком из apt-mark
  • Мы качаемся, потому что можем.
Оли
источник
Я сомневаюсь, что это верно, поскольку dpkg часто показывает пакеты, которые не установлены
txwikinger
Я знаю, что ты имеешь в виду, но мой баш-фу недостаточно силен. Я знаю, что вы можете показать статус из dpkg-запроса, выполнить поиск и затем вырезать статус. Я пойду.
Оли
comm -3 <(dpkg -l | grep '^ii' | cut -d \ -f 3|sort) <(apt-mark showauto|sort)по-настоящему лучше;)
LassePoulsen
-1

В этом списке перечислены все установленные вручную пакеты без: зависимостей, удаленных пакетов, пакетов, установленных во время установки системы.

unopts() {
  in=`cat`
  echo "$in" | sed -r 's/ --[^ ]+//g;s/ -[^ ]+//g'
}

list() {
  cat '/var/log/apt/history.log' |
  grep --color=never -v '\-o APT::Status-Fd=4 \-o APT::Keep-Fds::=5 \-o APT::Keep-Fds::=6' |
  egrep --color=never "Commandline: apt-get.* $1" |
  sed -r "s/Commandline: apt-get//;s/ $1//" |
  unopts |
  tr ' ' '\n' |
  sed '/^$/d'
}

hapt() {
  tmp=`mktemp -d`
  installed=$tmp/installed
  deleted=$tmp/deleted
  dpkg=$tmp/dpkg
  list 'install' > $installed
  list '(remove|purge|autoremove)' > $deleted
  dpkg --get-selections |
  grep -v 'deinstall' |
  cut -f 1 > $dpkg
  while read package
  do
    sed -i "0,/$package/{//d;}" $installed
  done < $deleted
  while read package
  do
    if [ -z "`grep --color=never "^$package$" $dpkg`" ]
    then
      sed -i "0,/$package/{//d;}" $installed
    fi
  done < $installed
  cat $installed
  rm -r $tmp
}
wieczorek1990
источник