Linux Ubuntu の無駄なファイルを確認し、お掃除しよう (おまけでvirtualbox イメージサイズ圧縮方法)

実験でaptのミラーサイトを作ろうとapt-mirrorコマンドを利用していたところ、途中で動作が止まり、再起動後はDisplayが立ち上がらず。
かろうじてsshログインは出来たのですが、確認すると容量がいっぱいに。なんと…
というわけでLinux内のディスクをお掃除しましょう。

今回の環境はUbuntu 18.04での確認となります。

#**現在の容量確認**

Linuxでの**各ファイルシステム領域の容量はdfコマンド**で確認できます。

```
$df
Filesystem     1K-blocks    Used Available Use% Mounted on
udev             4054564       0   4054564   0% /dev
tmpfs             816796    1220    815576   1% /run
/dev/sda1       10253588 6853008   2860012  71% /
tmpfs            4083972       0   4083972   0% /dev/shm
tmpfs               5120       4      5116   1% /run/lock
tmpfs            4083972       0   4083972   0% /sys/fs/cgroup
/dev/loop0        142848  142848         0 100% /snap/gnome-3-26-1604/64
...
tmpfs             816792       0    816792   0% /run/user/1000
```

凝ったファイルシステムを構築していなければ、**基本的に/にマウントされている部分がユーザーが利用している領域になっている**はずです。これは色々削除した後ですが、実際は/の場所が100%になっていました。

こうなると/tmpにファイルも作れないので、通常起動するプログラムも起動できないなんてことはざらにあります。
今回は何とかログイン出来たので、原因を深堀してスリム化を図りましょう。

#**容量の多いフォルダを調査**

##**1. 原因がわかっているならまずは対処**

とりあえず100%までいってしまうと何もできないので、今回は**apt-mirrorコマンドでたまったデータである/var/spool/apt-mirror/mirror/を削除**。これだけで3GByte弱埋まってしまっていた模様。apt updateも起動しているので動作に問題はなさそうです。

##**2. 他にゴミファイルが無いか確認**

根本を解決したとはいえ、ちょっとした調べものの為の環境に7GByteはちょっと。
せっかくなので他の要素も探ります。本章では便利ツールを順に紹介。
今回はこれらのおかげでユーザーファイルではなくパッケージに無駄がありそうなことがわかりました。

###**ファイルサイズ確認方法 その1. `ncdu`**

[こちらの記事](https://qiita.com/oshou/items/2630f9f1c1131beb748e#%E4%B8%8D%E8%A6%81%E3%83%87%E3%83%BC%E3%82%BF%E3%81%AE%E5%89%8A%E9%99%A4)で**ncdu**コマンドというものが紹介されていました。この記事が元々紹介していた**du -shコマンドの上位互換**。
(私はよく見ていなくて`du -sh`で場所を特定しました。よく記事を読め自分。)

こちらは**グラフィカルにフォルダサイズを表示してくれる**上、**気になるフォルダの中も掘り下げて確認可能**な優れモノツールになっております。

<img width="800" alt="ncdu.png" src="https://qiita-image-store.s3.amazonaws.com/0/252277/b7aa9278-7d81-030c-8c5c-36a4747d6d5e.png">

普通に**apt install ncduでインストール可能**、**パッケージサイズも91KByte**と文句なしです。

###**ファイルサイズ方法 その2. `du -sh`**

上記記事の元々の紹介コマンドがこちら。

```
$du -sh /*
...
2.7G    /snap
...
3.2G    /usr
1.8G    /var
```

上記はサイズの大きな箇所を抜粋しました。これでも十分対象のフォルダを絞ることが出来ますね。

###**ファイルサイズ方法 その3. `tree -s`**

フォルダではなくフォルダ内のサイズの大きなファイルを探すならこちらが便利です。

```
usr/bin$ tree -s
.
|-- [      51384]  [
|-- [      10104]  411toppm
|-- [      22696]  aa-enabled
...
`-- [      10336]  zlib-flate
```

指定した位置以下のファイルサイズが1つ1つ表示されます。
こちらも**apt install tree**でインストール可能。

細かい確認には便利ですが、大枠で原因を探るには向かない方法ですね。

#**がっつりお掃除の前に: バックアップを取ろう！ (VirtualBoxの場合の手順)**

がっつりお掃除しすぎて今の環境が壊れてしまった！なんて悲しいことはないので、バックアップを取りましょう。

##**通常のイメージバックバックアップ**

1. ホストPC(私はWindows 10)のOracle VM VirtualBox起動
2. 対象イメージを選択
3. ファイル⇒仮想アプライアンスのエクスポート

でイメージのバックアップが取れます。
ただ、普通にやると結構な容量になります。私の場合使い始めて**普通にやると5.59GByte**。
個人で使うならいいですが、**共有したりバックアップ対象が増える場合はちょっと大きなサイズ**ですね。

##**バックアップイメージのスリム化**

こちらも手順を踏むとスリム化が可能です。イメージとしては
**使っていない領域を0埋めし、VirtualBoxの機能で圧縮**という感じです。

手順は以下の通り:
**1. ゲストOS側: 利用していない箇所を0埋めする。**

```:ゲスト側がLinuxの場合
dd if=/dev/zero of=zero bs=4k; \rm zero
```
**2. ホストOS側: イメージを圧縮する。**
cmd等でコマンドプロンプト起動後、以下を実行

```:ホストOS側でのイメージを圧縮
>cd C:\Program Files\Oracle\VirtualBox
C:\Program Files\Oracle\VirtualBox> VBoxManage.exe list hdds
UUID:           189ce5d9-31b5-4f81-92ed-054fd52b3a09 <=こんな感じでUUIDが出てくるので、対象のUUIDをメモ
Parent UUID:    base
...
C:\Program Files\Oracle\VirtualBox> VBoxManage.exe modifyhd 189ce5d9-31b5-4f81-92ed-054fd52b3a09 --compact
```

※"C:\Program Files\Oracle\VirtualBox\"はVirtualBoxのインストールパス。

**3. ホストOS側: エクスポートする。**

通常時と同様、[ホストPC(私はWindows 10)のOracle VM VirtualBox起動], [対象イメージを選択], [ファイル⇒仮想アプライアンスのエクスポート]の順です。

私が今回試したケースだと、**5.59GByte⇒2.94GByteに削減**！
大分サイズ圧縮されるのでぜひ実施してみてください。

#**お掃除しよう！**

##**気付かず不要となった無駄パッケージの削除**

細かく調べると、/usr/binや/usr/libが大きな割合を占めていました。ということは余分なパッケージを削除しないと容量は減らなそうです。
こんな時に便利なaptコマンドがあります。(yumにもあるはず)

```
apt-get autoremove
apt-get autoclean
```

依存関係のない無駄パッケージを削除してくれます。しばらく使っている環境では、これだけでかなり容量がすっきりすることもあります。
※[apt系コマンドをまとめてくれている記事](https://qiita.com/white_aspara25/items/723ae4ebf0bfefe2115c)がありましたので合わせて共有。

ここで7GByteは切りました。ちょっとすっきり。他にも不要なパッケージがあれば削除しちゃいましょう。

##**不要な linux-image パッケージを削除**

他にパッケージを探す前に検索してみると、[このような記事を発見](https://qiita.com/inohiro/items/5d358c30eb7bacb37c7c)。
いや、インストールしてそんなに立っていないのに、不要なlinuxイメージなんて…普通にありました。
私の**カーネルは`4.15.0-20-generic`なのに、`linux-image-4.15`等があります**。

```
$dpkg -l 'linux-image-*'
Desired=Unknown/Install/Remove/Purge/Hold
| Status=Not/Inst/Conf-files/Unpacked/halF-conf/Half-inst/trig-aWait/Trig-pend
|/ Err?=(none)/Reinst-required (Status,Err: uppercase=bad)
||/ Name                           Version              Architecture         Description
+++-==============================-====================-====================-=================================================================
rc  linux-image-4.15.0-13-generic  4.15.0-13.14         amd64                Linux kernel image for version 4.15.0 on 64 bit x86 SMP
ii  linux-image-4.15.0-15-generic  4.15.0-15.16         amd64                Linux kernel image for version 4.15.0 on 64 bit x86 SMP
ii  linux-image-4.15.0-20-generic  4.15.0-20.21         amd64                Signed kernel image generic
rc  linux-image-extra-4.15.0-13-ge 4.15.0-13.14         amd64                Linux kernel extra modules for version 4.15.0 on 64 bit x86 SMP
ii  linux-image-extra-4.15.0-15-ge 4.15.0-15.16         amd64                Linux kernel extra modules for version 4.15.0 on 64 bit x86 SMP
ii  linux-image-generic            4.15.0.20.23         amd64                Generic Linux kernel image
un  linux-image-unsigned-4.15.0-20 <none>
```

不要なimageは以下コマンドで一括削除出来ます。詳細は[元サイトの参考](https://markmcb.com/2013/02/04/cleanup-unused-linux-kernels-in-ubuntu/)か[余談](https://qiita.com/developer-kikikaikai/items/7deaffd0c9b521e1366c#linux-image%E5%89%8A%E9%99%A4%E3%82%B3%E3%83%9E%E3%83%B3%E3%83%89%E3%81%AB%E3%81%A4%E3%81%84%E3%81%A6)を見てください。

```
dpkg -l 'linux-*' | sed '/^ii/!d;/'"$(uname -r | sed "s/\(.*\)-\([^0-9]\+\)/\1/")"'/d;s/^[^ ]* [^ ]* \([^ ]*\).*/\1/;/[0-9]/!d' | xargs sudo apt-get -y purge
```

##**大きいサイズのパッケージを検索**

[こちらのサイト](https://blog.be-dama.com/2012/09/28/debian%E3%83%91%E3%83%83%E3%82%B1%E3%83%BC%E3%82%B8%E3%82%92%E3%82%B5%E3%82%A4%E3%82%BA%E9%A0%86%E3%81%AB%E4%B8%A6%E3%81%B9%E3%82%8B%E6%96%B9%E6%B3%95/)にパッケージサイズの確認方法が載っていました。
少しコマンドをいじって**インストールされているパッケージのみ、大きい順にサイズ一覧が出る**よう修正。**単位はKByte**です。

```
dpkg-query  -l | grep "^ii" | awk -F" " '{print $2}' | xargs dpkg-query -W -f='${Installed-Size}\t${Package}\n' | sort -nr | less
```

サイズの大きい物から確認し、色々と自分には不必要なパッケージを削除しました。
私が削除したのは以下。

|パッケージ名|用途|
|:-------------|:-------------|
|firefox |ブラウザ|
|thunderbird|Linuxのメーラー|
|libreoffice-core|Windows Office利用の為のOSS|
|libreoffice-common|LibreOfficeがらみ。|
|mythes-en-us|LibreOfficeがらみ。English (USA) Thesaurus for LibreOffice|
|ure|LibreOfficeがらみ。LibreOffice UNO runtime environment|
|orca|視覚障碍者向けのサポートツール|
|libgphoto2-6 |デジタルカメラライブラリ|

こう見るだけでも色々な機能があるんですね、幅広い。
この辺を消したところで全体の60%を切ったのでここらでお掃除完了です。

#**感想**

最初はただ起動できなくなったイメージを起動できるようにするだけと思っていたのですが、今まで困ってたけど仕事では時間が取れず放置していたことが色々頭に浮かんだので半分調査報告の気分で纏めました。
これで大抵の環境内ファイルサイズ系の困りごとは解決できそうかな。いい勉強になりました。

#**追記**

##**簡単バックアップ～スナップショット**

@aaaaAAAA1111さんより、**VirtualBoxのスナップショットが便利**だと伺い試してみました。

使い方は簡単。対象のマシンを選択している状態でVirtualBoxマネージャーのマシンツール→スナップショットを選択し、カメラアイコンの「作成」を押すだけ。
<img width="821" alt="snapshot.png" src="https://qiita-image-store.s3.amazonaws.com/0/252277/a3e53bb8-03bd-1bd7-da3e-7f615190b31c.png">

戻すときは取ってあったスナップショットを選択して「復元」を押します。「復元」 or 「キャンセル」の選択子が出るので「復元」を選ぶと最新状態が上書きされます。

この方法、別マシンへの共有は出来ないですが、とにかくバックアップが速いです。
それ以外にも、

- **起動中でもその瞬間の状態がそのまま保存される**
- 前のスナップをから新たにスナップを作成したりと、**色々な状態のスナップ作成可能**

と、**調査・開発効率向上に効果がありそうな機能**となっています。

コード管理にgitを使われている方は、ちょうどgitのローカルリポジトリにbranchを切るような間隔で、PCの状態を丸ごとブランチ分けするようなイメージが近いんじゃないでしょうか。
そのうち教わった話を整理しつつ、便利な運用例を纏めたいと思います。


ちなみに、せっかく簡単バックアップが出来たのでかたっぱしからサイズの大きいパッケージを消してみました。

```
gvfs gvfs-daemons libgl1-mesa-dri (libgl1-mesa-dri削除の為)
linux-firmware
firefox
linux-modules-extra-4.15.0-20-generic
linux-image-extra-4.15.0-15-generic
libreoffice-core
thunderbird
fonts-noto-cjk
libreoffice-common
linux-headers-4.15.0-20
linux-headers-4.15.0-15
valgrind
linux-image-4.15.0-15-generic
```

ここまでは削除、コードのmake, 実行まで出来るが成功。案外linux-firmwareとかがなくてもコンパイルくらいは出来るんですね。(**※一度でいいから片っ端からパッケージ削除をやってみたかっただけなので、動作の保証はしません**)
最後`linux-modules-4.15.0-20-generic`を削除したところで動かなくなったのでスナップショットを復元。無事元の状態に戻ることが出来ました。
復元も簡単なので、今回のようなお試しの為のバックアップには最適！

#**余談:**
### **snapフォルダ**

検索時に何やら"/snap/"という見慣れないフォルダ発見。
Ubuntu16.04から導入されたシステムで、通常のaptパッケージにある依存関係問題を解消したパッケージ群だそうです。
中身を見ると必要そうなので今回はスルー

詳細は[こちら](https://ubuntuapps.blog.fc2.com/blog-entry-847.html)。興味のある方はどうぞ

また、Ubuntu18.04のsnap gnomeには[日本語周りで不具合がある](https://kledgeb.blogspot.jp/2018/05/ubuntu-1804-98-gnome.html)とのことなので、気になる方は差し替えるといいと思います。私は基本terminalでの使用なので気にしませんが。

### **linux-image削除コマンドについて**

参照よろしくで済まそうと思ったんですが、先日コマンド実行に気を付けましょう的なことを記事にした手前、ぱっと見理解できない難解コマンドをそのまま載せるのは気が引けたので、解説。

やってることはこうです。
1. `dpkg -l 'linux-*'` で一覧表示を表示
2. ` sed '/^ii/!d;/`で、先頭ii(インストールされているもの)だけを表示
3. `"$(uname -r | sed "s/\(.*\)-\([^0-9]\+\)/\1/")"`でkernelのバージョン情報を数字だけ取得し、表示から除外
4. `"s/^[^ ]* [^ ]* \([^ ]*\)"`でスペースをいい感じに削ってName部分を取得
5. `"/[0-9]/!d'"`でバージョン数が含まれるもののみ表示。(3で現在のkernelを除いているので、無駄なkernelイメージだけになります。)
6. `xargs`で`sudo apt-get -y purge`の最後の引数に5を渡して削除

という流れ。これらを全部`sed`で表現してるのは凄いな。
やってることの意味合いとしては以下のような感じと同じですね。

```:スクリプト
kernelname=`uname -r | sed "s/\(.*\)-\([^0-9]\+\)/\1/"`;
LIST=`dpkg -l 'linux-*' | grep "^ii" | grep -v ${kernelname} | awk -F " " '{print $2}'  | grep  "[0-9]"`
for data in $LIST
do
    sudo apt-get -y purge $data
done
```

```:1行
kernelname=`uname -r | sed "s/\(.*\)-\([^0-9]\+\)/\1/"`; dpkg -l 'linux-*' | grep "^ii" | grep -v ${kernelname} | awk -F " " '{print $2}'  | grep  "[0-9]" | xargs sudo apt-get -y purge
```

ちなみに`xargs`について慣れない方に補足。こんな感じで|前の結果を引っ張ってきて次のコマンドに利用します。

```:xargs例
$echo "test1 test2 test3" | xargs touch
touch test1を実行
touch test2を実行
touch test3を実行
$ ls
test1  test2  test3
```

xargsは便利なんですけど、複雑なコマンドの最後にぶち込むと「ちょっとコマンド間違ってた！」みたいなことをやると大変なことになったりするので、自作する時はご注意ください。

### **パッケージ削除について**

完全なメモです。libgl1-mesa-driを消すとGUI系が消えます。wiresharkが使えなくなるのが個人的には嫌なので却下ですが、容量は上位なのでスリム化にはいいかも。(autoremoveで大量にUIを使うパッケージが消えてくれるっぽいです。)

# **参考**

ディスク容量がいっぱいの時にやる事(ncdu, duコマンド)
https://qiita.com/oshou/items/2630f9f1c1131beb748e

[Ubuntu] apt-get まとめ
https://qiita.com/white_aspara25/items/723ae4ebf0bfefe2115c

仮想ディスクの圧縮
http://vboxmania.net/content/%E4%BB%AE%E6%83%B3%E3%83%87%E3%82%A3%E3%82%B9%E3%82%AF%E3%81%AE%E5%9C%A7%E7%B8%AE

Ubuntuで不要なファイルを削除してディスクスペースを確保する
https://qiita.com/inohiro/items/5d358c30eb7bacb37c7c
同記事の参考元(長いコマンドの説明が記載されている)
https://markmcb.com/2013/02/04/cleanup-unused-linux-kernels-in-ubuntu/

debianパッケージをサイズ順に並べる方法
https://blog.be-dama.com/2012/09/28/debian%E3%83%91%E3%83%83%E3%82%B1%E3%83%BC%E3%82%B8%E3%82%92%E3%82%B5%E3%82%A4%E3%82%BA%E9%A0%86%E3%81%AB%E4%B8%A6%E3%81%B9%E3%82%8B%E6%96%B9%E6%B3%95/
dpkg-queryの表示サイズ情報
https://www.debian.org/doc/manuals/debian-reference/pr01.ja.html

snapフォルダ
https://ubuntuapps.blog.fc2.com/blog-entry-847.html
snapフォルダの不具合
https://kledgeb.blogspot.jp/2018/05/ubuntu-1804-98-gnome.html