Jak uaktualnić wszystkie pakiety Pythona za pomocą pip

Czy możliwe jest uaktualnienie wszystkich pakietów Pythona jednocześnie z pip?

Uwaga : istnieje Prośba o funkcję w oficjalnym śledzeniu problemów.

 2234
Author: Boris, 2010-04-27

30 answers

Nie ma jeszcze wbudowanej flagi, ale możesz użyć

pip list --outdated --format=freeze | grep -v '^\-e' | cut -d = -f 1  | xargs -n1 pip install -U

Uwaga: istnieją nieskończone potencjalne różnice w tym zakresie. Staram się, aby ta odpowiedź była krótka i prosta, ale proszę sugerować różnice w komentarzach!

W starszej wersji pip możesz użyć tego zamiast:

pip freeze --local | grep -v '^\-e' | cut -d = -f 1  | xargs -n1 pip install -U

grep jest pominięciem edytowalnych ("-e") definicji pakietów, zgodnie z sugestią @jawache. (Tak, można zastąpić grep+cut z sed lub awk lub perl lub...).

The -n1 Flaga dla xargs zapobiega zatrzymywaniu wszystkiego, jeśli aktualizacja jednego pakietu nie powiedzie się (thanks @andsens).

 2444
Author: rbp,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-08-06 13:33:29

Możesz użyć następującego kodu Pythona. W przeciwieństwie do pip freeze, nie wyświetli ostrzeżeń i błędów FIXME. dla pip

import pip
from subprocess import call

packages = [dist.project_name for dist in pip.get_installed_distributions()]
call("pip install --upgrade " + ' '.join(packages), shell=True)

Dla pip >= 10.0.1

import pkg_resources
from subprocess import call

packages = [dist.project_name for dist in pkg_resources.working_set]
call("pip install --upgrade " + ' '.join(packages), shell=True)
 717
Author: MSS,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-09-17 12:55:35

Aby uaktualnić wszystkie lokalne Pakiety; można użyć pip-review:

$ pip install pip-review
$ pip-review --local --interactive

pip-review jest widelcem pip-tools. Zobacz też pip-tools Problem wymieniony przez @ knedlsepp. pip-review pakiet działa, ale pip-tools pakiet już nie działa.

pip-review działa na Windows od wersji 0.5.

 686
Author: jfs,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 12:02:46

Poniższe rozwiązanie działa w systemie Windows i powinno być dobre także dla innych ($ jest katalogiem, w którym się znajdujesz, w wierszu polecenia. Na przykład C:/Users/Username ).

Do

$ pip freeze > requirements.txt

Otwórz plik tekstowy, zamień == na >= i wykonaj:

$ pip install -r requirements.txt --upgrade

Jeśli masz problem z pewnym pakietem opóźniającym upgrade (NumPy czasami), po prostu przejdź do katalogu ($), skomentuj nazwę (dodaj # przed nim) i uruchom upgrade ponownie. Możesz później odkomenderuj tę sekcję z powrotem. Jest to również Świetne do kopiowania środowiska globalnego Pythona.


Inny sposób:

Podoba mi się również metoda PIP-review:

py2
$ pip install pip-review

$ pip-review --local --interactive

py3
$ pip3 install pip-review

$ py -3 -m pip_review --local --interactive

Możesz wybrać 'a', aby uaktualnić wszystkie pakiety; jeśli jedno uaktualnienie się nie powiedzie, uruchom je ponownie i będzie kontynuowane przy następnym.

 358
Author: azazelspeaks,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:52:16

Użycie pipupgrade!

$ pip install pipupgrade
$ pipupgrade --verbose --latest --yes

Pipupgrade pomaga uaktualnić system, lokalny lub pakiety z pliku requirements.txt! Selektywnie aktualizuje również pakiety, które nie psują zmian.

Pipupgrade zapewnia również upgrade pakietów obecnych w wielu środowiskach Pythona. Jest kompatybilny z Pythonem 2.7+, Pythonem 3.4 + i pip 9+, pip 10+, pip 18+, pip 19+.

Tutaj wpisz opis obrazka

Uwaga: jestem autorem narzędzia.

 182
Author: Achilles Gasper Rasquinha,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 22:33:50

Wersja Windows po zapoznaniu się z doskonałą dokumentacją dla FOR autor: Rob van der Woude:

for /F "delims===" %i in ('pip freeze -l') do pip install -U %i
 135
Author: Piotr Dobrogost,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:40:52

Ta opcja wydaje mi się bardziej prosta i czytelna:

pip install -U `pip list --outdated | awk 'NR>2 {print $1}'`

Wyjaśnienie jest takie, że pip list --outdated wyświetla listę wszystkich nieaktualnych pakietów w tym formacie:

Package   Version Latest Type 
--------- ------- ------ -----
fonttools 3.31.0  3.32.0 wheel
urllib3   1.24    1.24.1 wheel
requests  2.20.0  2.20.1 wheel

W poleceniu awk, NR>2 pomija dwa pierwsze rekordy (linie) i {print $1} wybiera pierwsze słowo każdej linii (zgodnie z sugestią SergioAraujo, usunąłem tail -n +3, ponieważ awk rzeczywiście może obsługiwać pomijanie rekordów).

 81
Author: Marc,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-02-25 16:57:29

Możesz po prostu wydrukować nieaktualne Pakiety:

pip freeze | cut -d = -f 1 | xargs -n 1 pip search | grep -B2 'LATEST:'
 74
Author: janrito,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:39:42

Następujące Jednowierszowe mogą okazać się pomocne:

(pip > 20.0)

pip list --format freeze --outdated | sed 's/=.*//g' | xargs -n1 pip install -U

Starsze Wersje:

pip list --format freeze --outdated | sed 's/(.*//g' | xargs -n1 pip install -U

xargs -n1 działa, jeśli wystąpi błąd.

Jeśli potrzebujesz większej kontroli "drobnoziarnistej" nad tym, co zostało pominięte i co powoduje błąd, nie powinieneś dodawać znacznika -n1 i jawnie definiować błędy do zignorowania, przez "Orurowanie" następującej linii dla każdego osobnego błędu:

| sed 's/^<First characters of the error>.*//'

Oto działający przykład:

pip list --format freeze --outdated | sed 's/=.*//g' | sed 's/^<First characters of the first error>.*//' | sed 's/^<First characters of the second error>.*//' | xargs pip install -U
 69
Author: raratiru,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-06-20 09:12:55

Solidniejsze Rozwiązanie

Dla pip3 , użyj tego:

pip3 freeze --local |sed -rn 's/^([^=# \t\\][^ \t=]*)=.*/echo; echo Processing \1 ...; pip3 install -U \1/p' |sh

Dla pip , po prostu usuń 3s jako takie:

pip freeze --local |sed -rn 's/^([^=# \t\\][^ \t=]*)=.*/echo; echo Processing \1 ...; pip install -U \1/p' |sh

OS X Oddity

[[5]}OS X, od lipca 2017, jest dostarczany z bardzo starą wersją sed (kilkanaście lat). Aby uzyskać rozszerzone wyrażenia regularne, użyj -E zamiast -r w powyższym rozwiązaniu.

Rozwiązywanie problemów z popularnymi rozwiązaniami

To rozwiązanie jest dobrze zaprojektowane i przetestowane 1 , natomiast są problemy z nawet najbardziej popularnymi rozwiązaniami.

  • problemy z przenośnością spowodowane zmianą funkcji wiersza poleceń pip
  • awariaxargs z powodu częstych błędów procesów potomnych PIP lub pip3
  • zatłoczone logowanie z raw xargs wyjście
  • [34]}opierając się na mostku Python-to-OS, potencjalnie aktualizując go 3

Powyższe polecenie wykorzystuje najprostszą i najbardziej przenośną składnię PIP w połączenie z sed i sh w celu całkowitego przezwyciężenia tych problemów. Szczegóły operacji sed można sprawdzić w komentowanej wersji2.


Szczegóły

[1] testowane i regularnie używane w Linuksie 4.8.16-200.fc24.klaster x86_64 i przetestowany na pięciu innych systemach Linux / Unix. Działa również na Cygwin64 zainstalowanym w systemie Windows 10. Konieczne jest testowanie na iOS.

[2] aby dokładniej zobaczyć anatomię komendy, to jest dokładnym odpowiednikiem powyższego polecenia pip3 z komentarzami:

# Match lines from pip's local package list output
# that meet the following three criteria and pass the
# package name to the replacement string in group 1.
# (a) Do not start with invalid characters
# (b) Follow the rule of no white space in the package names
# (c) Immediately follow the package name with an equal sign
sed="s/^([^=# \t\\][^ \t=]*)=.*"

# Separate the output of package upgrades with a blank line
sed="$sed/echo"

# Indicate what package is being processed
sed="$sed; echo Processing \1 ..."

# Perform the upgrade using just the valid package name
sed="$sed; pip3 install -U \1"

# Output the commands
sed="$sed/p"

# Stream edit the list as above
# and pass the commands to a shell
pip3 freeze --local | sed -rn "$sed" | sh

[3] Aktualizacja komponentu Pythona lub PIP, który jest również używany w aktualizacji komponentu Pythona lub PIP, może być potencjalną przyczyną blokady lub uszkodzenia bazy danych pakietów.

 58
Author: Douglas Daseeco,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2021-02-01 13:21:48

To wydaje się bardziej zwięzłe.

pip list --outdated | cut -d ' ' -f1 | xargs -n1 pip install -U

Wyjaśnienie:

pip list --outdated gets lines like these

urllib3 (1.7.1) - Latest: 1.15.1 [wheel]
wheel (0.24.0) - Latest: 0.29.0 [wheel]

W cut -d ' ' -f1, -d ' ' ustawia" spację " jako ogranicznik, -f1 oznacza uzyskanie pierwszej kolumny.

Więc powyższe linie stają się:

urllib3
wheel

Następnie przekaż je do xargs, aby uruchomić polecenie pip install -U, z każdą linią jako argumentami dołączającymi

-n1 ogranicza liczbę argumentów przekazywanych do każdego polecenia pip install -U do 1

 42
Author: Shihao Xu,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-12-18 18:30:49

Miałem ten sam problem z aktualizacją. Rzecz w tym, że nigdy nie uaktualniam wszystkich pakietów. Uaktualniam tylko to, czego potrzebuję, ponieważ projekt może się zepsuć.

Ponieważ nie było łatwego sposobu na uaktualnienie pakietu po pakiecie i aktualizację wymagań.plik txt, napisałem to pip-upgrader który aktualizuje również wersje w pliku requirements.txt dla wybranych pakietów (lub wszystkich pakietów).

Instalacja

pip install pip-upgrader

Użycie

Aktywuj swój virtualenv (ważne, ponieważ zainstaluje również nowe wersje uaktualnionych pakietów w bieżącym virtualenv).

cd do katalogu projektu, następnie uruchom:

pip-upgrade

Zaawansowane użycie

Jeśli wymagania są umieszczone w niestandardowej lokalizacji, wyślij je jako argumenty:

pip-upgrade path/to/requirements.txt

Jeśli już wiesz, jaki pakiet chcesz uaktualnić, po prostu wyślij je jako argumenty:

pip-upgrade -p django -p celery -p dateutil

Jeśli chcesz uaktualnić do wersji pre-release / post-release, dodaj --prerelease argument na twoje polecenie.

Pełne ujawnienie: napisałem ten pakiet.

 35
Author: Simion Agavriloaei,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 22:13:15

Jednowierszowa Wersja Ramana ' s answer .

python -c 'import pip, subprocess; [subprocess.call("pip install -U " + d.project_name, shell=1) for d in pip.get_installed_distributions()]'
 29
Author: Salman von Abbas,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:43:46

Od https://github.com/cakebread/yolk:

$ pip install -U `yolk -U | awk '{print $1}' | uniq`

Jednak najpierw musisz zdobyć żółtko:

$ sudo pip install -U yolk
 28
Author: tkr,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:41:31

Podczas używania virtualenv i jeśli chcesz tylko uaktualnić Pakiety dodane {[5] } do twojego virtualenv, możesz zrobić:

pip install `pip freeze -l | cut --fields=1 -d = -` --upgrade
 24
Author: brunobord,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:40:08

Najprostszym i najszybszym rozwiązaniem jakie znalazłem w dyskusji PIP issue jest:

pip install pipdate
pipdate

Źródło: https://github.com/pypa/pip/issues/3819

 22
Author: RedEyed,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-03-03 05:26:23

Windows PowerShell solution

pip freeze | %{$_.split('==')[0]} | %{pip install --upgrade $_}
 19
Author: Apeirogon Prime,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:58:44

Użyj AWK pakiety aktualizacji:

pip install -U $(pip freeze | awk -F'[=]' '{print $1}')

Windows PowerShell update

foreach($p in $(pip freeze)){ pip install -U $p.Split("=")[0]}
 16
Author: JohnDHH,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 22:20:18

The pip_upgrade_outdated robi swoje. Według jego dokumentacji :

usage: pip_upgrade_outdated [-h] [-3 | -2 | --pip_cmd PIP_CMD]
                            [--serial | --parallel] [--dry_run] [--verbose]
                            [--version]

Upgrade outdated python packages with pip.

optional arguments:
  -h, --help         show this help message and exit
  -3                 use pip3
  -2                 use pip2
  --pip_cmd PIP_CMD  use PIP_CMD (default pip)
  --serial, -s       upgrade in serial (default)
  --parallel, -p     upgrade in parallel
  --dry_run, -n      get list, but don't upgrade
  --verbose, -v      may be specified multiple times
  --version          show program's version number and exit

Krok 1:

pip install pip-upgrade-outdated

Krok 2:

pip_upgrade_outdated
 13
Author: adrin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 22:26:11

Możesz spróbować tego:

for i in ` pip list | awk -F ' ' '{print $1}'`; do pip install --upgrade $i; done
 12
Author: 何宗翰,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:45:19

Dość niesamowite żółtko to ułatwia.

pip install yolk3k # Don't install `yolk`, see https://github.com/cakebread/yolk/issues/35
yolk --upgrade

Więcej informacji na temat żółtka: https://pypi.python.org/pypi/yolk/0.4.3

Może zrobić wiele rzeczy, które prawdopodobnie uznasz za przydatne.

 12
Author: user1175849,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:57:41

Odpowiedź Ramana zadziałała dla mnie najlepiej, z tych tutaj, ale musiałem dodać kilka haczyków:

import pip
for dist in pip.get_installed_distributions():
    if 'site-packages' in dist.location:
        try:
            pip.call_subprocess(['pip', 'install', '-U', dist.key])
        except Exception, exc:
            print exc

Sprawdzenie site-packages wyklucza moje Pakiety programistyczne, ponieważ nie znajdują się one w systemowym katalogu site-packages. Try-except po prostu pomija pakiety, które zostały usunięte z PyPI.

Do endolith : też liczyłem na łatwe pip.install(dist.key, upgrade=True), ale wygląda na to, że pip miał być używany przez cokolwiek oprócz linii poleceń (w dokumentach nie ma wzmianki o wewnętrzne API, a deweloperzy pip nie używali docstringów).

 10
Author: chbrown,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:42:15

A pure Bash/z shell one-liner dla osiągnięcia tego:

for p in $(pip list -o --format freeze); do pip install -U ${p%%=*}; done

Lub w ładnie sformatowany sposób:

for p in $(pip list -o --format freeze)
do
    pip install -U ${p%%=*}
done
 10
Author: German Lashevich,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-12-14 12:01:38

Najkrótszy i najłatwiejszy w systemie Windows.

pip freeze > requirements.txt && pip install --upgrade -r requirements.txt && rm requirements.txt
 9
Author: Ankireddy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-04-23 07:25:16

Wysłałem przez pull-request do ludzi pip ; w międzyczasie użyj tego rozwiązania biblioteki pip napisałem:

from pip import get_installed_distributions
from pip.commands import install

install_cmd = install.InstallCommand()

options, args = install_cmd.parse_args([package.project_name
                                        for package in
                                        get_installed_distributions()])

options.upgrade = True
install_cmd.run(options, args)  # Chuck this in a try/except and print as wanted
 9
Author: Samuel Marks,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:46:31

Wydawało mi się, że to działa...

pip install -U $(pip list --outdated | awk '{printf $1" "}')

Użyłem printf ze spacją, aby odpowiednio oddzielić nazwy pakietów.

 9
Author: SaxDaddy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:50:05

To powinno być bardziej skuteczne:

pip3 list -o | grep -v -i warning | cut -f1 -d' ' | tr " " "\n" | awk '{if(NR>=3)print}' | cut -d' ' -f1 | xargs -n1 pip3 install -U
  1. pip list -o wyświetla nieaktualne Pakiety;
  2. grep -v -i warning odwrócone dopasowanie na warning, aby uniknąć błędów podczas aktualizacji
  3. cut -f1 -d1' ' zwraca pierwsze słowo - nazwę przestarzałego pakietu;
  4. tr "\n|\r" " " konwertuje wynik wielowierszowy z cut na jednoliniową listę rozdzieloną spacjami;
  5. awk '{if(NR>=3)print}' pomija linie nagłówka
  6. cut -d' ' -f1 pobiera pierwszą kolumnę
  7. xargs -n1 pip install -U pobiera 1 argument z lewej rury i przekazuje go do polecenia, aby uaktualnić listę pakietów.
 8
Author: Alex V,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 21:49:15

Użycie:

pip install -r <(pip freeze) --upgrade
 8
Author: user8598996,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 22:13:57

To jest rozwiązanie PowerShell dla Pythona 3:

pip3 list --outdated --format=legacy | ForEach { pip3 install -U $_.split(" ")[0] }

I dla Pythona 2:

pip2 list --outdated --format=legacy | ForEach { pip2 install -U $_.split(" ")[0] }

To ulepsza Pakiety jeden po drugim. So a

pip3 check
pip2 check

Następnie należy upewnić się, że żadne zależności nie są łamane.

 7
Author: Nils Ballmann,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-07-04 13:49:29

Jedna linia w PowerShell 5.1 z uprawnieniami administratora, Python 3.6.5 i pip Wersja 10.0.1:

pip list -o --format json | ConvertFrom-Json | foreach {pip install $_.name -U --no-warn-script-location}

Działa płynnie, jeśli na liście nie ma uszkodzonych pakietów lub specjalnych kółek...

 7
Author: Sébastien Wieckowski,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2020-10-06 22:29:56