Github Actions - Artifact

2025. 10. 13. 17:19CI\CD/Github Actions

반응형

Artifact

아티팩트는 워크 플로우의 Job의 Step에서 만든 결과물을 파일로 저장하고 같은 워크플로우의 다른 Job에 넘겨 사용하거나 실행이 끝난 뒤 사람이 다운로드 해서 확인하거나 다른 워크플로우의 잡에서 받아서 후속 작업을 하도록 하는 저장물이다.

이는 Job끼리는 병렬로 실행되며 각자 다른 러너에 의해서 실행되기에 파일이 연속적으로 유지되지 않기 때문에 사용되는 기술이다.

업로드 : upload-artifact

아티팩트는 업로드라는 것을 통해서 원하는파일을 저장하여 하나의 아티팩트로 만들어준다.

이때 이 업로드는 Job의 Step에서 이뤄지며 uses에 actions/upload-artifact@버전 을 사용해서 아티팩트를 만든다.

uses: actions/upload-artifact@v4

 

이 업로드 액션에는 with구문을 추가해서 input을 추가할 수 있는데 이는 아래와 같다.

 

1) name(선택, default : artifact)

name은 아티팩트의 명칭을 지정한다, 이는 하나의 워크플로우 안에서 동일한 아티팩트 name값이 존재하면 안된다

설정하지 않을 경우 기본값인 artifact로 설정되며 미지정한 name이 두개 이상일 경우 값의 중복으로 에러가 난다.

- uses: actions/upload-artifact@v4
  with:
    name: build-artifacts

 

2) path(필수)

업로드할 파일, 디렉터리, 와일드카드 경로를 지정한다(여러 줄로 여러개 설정 가능)

- uses: actions/upload-artifact@v4
  with:
    name: build-artifacts
    path: |
      dist/**
      reports/*.xml

 

3) if-no-files-found(선택, default : warn)

path에 매칭되는 파일이 없을 경우 동작을 지정한다.

값으로는 warn(파일이 없다면 경고만 남기고 계속 진행한다) / error(파일을 못찾으면 스탭이 실패한다) / ignore(파일이 없어도 아무 로그 없이 통과시킨다) 을 지정할 수 있다.

- uses: actions/upload-artifact@v4
  with:
    name: build-artifacts
    path: |
      dist/**
      reports/*.xml
    if-no-files-found: error   # 없으면 실패 처리

 

4) retention-days(선택, default : organization/repo의 설정에 따름)

보관 일 수 로 만료되면 삭제된다

최소 1일에서 최대 90일까지 지정이 가능하다.

이는 조직 혹은 레포지토리의 정책 상한에 따라 책정되기에 변경될 가능성이 있다.

- uses: actions/upload-artifact@v4
  with:
    name: build
    path: dist/**
    retention-days: 30  # 조직/레포 정책이 14일이면 14일로 캡됨

 

5) compression-level(선택, default : 6)

업로드시 Zlib 압축 레벨로 0에서 9 사이로 지정이 가능 하며 압축을 많이 할 수록 속도가 빨라지고 압축을 덜 할 수 록 속도가 느려진다.

내용이 이미 압축되어 있는 zip, jar, war, tar 등의 파일이나 압축을 해도 그렇게 이득을 보지 않는 포멧의 bin, iso, db 덤프파일, sqlite파일등의 파일이나 압축이 잘 되지 않는 대용량의 파일의 경우는 0을 두는 것이 좋고 

텍스트 위주의 산출물이나 소형 산출물의 경우는 9나 6을 둬서 압축을 하는 것이 용량 절감 효과가 좋다.

# 이미 압축/대용량 바이너리 → 압축 안 함
- uses: actions/upload-artifact@v4
  with:
    name: binaries
    path: |
      build/**/*.zip
      media/**/*.mp4
      model/**/*.pt
    compression-level: 0

# 텍스트/로그 → 압축 강화
- uses: actions/upload-artifact@v4
  with:
    name: logs
    path: logs/**/*.log
    compression-level: 9

 

6) overwrite(선택, default : false)

같은 이름의 아티팩트가 있으면 먼저 삭제한 후에 업로드를 한다는 설정으로 같은 이름의 파일이 없다고 해도 실패하지는 않는다.

# 처음 업로드(기존 없음 → 신규 생성)
- uses: actions/upload-artifact@v4
  with:
    name: my-artifact
    path: dist/**

# 나중에 내용 바꿔서 같은 이름으로 다시 업로드(기존이 있으므로 교체)
- uses: actions/upload-artifact@v4
  with:
    name: my-artifact
    path: dist/**
    overwrite: true

 

7) include-hidden-files(선택, default : false)

숨김 파일/폴더(예: .env, .next, .cache, .gitignore 등)도 업로드 대상에 포함할지를 지정한다.

- uses: actions/upload-artifact@v4
  with:
    name: build-outputs
    path: |
      dist/**
      .next/cache/**        # dot-dir
    include-hidden-files: true

 

다운로드 : download-artifact

그리고 이렇게 만든 아티팩트는 위에서 말했던것 처럼 다른 Job(외부/내부 동일)이 사용하기 위해서 다운로드라는 과정을 진행한다

다운로드는 동일하게 Job의 Step에서 사용하며 uses에 actions/download-artifact@버전 을 사용해서 아티팩드를 가져온다

uses: actions/download-artifact@v4

 

이 다운로드 액션에는 with구문을 추가해서 input을 추가할 수 있는데 이는 아래와 같다.

 

1) name(선택)

특정 아티팩트 1개를 지정해서 다운받기 위해서 사용된다.

만약 name을 지정하지 않는다면 해당 workflow의 모든 아티팩트를 내려받는다.

업로드한 with.name과 정확하게 동일해야만(대소문자 구분함) 가져올 수 있고 pattern과 동시에 사용하지 못한다.

만약 여러개의 아티팩트를 받고 싶다면 name 대신에 pattern이나 artifact-ids를 사용하는게 좋다.

다른 workflow의 아티팩트를 받고 싶다면 repository, run-id, github-token과 함께 지정해줘야 한다.

- uses: actions/download-artifact@v5
  with:
    name: build-linux
    path: artifacts/        # 저장 위치(폴더)

// artifacts/ 아래에 build-linux 아티팩트 내용만 내려받음


// 외부 리포/다른 run에서 받기(이름을 아는 경우)
- uses: actions/download-artifact@v5
  with:
    name: build-linux
    repository: owner/repo
    run-id: 1234567890
    github-token: ${{ secrets.GH_PAT }}  # actions:read 권한 필요
    path: artifacts/

 

2) pattern(선택)

이름을 글롭매칭(와일드 카드로 파일, 이름을 간단히 패턴 매칭하는 방식)으로 여러 개를 선택한다.

web-*, report-*과 같이 여러 아티팩트를 고를때 사용되며 name과 동시에 사용할 수 없다.

// 현재 run에서 접두사로 고르기
- uses: actions/download-artifact@v5
  with:
    pattern: build-*        # 예: build-linux, build-windows, build-macos …
    path: artifacts/
    
// 부분 문자열(포함) 매칭
- uses: actions/download-artifact@v5
  with:
    pattern: *release*      # 이름에 'release'가 들어간 모든 아티팩트
    path: artifacts/

 

3) path(선택, default : .(현재 작업 디렉터리))

아티팩트 파일을 내려받을 로컬 폴더를 지정한다.

폴더가 없으면 생성되고 여러개를 받을때 기본 값은 각 아티팩트 이름으로 하위 폴더가 생성된다.

- uses: actions/download-artifact@v5
  with:
    path: artifacts/        # 저장 위치
    
    
// 결과
artifacts/build-linux/…
artifacts/build-windows/…

 

4) merge-multiple(선택, default : false)

여러 아티팩트를 한 폴더로 병합해서 추출한다.

pattern(또는 name을 생략해서)으로 여러개를 받을 때에만 의미가 있다.

다만, 파일 명이 충돌 됨을 주의해야한다

# (권장) 아티팩트별 하위 폴더로 → 충돌 걱정 없음
- uses: actions/download-artifact@v5
  with:
    pattern: build-*
    path: artifacts/              # 결과: artifacts/build-linux/…, artifacts/build-windows/…

# (주의) 한 폴더로 합치기 → 파일명/경로 충돌 주의 필요
- uses: actions/download-artifact@v5
  with:
    pattern: build-*
    path: artifacts/all/
    merge-multiple: true          # 충돌 시 어떤 게 남는지 보장X

 

5) repository(선택, default : 현재 repo)

리포지토리를 설정하는 것으로 따로 설정하지 않으면 현재 리포지토리를 바라보고 가져오고 owner/repo와 같이 설정을 하면 해당 리포지토리에서 아티팩트를 가져온다.

다만 이렇게 사용할 경우는 권한이 존재하는 토큰이 존재해야만 한다.

이 때 run-id, github-token이 같이 사용되어야 한다.

// 같은 리포(현재 run → 모든 아티팩트)
- uses: actions/download-artifact@v5
  with:
    path: artifacts/
    # repository 생략(현재 리포), run-id 생략(현재 run)

// 같은 리포 다른 run에서 받기
- uses: actions/download-artifact@v5
  with:
    run-id: 1234567890
    path: artifacts/
    # repository 생략(같은 리포)

// 다른 리포의 특정 run에서 받기
- uses: actions/download-artifact@v5
  with:
    repository: other-owner/other-repo
    run-id: 1234567890
    github-token: ${{ secrets.GH_PAT }}  # repo/actions:read 권한
    path: artifacts/

// 다른 리포의 모든 아티팩트 받기
- uses: actions/download-artifact@v5
  with:
    repository: other-owner/other-repo
    run-id: 1234567890
    github-token: ${{ secrets.GH_PAT }}
    path: artifacts/
    # name 생략 → 해당 run의 모든 아티팩트

 

6) run-id(선택, default : 현재 run)

특정 워크플로우 실행에서 받아오는 설정으로 다른 run의 산출물을 참조할 때 사용된다.

쉽게 말해서 워크플로우의 실행을 고유하게 식별하는 숫자 ID로 다른 run(특히 다른 repo)의 아티팩트를 받을 때 꼭 필요하다.

- uses: actions/download-artifact@v5
  with:
    repository: owner/repo     # 생략 시 현재 리포
    run-id: 1234567890         # ← 이 실행의 아티팩트를 받음
    github-token: ${{ secrets.GH_PAT }}
    path: artifacts/

 

7) github-token(선택, default : ${{github.token}})

GitHub API를 호출해 아티팩트 메타데이터/파일을 내려받을 권한을 부여하는 토큰 입력값으로 기본적으로 리포지토리/워크플로 런의 아티팩트를 읽는 권한이 필요하다.

 

// 같은 리포, 같거나 다른 run에서 받기
with:
  github-token: ${{ github.token }}  # 또는 ${{ secrets.GITHUB_TOKEN }}
  
// 다른 리포(크로스 리포)에서 받기
with:
  repository: other-owner/other-repo
  run-id: 1234567890
  github-token: ${{ secrets.GH_PAT }}   # 미리 리포 시크릿에 저장

 

 

아티팩트 워크플로우 생성

이제 아티팩트를 사용하는 워크플로우를 한번 생성해보자.

먼저 파일을 하나 생성하고 워크플로우이 이름을 설정해주자.

그리고 push 이벤트에 트리거되도록 설정해주자.

 

이제 잡을 생성해주도록 하자.

잡에서는 에코를 통해서 txt파일을 생성하고 생성한 txt파일을 아티팩트로 만들어주는 과정을 진행한다.

먼저 text 파일을 echo를 통해서 만들어주고

이렇게 만든 파일을 아티팩트로 만들어주자.

이때 만들어진 파일은 현재 경로에 존재하기 때문에 현재 경로를 path로 설정해주자.

 

이제 이렇게 만든 아티팩트를 다음 job에서 download 해보자.

download도 아티팩트를 내려 받는 과정 이후에 그 파일을 cat을 통해서 출력하는 과정으로 진행한다.

주의해야 할점은 upload 이후에 download가 되어야하기 때문에 need를 통해서 종속성을 설정해줘야지만 업로드가 되고 다운로드를 진행한다는 점이다.

먼저 잡에 종속성을 추가해주고

아티팩트를 내려받아준다.

그리고 이렇게 내려 받은 파일을 cat을 통해서 읽어주도록 하자

 

이제 commit & push 해주면 

text파일을 아티팩트로 업로드를 하고

동일한 명칭의 아티팩트를 찾아서 다운로드가 정상적으로 되었고 read text file에서 hi.txt를 찾는걸 볼 수 있다.

 

그리고 한 step 밖으로 나가면 

이렇게 아티팩트가 저장됨을 알 수 있고 우측 다운로드 버튼을 통해 직접 다운도 가능하고 쓰레기통 버튼을 통해서 삭제도 가능하다.

 

반응형