web-dev-qa-db-ja.com

Dockerコンテナの時間とタイムゾーン(変更は反映されません)

Dockerコンテナーはどこで時間情報を取得しますか?基本的なubuntu:trustyイメージからいくつかのコンテナーを作成し、それを実行して 'date'を要求すると、UTC時間を取得します。

しばらくの間、Dockerfileで次のようにすることでこれを回避しました。

RUN Sudo echo "America/Los_Angeles" > /etc/timezone

ただし、何らかの理由で動作を停止しました。オンラインで検索すると、以下の提案が表示されました。

docker run -v /etc/timezone:/etc/timezone [image-name]

これらの方法はどちらもタイムゾーンを正しく設定します!

$ cat /etc/timezone
America/Los_Angeles
$ date
Tue Apr 14 23:46:51 UTC 2015

誰が何を与えるか知っていますか?

159
Chockomonkey

ここでの秘密は、dpkg-reconfigure tzdata/etc/localtime内のファイルへのコピー、ハードリンク、またはシンボリックリンク(シンボリックリンクが推奨)として/usr/share/zoneinfoを作成するだけであることです。したがって、Dockerfileから完全にこれを行うことができます。考慮してください:

ENV TZ=America/Los_Angeles
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone

おまけとして、TZもコンテナーに正しく設定されます。

これはディストリビューションに依存しないため、ほとんどすべてのLinuxで動作します。

注:アルパインベースのイメージを使用している場合は、最初にtzdataをインストールする必要があります。 (この問題を参照 ここ

このように見えます:

RUN apk add --no-cache tzdata
ENV TZ America/Los_Angeles
235
Michael Hampton

通常、次のように、Dockerコンテナに環境変数を設定するだけで十分です。

docker run -e TZ=Europe/Amsterdam debian:jessie date

もちろん、これはdocker-composeでも機能します。

68
Victor Klos

ローカルファイル(/ etc/timezoneおよび/ etc/localtime)をdocker-containerのボリュームとして追加できます。

docker-compose.yml次の行を追加します。

volumes:
    - "/etc/timezone:/etc/timezone:ro"
    - "/etc/localtime:/etc/localtime:ro"

これで、コンテナの時間はホストと同じになります

23
thhan

イメージに/etc/localtimeをマウントして、Host -vと同期するのが最も一般的なマウントです。

しかし issue 12084 を参照してください:

ソフトウェアがファイル/etc/timezoneを設定する必要がある場合は機能しないため、正しくありません。
このように使用すると、デフォルト値etc/UTCのままになります。

実際、Dockerコンテナー内にタイムゾーンを設定するための簡単で洗練された方法はないと判断しました。
それで、ようやくこのソリューションに落ち着きました:

アプリのdockerfile:

# Relocate the timezone file
RUN mkdir -p /config/etc && mv /etc/timezone /config/etc/ && ln -s /config/etc/timezone /etc/

アプリのエントリポイントスクリプト:

# Set timezone as specified in /config/etc/timezone
dpkg-reconfigure -f noninteractive tzdata

特定の国または地域にローカライズされたデータ量/config dockerfile:

# Set the time zone
RUN echo "Europe/London" > /config/etc/timezone

... 3つの個別のファイルを含み、ランタイムコンテナーの開始ごとに/etc/localtimeを再作成するため、エレガントではありません。これはかなり無駄です。

ただし、これは正しく機能し、ベースアプリイメージと国ごとのローカライズされた構成の分離に成功します。
3行のコード。

22
VonC

Ubuntu 16.04画像にバグがあります。解決策は

    ENV TZ 'Europe/Tallinn'
    RUN echo $TZ > /etc/timezone && \
    apt-get update && apt-get install -y tzdata && \
    rm /etc/localtime && \
    ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && \
    dpkg-reconfigure -f noninteractive tzdata && \
    apt-get clean
12
qwerty

ubuntuに基づくDockerイメージを使用している場合:

# Change the docker default timezone from UTC to SGT
echo "Asia/Singapore" > /etc/timezone
dpkg-reconfigure tzdata
date
4
Xianlin

ここに2セントを追加します。これは、これらのいくつかを試しましたが、アルパインベースのイメージでは機能しなかったためです。

しかし、これはトリックをしました:

ENV TZ=America/Toronto
RUN apk update
RUN apk upgrade
RUN apk add ca-certificates && update-ca-certificates
RUN apk add --update tzdata
RUN rm -rf /var/cache/apk/*

[ ソース ]

4
Alpha

情報と問題へのリンクを提供してくれたVonCに感謝します。これは非常に複雑な混乱のように思えるので、私はこれを解決する方法について自分自身のアイデアでいくつかのテストを行い、それはうまく機能しているようです。

>docker run -it ubuntu:trusty /bin/bash
#dpkg-reconfigure tzdata

(プロンプトに従ってタイムゾーンを選択してください)

>docker commit [container-id] chocko/ubuntu:local

次に、これを反映するようにDockerfileを更新しました。

FROM chocko/ubuntu:local

見落とすのは簡単すぎると思われるので、これには何か問題があるに違いありません...それともこれは受け入れられますか?

3
Chockomonkey

docker run引数でタイムゾーンを設定するより一般的な方法:

-e TZ=`ls -la /etc/localtime | cut -d/ -f8-9`

または再利用のために:

function GET_TZ () {
    ls -la /etc/localtime | cut -d/ -f8-9
}

...
-e TZ=`GET_TZ`
1
Mugen