도커 컨테이너 시간 및 시간대 (변경 사항이 반영되지 않음)


135

Docker 컨테이너는 시간 정보를 어디서 얻습니까? 기본 우분투 : trusty 이미지에서 일부 컨테이너를 만들었으며이를 실행하고 '날짜'를 요청하면 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

무엇을 제공하는지 아는 사람이 있습니까?


3
를 사용하는 경우 먼저 Alpine설치해야합니다. github.com/gliderlabs/docker-alpine/issues/136tzdata
Belter

1
참고로. . . docker build / dockerfile 시간이 아닌 docker 런타임에 컨테이너 시간대를 설정하고 싶습니다. 사용하여 -v /etc/localtime:/etc/localtime:ro작품의 (에 CentOS) 종류. 내부 컨테이너 명령 줄 날짜는 예상 시간대 형식으로 날짜를 반환합니다. 그러나 컨테이너에서 실행되는 jenkins는 시간대가 UTC라고 생각합니다. 왜? / etc / localtime은 빌드 된 컨테이너의 ../usr/share/zoneinfo/UTC에 대한 심볼릭 링크입니다. 컨테이너의 UTC 파일 내용이 이제 새로운 시간대입니다. 그러나 jenkins (및 아마도 다른 Java 기반 소프트웨어)는 여전히 "UTC"인 symlink의 이름을 사용합니다. 솔루션 검색. . .
gaoithe

1
두 가지가 필요합니다. 1. 컨테이너가 생성되면 init 스크립트를 사용하여 / etc / localtime symlink 및 / etc / timezone을 설정하십시오. 2. jenkins 시간대는 두 가지 Java 옵션에서 가져옵니다.이 옵션은 init 스크립트로 전달되어야합니다. jenkins 프로세스를 시작합니다. 예 : "-Dorg.apache.commons.jelly.tags.fmt.timeZone = America / New_York -Duser.timezone = America / New_York". 사과, 이것은 젠킨스 특정이지만 다른 젠킨스 사용자에게 유용합니다.
gaoithe

답변:


208

여기서 비밀은 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


5
Ubuntu : 16.04 (및 다른 버전)를 사용하려면 tzdata이 작업을 수행하기 위해 패키지를 설치 해야합니다 .
Opsse

5
Dockerfile에서 시간대를 하드 코딩하는 것이 현명하지 않다고 생각하는 유일한 사람입니까?
볼프강

1
@Wolfgang 이것은 예입니다. 명령 줄, docker-compose.yml 등과 같은 환경 변수를 제공하는 다른 방법으로 제공 할 수 있습니다.
Michael Hampton

적어도 알파인 기반 이미지의 경우 TZ변수를 설정하는 것만 으로 충분 하다는 것을 알았 습니다. 심볼릭 링크 또는 다른 것을 설정할 필요가 없었습니다.
code_dredd

58

일반적으로 다음과 같이 docker 컨테이너에 환경 변수를 설정하면 충분합니다.

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

물론 이것은 또한 작동합니다 docker-compose.


2
이것은 가장 우아한 방법 인 것 같습니다. 와 같은 일부 기본 이미지 에는 Dockerfile에 추가해야 할 패키지 ubuntu:16.04가 없습니다 tzdata.
Julien Fastré

1
+1-나는 Julien에 동의합니다. 이것은 런타임에 시간대를 설정하는 가장 우아한 방법으로 보입니다. 이것은 CentOS와 잘 작동합니다. 알파인 이미지에는 'tzdata'패키지를 설치해야합니다. 추가 3MB 이미지 페이로드를 견딜 수없는 경우를 제외하고 빌드 시간에 하 코딩 구성보다 선호되는 'tzdata'패키지를 설치해야합니다. :)
Frelling

이것은 좋지만 저에게는 효과가없는 것 같습니다 (CentOS 7.5.1804 및 tzdata-2018e-3.el7.noarch 사용)? 슬픈 얼굴
gaoithe

22

/etc/localtime이미지에 마운트 하여 동기화하는 host -v것이 가장 인기있는 이미지 입니다.

그러나 이슈 12084 참조 :

소프트웨어에서 파일 /etc/timezone을 설정 해야하는 경우 작동하지 않기 때문에 올바르지 않습니다 .
그런 식으로 사용하면 기본값으로 남습니다 etc/UTC.

실제로 도커 컨테이너 안에 표준 시간대를 설정하는 완벽한 방법이 없다는 것을 확인했습니다.
결국이 솔루션에 정착했습니다.

앱 도커 파일 :

# 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특정 국가 또는 지역으로 현지화 된 데이터 볼륨 도커 파일 :

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

... 3 개의 별도 파일이 /etc/localtime포함되어 있으며 모든 런타임 컨테이너 시작 시마다 다시 작성하기 때문에 우아하지 않습니다 . 오히려 낭비입니다.

그러나 제대로 작동하고 기본 앱 이미지와 각 국가 별 로컬 구성을 성공적으로 분리합니다.
3 줄의 코드로


1
나를 위해, 그것은 : RUN echo "Europe/London" > /etc/timezone
jpmottin

@jpmottin 그렇다면 serverfault.com/a/856593/783 에서와 같이 조금 ?
VonC

18

도커 컨테이너에서 로컬 파일 (/ etc / timezone 및 / etc / localtime)을 볼륨으로 추가 할 수 있습니다.

docker-compose.yml다음 줄로 업데이트하십시오 .

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

이제 컨테이너 시간은 호스트와 동일합니다.


CentOS 배포 호스트 echo "Europe/Paris" > /etc/timezone에서 컨테이너를 다시 시작하기 전에 명령을 입력하십시오 .
CrazyMax

MacOS 호스트에서 작동합니까?
Redsandro

MAC에서 작동하지 않음
Marcello de Sales

이것은 MacOS에서 작동했지만 오랜 시간 후에 다시 시도한 결과는 다음과 같습니다. High Sierra 또는 도커 변경으로 인해이 문제가 발생했는지 확실하지 않습니다. "docker : 데몬의 오류 응답 : 마운트 거부 : / etc / localtime 경로가 OS X에서 공유되지 않고 Docker에 알려지지 않았습니다. Docker에서 공유 경로를 구성 할 수 있습니다- > 환경 설정 ...-> 파일 공유. 자세한 내용은 docs.docker.com/docker-for-mac/osxfs/#namespaces 를 참조하십시오 . "
gae123

1
/ etc / localtime이 심볼릭 링크이므로 zoneinfo 데이터베이스가 손상됩니다 (따라서 / usr / share / zoneinfo / Some / Thing은 컨테이너 내부에 / usr / share / zoneinfo / UTC로 마운트 될 수 있음). 호스트의 db 파일과 컨테이너의 db 파일을 혼합한다는 것은 말할 것도 없습니다.
ionelmc

12

우분투 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

1
진지하게 ... 이것은 효과가있는 유일한 솔루션입니다!
Gerrat

1
또한이 작업을 수행해야했습니다-기본적으로 tzdata가 더 이상 일부 배포판에없는 것 같습니다.
Peter

4

다음을 기반으로 도커 이미지를 사용하는 경우 ubuntu:

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

3

정보와 문제에 대한 링크에 대한 VonC에 감사드립니다. 이것은 복잡한 혼란처럼 보이 므로이 문제를 해결하는 방법에 대한 내 자신의 아이디어를 테스트했으며 훌륭하게 작동하는 것 같습니다.

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

(내 시간대를 선택하라는 메시지를 따릅니다)

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

그런 다음 Dockerfile을 다음과 같이 업데이트했습니다.

FROM chocko/ubuntu:local

간과하기가 너무 쉽기 때문에 이것에 문제가있는 것 같습니다.


이것은 또한 시도한 것이지만 시간대 는 컨테이너 후에도 여전히 재설정됩니다 exit. 데비안에 있습니다.
Mike Chamberlain

@MikeChamberlain 위의 Michael Hampton의 답변을 받아 보셨습니까? 나는 그것을 직접 구현하지는 않았지만 그것이받은 공표를 고려할 수있는 방법이라고 생각합니다.
Chockomonkey

2

이 중 몇 가지를 시도했지만 알파인 기반 이미지에서는 작동하지 않았으므로 여기에 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/*

[ 출처 ]


1

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`

기본 이미지가 알파인 (5MB)이고 "tzdata"가 설치되어 있지 않은 경우에는 도움이되지 않습니다.
max4ever
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.