Chcę wyodrębnić plik z obrazu Docker bez konieczności uruchamiania obrazu.
Ta docker saveopcja nie jest dla mnie obecnie opłacalną opcją, ponieważ zapisuje zbyt duży plik, aby rozpakować określony plik.
Chcę wyodrębnić plik z obrazu Docker bez konieczności uruchamiania obrazu.
Ta docker saveopcja nie jest dla mnie obecnie opłacalną opcją, ponieważ zapisuje zbyt duży plik, aby rozpakować określony plik.
Odpowiedzi:
Możesz wyodrębnić pliki z obrazu za pomocą następujących poleceń:
docker create $image # returns container ID
docker cp $container_id:$source_path $destination_path
docker rm $container_id
Zgodnie z docker create dokumentacją nie uruchamia to kontenera:
docker createPolecenie tworzy warstwę do zapisu kontenera po określonym obrazem i przygotowuje ją do prowadzenia określonego polecenia. Identyfikator kontenera jest następnie drukowany naSTDOUT. Jest to podobne dodocker run -dtego, że kontener nigdy się nie uruchamia. Następnie możesz użyćdocker start <container_id>polecenia, aby uruchomić kontener w dowolnym momencie.
Dla porównania (moja poprzednia odpowiedź), mniej efektywny sposób wyodrębnienia pliku z obrazu to:
docker run some_image cat $file_path > $output_path
docker run --entrypoint /bin/sh my_image -c /bin/cat some_file
Żadne z powyższych nie działało dla mnie. Kompletne działające polecenie to:
docker run --rm --entrypoint /bin/sh image_name -c "cat /path/filename" > output_filename
Bez cudzysłowów catjest przekazywany bez nazwy pliku, więc nie wie, co pokazać. Dobrym pomysłem jest również usunięcie kontenera po zakończeniu polecenia.
Jeśli się nie mylę, uważam, że kontenery dokerów przechowują pliki buforowane utworzone w następującym katalogu Ubuntu:
/var/lib/docker/aufs/diff/<container_id>
Stamtąd powinieneś być w stanie uzyskać dostęp do systemu plików i odzyskać swoje pliki.
layersizei jsonnie jest czytelny dla użytkownika (nawet jeśli użytkownik należy do grupy dokerów). /var/lib/docker/aufs/diffbędzie zawierał plik, którego szukam (ale nie jest podzielony na kategorie według identyfikatora kontenera) i również nie jest czytelny.
/var/lib/docker/aufs(ale nie wszystkie inne katalogi w /var/lib/docker/)
Jeśli przechowywanie pełnego wyjścia docker savenie jest opcją, możesz użyć potoków, aby wyodrębnić z niego tylko potrzebny plik.
Niestety, ponieważ wynikiem jest „smoła smół”, może to być proces iteracyjny.
To, co zrobiłem, gdy potrzebowałem teraz wyodrębnić plik, to:
1) Określ, którą wersję obrazu ostatnio zmienił interesujący Cię plik (sposób, w jaki to robisz, prawdopodobnie zależy od Twojego obrazu) oraz datę jego utworzenia / zapisania
2) Uzyskaj pełny spis treści z danych wyjściowych docker savepolecenia za pomocą:
docker save IMAGE_NAME | tar -tvf -
3) Wyczyść layer.tarplik (i) na wyjściu tego polecenia, które pasują do daty obrazu określonego w kroku 1. (możesz dodać, | grep layer.taraby po prostu pokazać te pliki)
4) Wyodrębnij ten layer.tarplik do standardu i uzyskaj spis treści:
docker save IMAGE_NAME | tar -xf - -O CHECKSUM_FROM_LIST/layer.tar | tar -tvf -
5) Sprawdź, czy żądany plik znajduje się na liście, i wypakuj go, gdy znajdziesz nazwę:
docker save IMAGE_NAME | tar -xf - -O CHECKSUM_FROM_LIST/layer.tar | tar -xf - PATH/TO/YOUR/FILE
Jeśli istnieje więcej niż jeden layer.tarplik pasujący do daty, której szukasz w kroku 2/3, może być konieczne powtórzenie kroku 4 dla każdego z nich, aż znajdziesz właściwy
Zamień tekst drukowanymi literami w powyższych poleceniach na prawidłowe nazwy obrazów, sumy kontrolne i nazwy plików dla twojej sprawy.