{"id":2281,"date":"2023-12-02T12:49:23","date_gmt":"2023-12-02T16:49:23","guid":{"rendered":"https:\/\/lowtek.ca\/roo\/?p=2281"},"modified":"2023-12-02T12:49:23","modified_gmt":"2023-12-02T16:49:23","slug":"docker-system-prune-not-always-what-you-expect","status":"publish","type":"post","link":"https:\/\/lowtek.ca\/roo\/2023\/docker-system-prune-not-always-what-you-expect\/","title":{"rendered":"Docker system prune &#8211; not always what you expect"},"content":{"rendered":"<p>Containers have improved my &#8216;home lab&#8217; significantly. I&#8217;ve run a server at home (exposed to the internet) for many years. Linux has made this both easy to do, and fairly secure.<\/p>\n<p>However, in the old &#8211; &#8220;I&#8217;ll just install these packages on my linux box&#8221; &#8211; model, you&#8217;d end up with package A needing some dependency and package B needing the same one, then you&#8217;d have version conflicts. It was always something you could resolve, but with enough software you&#8217;d have a mess of dependencies to figure out.<\/p>\n<p>Containers solves this by giving you a lightweight &#8216;virtualization&#8217; isolating each of your packages from each other AND it also is a very convenient distribution mechanism. This allows you to easily get a complete functional application with all of it&#8217;s dependencies in a single bundle. I&#8217;ll point at <a href=\"https:\/\/www.linuxserver.io\/\">linuxserver.io<\/a> as a great place to get curated images from. Also, consider having an update policy to help you keep current, something like <a href=\"https:\/\/lowtek.ca\/roo\/2022\/knowing-when-to-update-your-docker-containers-with-diun\/\">DUIN<\/a>, or fully automate with <a href=\"https:\/\/github.com\/containrrr\/watchtower\">watchtower<\/a>.<\/p>\n<p>Watchtower does have the ability to do some <a href=\"https:\/\/containrrr.dev\/watchtower\/arguments\/#cleanup\">cleanup<\/a> for you, but I&#8217;m not using watchtower (yet). I have included some <a href=\"https:\/\/lowtek.ca\/roo\/2023\/update-managing-docker-containers-with-makefiles\/\">image clean up into my makefiles<\/a> because I was trying to fight filesystem bloat due to updates. While I don&#8217;t want to prematurely delete anything, I also don&#8217;t want a lot of old cruft using up my disk space.<\/p>\n<p>I recently became aware of the large number of docker volumes on my system. I didn&#8217;t count, but it was well over 50 (the list filled my terminal window). This seemed odd, some of them had a creation date of 2019.<\/p>\n<p>Let&#8217;s just remove them <code>docker volume prune<\/code> &#8211; yup, remove all volumes not used by at least one container. Hmm, no &#8211; I still have so many. Let&#8217;s investigate further.<\/p>\n<pre class=\"lang:default decode:true\">$ docker ps -a --filter volume=efd0e9391281d9d6c9f3270be983dffd7830ea5196da44e9be7bf8d7c56db593\r\nCONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES<\/pre>\n<p>What? If I sub in a volume id that I know is attached to a container, I do get the container shown to me. This feels like both <code>docker system prune<\/code> and <code>docker volume prune<\/code> are broken.<\/p>\n<p>Thankfully the internet is helpful if you know what to search for. <a href=\"https:\/\/stackoverflow.com\/questions\/75493720\/docker-volume-prune-not-deleting-unused-volumes\">Stackoverflow helped me out<\/a>. It in turn pointed me at a <a href=\"https:\/\/github.com\/docker\/cli\/issues\/4028\">github issue<\/a>. Here is what I understand from those.<\/p>\n<blockquote><p>Docker has both anonymous and named volumes. Unfortunately, many people were naming volumes and treating them like permanent objects. Running <code>docker system prune<\/code> was removing these named volumes if there wasn&#8217;t a container associated with it. Losing data sucks, so docker has changed to not remove named volumes as part of a prune operation.<\/p><\/blockquote>\n<p>In my case, I had some container images which had mount points that I wasn&#8217;t specifying as part of my setup. An example is a \/var\/log mount &#8211; so when I create the container, docker is creating a volume on my behalf &#8211; and it&#8217;s a named volume. When I recreate that image, I&#8217;m getting a new volume and &#8216;leaking&#8217; a named volume which is no longer attached to a container. This explains why I had 50+ volumes hanging out.<\/p>\n<p>You can easily fix this<\/p>\n<pre class=\"lang:default decode:true\">docker volume prune --filter all=1\r\n\r\n[lots of output]\r\n\r\nTotal reclaimed space: 53.13MB<\/pre>\n<p>Yup, now I have very few docker volumes on my system &#8211; the remaining ones are associated with either a running or a stopped container.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Containers have improved my &#8216;home lab&#8217; significantly. I&#8217;ve run a server at home (exposed to the internet) for many years. Linux has made this both easy to do, and fairly secure. However, in the old &#8211; &#8220;I&#8217;ll just install these packages on my linux box&#8221; &#8211; model, you&#8217;d end up with package A needing some &hellip; <a href=\"https:\/\/lowtek.ca\/roo\/2023\/docker-system-prune-not-always-what-you-expect\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;Docker system prune &#8211; not always what you expect&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[6],"tags":[],"class_list":["post-2281","post","type-post","status-publish","format-standard","hentry","category-computing"],"_links":{"self":[{"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/posts\/2281","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/comments?post=2281"}],"version-history":[{"count":2,"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/posts\/2281\/revisions"}],"predecessor-version":[{"id":2284,"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/posts\/2281\/revisions\/2284"}],"wp:attachment":[{"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/media?parent=2281"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/categories?post=2281"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/lowtek.ca\/roo\/wp-json\/wp\/v2\/tags?post=2281"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}