Dockerコンテナ上のElasticsearchのデータを永続化する

[5分でMacにDockerをインストールしてElasticsearchを起動する](https://qiita.com/matyahiko2831/items/dd64aa91f2b03e50f05d)
の続編です。

Dockerコンテナ上のElasticsearchのデータを永続化してみました。

# やりたいこと
- コンテナ上に状態を持たずにデータを永続化する
- docker-composeを書いてみる

# 前提
- MacOSであること
- Dockerがインストール済であること
- Gitがインストール済であること
- "**~/DockerWorkspace**"というディレクトリで作業します

# 手順
## docker-compose.ymlの作成
```docker-compose.yml
version: '3.3'
services:
  elasticsearch:
    # Docker Hubからイメージを取得
    image: elasticsearch
    ports:
      - "9200:9200"
    expose:
      - 9300
    volumes:
      # コンテナのディレクトリをvolumeへマウント
      # ボリューム名:マウント対象のパス
      - es-data:/usr/share/elasticsearch/data

volumes:
  es-data:
    # ボリューム'es-data'はlocalに保存します
    driver: local
```

### docker-composeとは
>Compose とは、複数のコンテナを使う Docker アプリケーションを、定義・実行するツールです。
>Compose はアプリケーションのサービスの設定に、Compose ファイルを使います。
>そして、コマンドを１つ実行するだけで、設定した全てのサービスを作成・起動します。
>(引用元:http://docs.docker.jp/compose/overview.html)

ということは、単一コンテナの場合、あんまり意味ない？
複数コンテナ起動は別の機会に試します。。。

### ボリューム(volume)とは
>データ・ボリューム (data volume) とは、１つまたは複数のコンテナ内で、特別に設計されたディレクトリであり、 ユニオン・ファイルシステム (Union File System) をバイパス（迂回）するものです。データ・ボリュームは、データの保持や共有のために、複数の便利な機能を提供します。
>データ・ボリュームは、データ保持のために設計されており、コンテナのライフサイクルとは独立しています。
>そのため、コンテナの削除時、Docker は 決して 自動的にボリュームを消さないだけでなく、コンテナから参照されなくなっても”後片付け”をせず、ボリュームはそのままです。
>(引用元:http://docs.docker.jp/engine/userguide/dockervolumes.html)

データ保存用のコンテナ。

## docker-composeをもとにコンテナを作成
```
$ docker-compose up
```

## ボリュームが作成されたことを確認
```
$ docker volume ls
docker volume ls
DRIVER              VOLUME NAME
local               dockerworkspace_es-data
```

## Elasticsearchの動作確認およびデータ投入
```
$ curl -XGET localhost:9200

$ curl -H 'Content-Type: application/json'  -XPOST http://localhost:9200/test_index/user -d '{"name":"hoge"}'

$ curl -X GET http://localhost:9200/test_index/user/_search?pretty
{
  "took" : 56,
  "timed_out" : false,
  "_shards" : {
    "total" : 5,
    "successful" : 5,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : 1,
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "test_index",
        "_type" : "user",
        "_id" : "AWP4DjXGGsoch-083Epu",
        "_score" : 1.0,
        "_source" : {
          "name" : "hoge"
        }
      }
    ]
  }
}
```

## コンテナを停止させる
```
$ docker stop <CONTAINER ID>
```
あるいは`control + c`

## ボリュームが削除されていないことを確認
```
$ docker volume ls
DRIVER              VOLUME NAME
local               dockerworkspace_es-data
```

## 再度、コンテナ起動
```
$ docker-compose up
```

## Elasticsearchのデータがコンテナ停止前の状態であることを確認
```
$ curl -X GET http://localhost:9200/test_index/user/_search?pretty
{
  "took" : 72,
  "timed_out" : false,
  "_shards" : {
    "total" : 5,
    "successful" : 5,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : 1,
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "test_index",
        "_type" : "user",
        "_id" : "AWP4DjXGGsoch-083Epu",
        "_score" : 1.0,
        "_source" : {
          "name" : "hoge"
        }
      }
    ]
  }
}
```

次は下記をおさえていきたいです。

- 複数コンテナの操作
- docker push

# 参考にさせていただいたサイト
- [JavaエンジニアのためのDocker入門 - Speaker Deck]
(https://speakerdeck.com/sammy7th/javaenziniafalsetamefalsedockerru-men)
- [2018年の最先端バックエンドエンジニアに必要なスキルについて考えてみました。](https://qiita.com/poly_soft/items/fb649573c19b7a5c0227)
- [localhost上にDockerでコンテナ化したElasticsearchクラスタを立てて自分用コマンド検索エンジンを作る](https://tech.recruit-mp.co.jp/infrastructure/docker-elasticsearch/)
- [Dockerfileとdocker buildコマンドでDockerイメージの作成](http://www.atmarkit.co.jp/ait/articles/1407/08/news031.html)
- [DockerのVolume機能について実験してみたことをまとめます](https://qiita.com/namutaka/items/f6a574f75f0997a1bb1d)