특정 RUN 명령에 대해 캐시 비활성화


103

Docker 이미지를 빌드 할 때마다 RUN실행하려는 Dockerfile에 몇 가지 명령이 -no-cache있습니다.

docker build --no-cache전체 Dockerfile에 대해 캐싱을 비활성화 한다는 것을 이해합니다 .

특정 RUN 명령에 대해 캐시를 비활성화 할 수 있습니까?


1
단일 명령에 대해 캐시를 비활성화 한 후 결과가 캐시 된 이전 실행과 일치하지 않으면 나머지 모든 단계를 다시 빌드해야합니다. 그것이 당신의 목표입니까, 아니면 단일 레이어 만 재 구축하고 어떻게 든 이전에 캐시 된 데이터가 저장된 곳에이를 주입하기를 원합니까?
BMitch

3
예를 들어 "git pull"명령과 같은 특정 레이어를 다시 빌드하고 싶었습니다. 지금은 저장소가 업데이트 되더라도 "git pull"명령이 캐시됩니다.
Vingtoft

2
사용하지 않는 인수를 전달하여 강제로 당기는 것은 쉽습니다. 그러나 캐시 된 항목이 재 구축 된 결과 모든 후속 레이어는 재 구축이 필요합니다. 예제는 여기 내 대답을 참조하십시오 .
BMitch

git 원격이 변경되었을 때 캐시를 무효화하려면 다음을 참조하십시오. Dockerfile 캐싱을 방지하는 방법 git clone . 연결된 답변에 대한 모든 크레딧은 @anq 입니다.
hpgmiskin

답변:


84

캐시를 비활성화하려는 지역 앞에 무의미하고 실행하기 쉬운 명령을 삽입하는 옵션이 항상 있습니다.

이 이슈 주석 에서 제안 된대로 빌드 인수 블록을 추가 할 수 있습니다 (이름은 임의적 일 수 있음).

ARG CACHEBUST=1 

같은 지역 전에 추가하여 각 실행 값을 수정 --build-arg CACHEBUST=$(date +%s)A와 docker build(실행에서의 고유성을 보장하기 위해, 여기에 현재 날짜이며, 값도 임의 일 수있다) 인수.

물론 이것은 중간 이미지의 해시 합계가 다르기 때문에 이후의 모든 블록에 대해서도 캐시를 비활성화합니다. 이는도 커가 현재 작동하는 방식을 고려하여 진정으로 선택적 캐시를 비활성화하여 사소하지 않은 문제를 비활성화합니다.


1
더 이상 작동하지 않는 것 같습니다. 방금 ---> Using cache내``ARG CACHEBUST = 1` 줄 아래에 있습니다 ... (예 --build-arg CACHEBUST=$(date +%s), 도커 명령에서 수행 했습니다)
Pylinux

나에게도 작동하지 않으며 플랫폼에 따라 다를 수 있습니다. ARG 변경으로 인해 캐시가 무효화 될 것으로 예상했을 것입니다.
올리버

6
RUN echo "$CACHEBUST"사용 ARG하면 캐시가 무효화되지 않으므로 추가 해야합니다.
Sidharth V

이 답변은 여기 내 문제를 해결 : stackoverflow.com/questions/63709147/...
샤피로의 yaacov

28

사용하다

ADD "https://www.random.org/cgi-bin/randbyte?nbytes=10&format=h" skipcache

항상 실행하려는 RUN 라인 앞에. 이것은 ADD가 항상 파일 / URL을 가져오고 위의 URL이 각 요청에 대해 임의의 데이터를 생성하기 때문에 작동합니다. 그런 다음 Docker는 결과를 비교하여 캐시를 사용할 수 있는지 확인합니다.

또한 추가 Docker 명령 줄 인수가 필요하지 않고 Docker-compose.yaml 파일에서도 작동하므로이를 테스트하고 잘 작동합니다. :)


3
random.org가 해당 엔드 포인트를 변경하기로 결정하면 어떻게됩니까? 그 행동을 어떻게 제어 하시겠습니까?
안드레스 레온 랑겔

@AndresLeonRangel 분명히 이것은 Docker 기능이 아니지만 Docker 구문과 잘 알려진 웹 서비스를 사용하는 해킹의 일종입니다. "randbyte"끝 점도 찾을 수 없으며 현재 베타 버전 인 새 API가 있습니다. 1) 실패 할 때까지이 엔드 포인트를 계속 사용하거나, 2) 새로운 엔드 포인트를 사용하거나 (실패 할 때까지) 3) 자신의 임의의 엔드 포인트를 작성할 수 있습니다.이 경우 모든 권한이 있습니다. :)
steve

3
이것은 몇 번 실패했습니다 ... 사이트가 다운되었을 때 !!! 나는 이것이 완벽한 해결책이 아니라고 생각합니다. ADD 실패 : 503 상태로 random.org/cgi-bin/randbyte?nbytes=10&format=h 를 가져 오지 못했습니다. 서비스를 사용할 수 없음 : <! DOCTYPE HTML>
Kathi

1
random.org 지금이 솔루션을 나누기 DDOS 보호 기능을 추가했습니다
브래드 루트

이 솔루션을 사용하지 않는 당신의 파이프 라인을 차단하지 않으려면이 빨간색 깜박임 반환 (503)를 작동 주어진하지 않습니다
OlegI

9

직접적으로는 아니지만 Dockerfile을 여러 부분으로 나누고 이미지를 빌드 한 다음 다음 Dockerfile의 시작 부분에있는이 이미지에서 캐싱을 사용하거나 사용하지 않고 이미지를 빌드 할 수 있습니다.


1
이렇게하면 기본 Docker 이미지에서 커밋 된 레이어를 업데이트 할 수 있습니까?
user_mda

7

2016 년 2 월부터는 불가능합니다.

이 기능은 GitHub 에서 요청되었습니다.


5

이 기능은 일주일 전에 추가되었습니다.

ARG FOO=bar

FROM something
RUN echo "this won't be affected if the value of FOO changes"
ARG FOO
RUN echo "this step will be executed again if the value of FOO changes"

FROM something-else
RUN echo "this won't be affected because this stage doesn't use the FOO build-arg"

https://github.com/moby/moby/issues/1996#issuecomment-550020843


0

나는 이것이 위의 @steve의 대답에 약간의 개선이라고 생각합니다.

RUN git clone https://sdk.ghwl;erjnv;wekrv;qlk@gitlab.com/your_name/your_repository.git

WORKDIR your_repository

# Calls for a random number to break the cahing of the git clone
# (/programming/35134713/disable-cache-for-specific-run-commands/58801213#58801213)
ADD "https://www.random.org/cgi-bin/randbyte?nbytes=10&format=h" skipcache
RUN git pull

이것은 git 클론의 Docker 캐시를 사용하지만 저장소의 캐시되지 않은 업데이트를 실행합니다.

나타납니다 일에, 그리고 빠른 -하지만 많은 감사는 기본 원칙을 제공 @ 스티브 할 수 있습니다.


-2

또 다른 빠른 해킹은 명령 전에 임의의 바이트를 작성하는 것입니다.

RUN head -c 5 /dev/random > random_bytes && <run your command>

캐시 미스를 강제하는 5 개의 임의 바이트를 작성합니다.


10
이러한 임의의 바이트를 쓴 결과도 캐시되므로 해당 명령 이전에 파일이 변경되지 않은 경우 명령을 다시 실행하지 않습니다. 이것은 아무것도 해결하지 못합니다.
Icy Defiance
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.