94 lines
7.4 KiB
Markdown
94 lines
7.4 KiB
Markdown
---
|
|
title: "Gradle Working With Files — Reproducible Archives (sec:reproducible_archives)"
|
|
source_type: official-doc
|
|
url: https://docs.gradle.org/current/userguide/working_with_files.html#sec:reproducible_archives
|
|
archive_url:
|
|
vendor: Gradle
|
|
related_branches: [feature-build-release-supply-chain-contract]
|
|
related_projects: []
|
|
tags: [official-doc, ci-cd, gradle, reproducible-builds, supply-chain]
|
|
created: 2026-06-15
|
|
---
|
|
|
|
# Gradle Working With Files — Reproducible Archives (sec:reproducible_archives)
|
|
|
|
> Layer: `raw/` — 공식 문서 원문 발췌·출처 기록.
|
|
> 검증된 요약은 `/ingest` 후 `wiki/concepts/`에 `source-summary-template` 형식으로 별도 작성. 원본은 raw에 영구 보관.
|
|
|
|
## Parent / 활용 branch
|
|
|
|
| Branch | 이 자료가 정당화하는 결정 |
|
|
|---|---|
|
|
| [[raw/branch-notes/feature-build-release-supply-chain-contract]] | Decision D10 — `preserveFileTimestamps=false` / `reproducibleFileOrder=true` 의 Gradle 공식 API 명세: 각 property 가 무엇을 하며, `tasks.withType<AbstractArchiveTask>().configureEach {}` 패턴으로 전역 적용하는 방법 |
|
|
|
|
## 출처 / Source
|
|
|
|
- 원본 URL: https://docs.gradle.org/current/userguide/working_with_files.html#sec:reproducible_archives
|
|
- 보조 URL (DSL reference): https://docs.gradle.org/current/dsl/org.gradle.api.tasks.bundling.AbstractArchiveTask.html
|
|
- 보조 URL (Javadoc): https://docs.gradle.org/current/javadoc/org/gradle/api/tasks/bundling/AbstractArchiveTask.html
|
|
- 아카이브 URL: (미등록)
|
|
- 저자 / 조직: Gradle (https://gradle.org)
|
|
- 발행일: (Gradle 공식 문서 — 버전 릴리즈마다 갱신)
|
|
- 마지막 확인일: 2026-06-15
|
|
|
|
## 왜 저장했는지 / Why archived
|
|
|
|
`feature-build-release-supply-chain-contract` 의 D10 결정 (`preserveFileTimestamps=false`, `reproducibleFileOrder=true` 를 `AbstractArchiveTask` 에 적용) 은 `UNSUPPORTED_DECISION` 으로 라벨되어 있었다. 본 자료는 두 property 의 공식 API 명세와 전역 적용 DSL 예시를 제공하며, D10 을 `official-vendor-doc` 강도로 승격하는 근거다.
|
|
|
|
## 핵심 인용 / Key quotes (verbatim)
|
|
|
|
> [§preserveFileTimestamps, DSL reference / Javadoc] "Specifies whether file timestamps should be preserved in the archive. If `false` this ensures that archive entries have the same time for builds between different machines, Java versions and operating systems."
|
|
|
|
> [§reproducibleFileOrder, DSL reference / Javadoc] "Specifies whether to enforce a reproducible file order when reading files from directories. Gradle will then walk the directories on disk which are part of this archive in a reproducible order independent of file systems and operating systems. This helps Gradle reliably produce byte-for-byte reproducible archives."
|
|
|
|
> [§sec:reproducible_archives, Kotlin DSL code example]
|
|
> ```kotlin
|
|
> tasks.withType<AbstractArchiveTask>().configureEach {
|
|
> preserveFileTimestamps = false
|
|
> reproducibleFileOrder = true
|
|
> }
|
|
> ```
|
|
|
|
> [§sec:reproducible_archives, Groovy DSL code example]
|
|
> ```groovy
|
|
> tasks.withType(AbstractArchiveTask) {
|
|
> preserveFileTimestamps = false
|
|
> reproducibleFileOrder = true
|
|
> }
|
|
> ```
|
|
|
|
## Claims Extracted / 추출된 주장
|
|
|
|
> 이 자료가 **직접 말하는 것만** claim 으로 분리한다. 내 프로젝트에 적용한 결론은 여기 쓰지 않는다.
|
|
|
|
| Claim ID | Claim (이 자료가 직접 말하는 것) | Evidence quote | Strength | Applies to | Does not prove |
|
|
|---|---|---|---|---|---|
|
|
| GRADLE-RA-C1 | `preserveFileTimestamps=false` 로 설정하면 archive entry 타임스탬프가 기계·JVM 버전·OS 와 무관하게 동일해진다 | [§preserveFileTimestamps] "If `false` this ensures that archive entries have the same time for builds between different machines, Java versions and operating systems." | `official-vendor-doc` | Gradle `AbstractArchiveTask` 를 상속한 모든 archive task (Zip, Jar, Tar, War, Ear 포함) | 특정 timestamp 값이 무엇인지 (1980-01-01 0:00 등) 는 본 인용이 직접 명시하지 않음; 다른 비결정성 요소(클래스파일 내 날짜, JDK 자체 출력물) 는 별도 제거 필요 |
|
|
| GRADLE-RA-C2 | `reproducibleFileOrder=true` 로 설정하면 Gradle 이 디렉터리를 OS·파일시스템과 무관한 순서로 탐색하여 byte-for-byte reproducible archive 를 생성할 수 있다 | [§reproducibleFileOrder] "Gradle will then walk the directories on disk which are part of this archive in a reproducible order independent of file systems and operating systems. This helps Gradle reliably produce byte-for-byte reproducible archives." | `official-vendor-doc` | Gradle `AbstractArchiveTask` 를 상속한 모든 archive task | "helps produce" 표현 — 다른 비결정성 원인(타임스탬프, 컴파일 출력 등)이 함께 제거되어야 실제 byte-for-byte 재현 가능. 본 property 단독으로는 충분조건 아님 |
|
|
| GRADLE-RA-C3 | `tasks.withType<AbstractArchiveTask>().configureEach {}` 블록으로 두 property 를 전역 일괄 적용하는 것이 Gradle 공식 권장 패턴이다 | [§sec:reproducible_archives, Kotlin DSL] `tasks.withType<AbstractArchiveTask>().configureEach { preserveFileTimestamps = false; reproducibleFileOrder = true }` | `official-vendor-doc` | Gradle build scripts (Kotlin DSL / Groovy DSL 모두) | 특정 Gradle 버전 최소 요구사항은 본 인용에서 명시되지 않음; `configureEach` vs 직접 호출 차이(lazy vs eager)는 본 claim 범위 밖 |
|
|
|
|
## Usage Boundaries / 적용 경계
|
|
|
|
- 이 자료가 직접 증명하는 것:
|
|
- `GRADLE-RA-C1`: `preserveFileTimestamps=false` 가 빌드 환경(기계/JVM/OS) 간 archive entry 타임스탬프를 통일한다
|
|
- `GRADLE-RA-C2`: `reproducibleFileOrder=true` 가 파일시스템 순서 의존성을 제거하여 byte-for-byte reproducible archive 에 기여한다
|
|
- `GRADLE-RA-C3`: `tasks.withType<AbstractArchiveTask>().configureEach {}` 가 두 property 전역 적용 패턴임을 공식 문서가 보여준다
|
|
- 이 자료가 증명하지 않는 것:
|
|
- 두 property 만 설정하면 완전한 reproducible build 가 보장된다는 것 (C2의 "helps" 표현 — 타임스탬프 entropy, JDK 버전 고정, 컴파일러 출력 결정론 등 추가 조건 필요)
|
|
- 특정 Gradle 버전에서 이 property 가 도입된 시점
|
|
- CI 환경(GitHub Actions 등) 에서의 실제 적용 검증
|
|
- 내 프로젝트에 적용하려면 추가 확인이 필요한 것:
|
|
- ca-skeleton 의 `build.gradle.kts` 에 `tasks.withType<AbstractArchiveTask>().configureEach {}` 블록 실제 적용 후 동일 commit 2회 빌드 → artifact SHA-256 비교 (`Claims To Verify` 항목)
|
|
- JDK 버전 고정 (`.tool-versions` 또는 `gradle/wrapper/`) 병행 여부 — D10 에서 함께 명시된 조건
|
|
|
|
## 메모 / Notes
|
|
|
|
- C2 의 "helps Gradle reliably produce byte-for-byte reproducible archives" 는 충분조건이 아닌 기여 표현. D10 의 "동일 commit 2회 build → artifact hash 일치" 테스트 계약은 이 두 property + JDK pin 조합의 실증으로 보완해야 한다.
|
|
- DSL reference 와 Javadoc 두 출처가 동일 verbatim 을 반환 — 설명이 단일 소스에서 생성된 것으로 보임.
|
|
- D10 의 Supporting Claims 를 `GRADLE-RA-C1`, `GRADLE-RA-C2`, `GRADLE-RA-C3` 로 갱신하면 `UNSUPPORTED_DECISION` 라벨 제거 가능.
|
|
|
|
## Related / 관련
|
|
|
|
- 같은 주제 Gradle 공식 문서: [[raw/official-docs/supply-chain-gradle-vs-maven-dependency-locking]] (dependency locking)
|
|
- 이 자료를 인용한 wiki 요약: (생성 시 추가)
|