re:dash on DockerでHTTP Proxy考慮して試してみる（2017/04版）

本家re:dashがDocker化したものを提供しているのでRancher化したかったのだけど、上手く行かず、ひとまずDocker実行出来るようにした。

また、現状(2017/4)の段階で、巷にあふれるre:dashのdocker実行の記事が古く、現状と構成が変わっていたのでメモも兼ねて残しています。

## やった事

* HTTP_Proxyの考慮
* 管理用DBはコンテナ外のPostgreSQLを使用
* Rancherの都合で、DockerのVer.は固定

## 前提条件

* Ubuntu Server 16.04 LTS
* DockerをインストールするホストのIPアドレスは、```192.168.1.9```とする
* re:dashからメール送信につかうSMTPサーバは認証無し
* re:dash用の管理DBは事前に空の状態で作成済み

## DockerのHTTP Proxy設定インストール

Dockerのインストールの前に、HTTP Proxyの設定を行い、インストールを実施します。
その後、Ver.を固定します。

### Docker向けにHTTP Proxyの設定を追加

外部接続する際にHTTP Proxyを使用している場合の為に、HTTP_PROXYの設定を追加。
また、ローカルサーバ間はHTTP Proxyが逆にじゃまになるので、ローカルサーバはHTTP Proxyを中継しないように、必要な分だけ１つずつ、IPアドレスを追加。

また、SMTPサーバがローカルサーバなら、no_proxyに追加しておく

#### Upstart and SysVinit向けのHTTP Proxyの設定

```
$ sudoedit /etc/default/docker
```

``` /etc/default/docker
export http_proxy="http://（proxyのIP）:（proxyのポート）/"
export https_proxy="http://（proxyのIP）:（proxyのポート）/"

export no_proxy="127.0.0.1,localhost,（内部のサーバのIP）"
```

#### systemd向けのHTTP Proxyの設定

```
$ sudo mkdir -p /etc/systemd/system/docker.service.d/
$ sudoedit /etc/systemd/system/docker.service.d/http-proxy.conf
```

```http-proxy.conf
[Service]
Environment="HTTP_PROXY=http://（proxyのIP）:（proxyのポート）/" "HTTPS_PROXY=http://（proxyのIP）:（proxyのポート）/" "NO_PROXY=127.0.0.1,localhost,（内部のサーバ）"
```

## Dockerのインストール

### Rancher用に、使用するVer.を固定して Dockerを利用する場合

その後、Dockerのオーケストレーションツール [Rancher](http://docs.rancher.com/rancher/v1.5/en/) を利用したいので、Rancherのドキュメントにある方法（[Getting Started with Hosts](http://docs.rancher.com/rancher/v1.5/en/hosts/)）でDockerをインストール

```
$ curl https://releases.rancher.com/install-docker/1.12.sh | sh
```

### docker-engineのVer.を固定

```
$ sudo apt-mark hold docker-engine 
```

### 固定できているか確認

updateリストには出るけどインストールは保留される

```
$ sudo apt update
$ sudo apt upgrade
パッケージリストを読み込んでいます... 完了
依存関係ツリーを作成しています                
状態情報を読み取っています... 完了
アップグレードパッケージを検出しています... 完了
以下のパッケージは保留されます:
  docker-engine
　：
```

### 最新の安定版のDocker CEインストールしたい場合

Rancher使わないので、最新で良いよって人は下記でインストール

```
$ curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
$ sudo add-apt-repository \
       "deb [arch=amd64] https://download.docker.com/linux/ubuntu \
       $(lsb_release -cs) \
       stable"
$ sudo apt-get update
$ sudo apt-get -y install docker-ce
```

### rootじゃなくてもdockerを実行出来るようにする

cf. [Post-installation steps for Linux](https://docs.docker.com/engine/installation/linux/linux-postinstall/)

```
$ sudo groupadd docker
$ sudo usermod -aG docker $USER
```

## インストールしたdockerの動作確認

```
$ docker run hello-world
Unable to find image 'hello-world:latest' locally
latest: Pulling from library/hello-world
78445dd45222: Pull complete 
　
　：

For more examples and ideas, visit:
 https://docs.docker.com/engine/userguide/
```

※実行できない場合は、再起動すると治る（再起動なしでも出来ないものかなぁ）

```
$ sudo reboot
```

## [docker-composeのインストール](https://docs.docker.com/compose/install/#upgrading)

```
$ sudo -i
# curl -L https://github.com/docker/compose/releases/download/1.12.0-rc2/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose
# chmod +x /usr/local/bin/docker-compose
```

## re:dashのインストール

ここからが本題。
[Setting up a Redash instance](https://redash.io/help-onpremise/setup/setting-up-redash-instance.html) を参考にDocker compose使ってre:dashを起動する

### re:dashを任意の場所にclone

```
$ git clone https://github.com/getredash/redash.git
$ cd redash
```

### Docker Composeで使用するデフォルトの環境変数ファイルを作成

Docker Composeはデフォルトで ```.env``` を読み込んでそこにある環境変数を使用するので、re:dashで使う環境変数として、表に出したくない DBのID/PW 等の環境変数を作成

redashディレクトリ直下に .envを作成

```".env"
# Docker Compose default environment
HTTP_PROXY=http://（proxyのIP）:（proxyのポート）
HTTPS_PROXY=http://（proxyのIP）:（proxyのポート）
NO_PROXY=127.0.0.1,localhost,（内部のサーバのIP）
MAIL_SERVER=（SMTPサーバのIP）
COOKIE_SECRET=sugoihimitunocookie
DB_USER=（事前に作成したデータベースredashへアクセス出来る PostgreSQLのID）
DB_PW=（DB_USERのIDのPW）
```

### docker-compose.production.ymlを変更

cloneしたディレクトリにある ```docker-compose.production.yml``` を以下のように変更

#### ポイント

* ```REDASH_DATABASE_URL``` に、外部のPostgreSQLを指定
   * 使用するPostgreSQLのデータベース名は"redash"
* ```REDASH_DATE_FORMAT``` を "YYYY/MM/DD"として日時表示を指定
* ```REDASH_MAIL_SERVER``` にSMTPサーバを指定
   * 認証が必要な場合は ```REDASH_MAIL_USERNAME``` と ```REDASH_MAIL_PASSWORD``` を追加する
   * その他に必要な設定は、 [Mail Configuration](https://redash.io/help-onpremise/setup/setting-up-redash-instance.html#mail-configuration) にある環境変数を必要に応じて追加する

```docker-compose.production.yml
version: '2'
services:
  server:
    build: .
    command: server
    depends_on:
      - redis
    ports:
      - "5000:5000"
    environment:
      PYTHONUNBUFFERED: 0
      REDASH_LOG_LEVEL: "INFO"
      REDASH_REDIS_URL: "redis://redis:6379/0"
      REDASH_DATABASE_URL: "postgresql://${DB_USER}:${DB_PW}@（DBサーバ）/redash"
      REDASH_COOKIE_SECRET: ${COOKIE_SECRET}
      HTTP_PROXY: ${HTTP_PROXY}
      HTTPS_PROXY: ${HTTPS_PROXY}
      NO_PROXY: ${NO_PROXY}
      REDASH_STATSD_HOST: 192.168.1.9
      REDASH_HOST: "http://192.168.1.9"
      REDASH_DATE_FORMAT: YYYY/MM/DD
      REDASH_MAIL_SERVER: ${MAIL_SERVER}
      REDASH_MAIL_PORT: 25
      REDASH_MAIL_DEFAULT_SENDER: "do-not-send@redash-admin.jp"
  worker:
    build: .
    command: scheduler
    environment:
      PYTHONUNBUFFERED: 0
      REDASH_LOG_LEVEL: "INFO"
      REDASH_REDIS_URL: "redis://redis:6379/0"
      REDASH_DATABASE_URL: "postgresql://${DB_USER}:${DB_PW}@（DBサーバ）/redash"
      QUEUES: "queries,scheduled_queries,celery"
      WORKERS_COUNT: 2
      HTTP_PROXY: ${HTTP_PROXY}
      HTTPS_PROXY: ${HTTPS_PROXY}
      NO_PROXY: ${NO_PROXY}
      REDASH_STATSD_HOST: 192.168.1.9
      REDASH_HOST: "http://192.168.1.9"
      REDASH_DATE_FORMAT: YYYY/MM/DD
      REDASH_MAIL_SERVER: ${MAIL_SERVER}
      REDASH_MAIL_PORT: 25
      REDASH_MAIL_DEFAULT_SENDER: "do-not-send@redash-admin.jp"
  redis:
    image: redis:2.8
    environment:
  nginx:
    image: redash/nginx:latest
    environment:
    ports:
      - "80:80"
    depends_on:
      - server
    links:
      - server:redash
````

## 使用するコンテナイメージを作成後、DB初期化

```
$ docker-compose -f docker-compose.production.yml run --rm server create_db
```

## 実行

```
$ docker-compose -f docker-compose.production.yml up
```

ブラウザで ```REDASH_STATSD_HOST``` に指定したホストを指定（```http://192.168.1.9```）してアクセス

## 簡単に使ってみて分かった事

### timestamp with timezoneの考慮の未対応

* クエリの表示結果の表示フォーマットは、 で指定できたが、表示している結果はUTCのままになっていて、JSTに表示はしてくれない（timezoneの考慮が無いみたい）

公式でもissueが挙がっていて、ユーザ単位にtimezoneを指定できるようにするっぽいのだが、時間がかかりそう。
cf. [User configuration for date/time format & default timezone](https://github.com/getredash/redash/issues/618)

なので、JSTでどうしてもダッシュボード作成したい場合、+9時間する必要があるので、クエリ作成時に、```hour at time zone 'JST'```または```timezone('JST', hour) as hour``` とするとtimestampをJSTに置き換え出来るので一旦はそれで逃げる。

### ダッシュボードのURLについて

* ダッシュボードの新規作成時にURLが確定するが、その後、ダッシュボード名を変更してもURLは変わらない
* ダッシュボード名に日本語を使うとURLが"-"になってしまう

ダッシュボード名が英語オンリーだと非エンジニアに非常に受けが悪いので、実運用する場合は、ダッシュボード新規作成時に半角英数でURLに使えるように作成し、その後に日本語に変える対応を行う。

### ダッシュボードへのアクセス制御

* ダッシュボード毎にアクセス出来るユーザに対して、アクセス制御やR/W制御もしたいがやり方が分からない

アクセス制御程度なら、re:dashの上にリバプロを追いて、URLで判断する？

## 参考

[Setting up a Redash Instance](https://redash.io/help-onpremise/setup/setting-up-redash-instance.html)
[Control and configure Docker with systemd > HTTP proxy](https://docs.docker.com/engine/admin/systemd/#http-proxy)
[Rancher JP](http://www.rancher.jp/)
[Rancher Labs](http://rancher.co.jp/)
[Docker Compose と Rails(+MySQL) で開発環境作成したときに気になったポイント](http://qiita.com/nak1114/items/1f7d48ff661555726427)
[Slash Docker was created to help those who are using Docker for development.](https://runnable.com/docker/)
[RedashをDockerで起動する（2017年3月版）](http://qiita.com/wizpra-koyasu/items/aa8b3fc069816d91ae05)