{"meta":{"title":"CircleCI에서 GitHub Actions 마이그레이션","intro":"GitHub Actions 및 CircleCI는 구성에서 몇 가지 유사점을 공유하므로 GitHub Actions 마이그레이션이 비교적 간단합니다.","product":"GitHub Actions","breadcrumbs":[{"href":"/ko/actions","title":"GitHub Actions"},{"href":"/ko/actions/tutorials","title":"자습서"},{"href":"/ko/actions/tutorials/migrate-to-github-actions","title":"GitHub Actions로 마이그레이션"},{"href":"/ko/actions/tutorials/migrate-to-github-actions/manual-migrations","title":"수동 마이그레이션"},{"href":"/ko/actions/tutorials/migrate-to-github-actions/manual-migrations/migrate-from-circleci","title":"CircleCI에서 마이그레이션"}],"documentType":"article"},"body":"# CircleCI에서 GitHub Actions 마이그레이션\n\nGitHub Actions 및 CircleCI는 구성에서 몇 가지 유사점을 공유하므로 GitHub Actions 마이그레이션이 비교적 간단합니다.\n\n## 소개\n\nCircleCI 및 GitHub Actions를 사용하면 코드를 자동으로 빌드하고 테스트하고 게시하고 릴리스하고 배포하는 워크플로를 만들 수 있습니다. CircleCI 및 GitHub Actions는 워크플로 구성에서 몇 가지 유사점을 공유합니다.\n\n* 워크플로 구성 파일은 YAML로 작성되며 리포지토리에 저장됩니다.\n* 워크플로에는 하나 이상의 작업이 포함됩니다.\n* 작업에는 하나 이상의 단계 또는 개별 명령이 포함됩니다.\n* 단계 또는 작업을 다시 사용하고 커뮤니티와 공유할 수 있습니다.\n\n자세한 내용은 [GitHub Actions에 대한 이해](/ko/actions/learn-github-actions/understanding-github-actions)을(를) 참조하세요.\n\n## 주요 차이점\n\nCircleCI에서 마이그레이션하는 경우 다음과 같은 차이점을 고려하세요.\n\n* CircleCI의 자동 테스트 병렬 처리는 사용자가 지정한 규칙 또는 기록 타이밍 정보에 따라 테스트를 자동으로 그룹화합니다. 이 기능은 GitHub Actions에 기본 제공되지 않습니다.\n* 컨테이너의 사용자 매핑이 다르기 때문에 Docker 컨테이너에서 실행되는 작업은 권한 문제에 민감합니다.\n  `USER` 명령을 \\_Dockerfile\\_에서 사용하지 않으면 많은 문제를 방지할 수 있습니다. GitHub 호스팅 실행기의 Docker 파일 시스템에 대한 자세한 내용은 [GitHub 호스팅 실행기](/ko/actions/using-github-hosted-runners/about-github-hosted-runners#docker-container-filesystem)을(를) 참조하세요.\n\n## 워크플로 및 작업 마이그레이션\n\nCircleCI는 `workflows` 파일에서 \\_\\_ 를 정의합니다. 이를 통해 둘 이상의 워크플로를 구성할 수 있습니다. GitHub에는 워크플로당 하나의 워크플로 파일이 필요하므로 `workflows`를 선언할 필요가 없습니다.\n\\_config.yml\\_에 구성된 각 워크플로에 대한 새 워크플로 파일을 만들어야 합니다.\n\nCircleCI와 GitHub Actions는 비슷한 구문을 사용하여 구성 파일에서 `jobs`를 구성합니다. CircleCI 워크플로에서 `requires`를 사용하는 작업 간의 종속성을 구성하는 경우 해당 GitHub Actions `needs` 구문을 사용할 수 있습니다. 자세한 내용은 [GitHub Actions에 대한 워크플로 구문](/ko/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idneeds)을(를) 참조하세요.\n\n## 작업으로 orbs 마이그레이션\n\nCircleCI 및 GitHub Actions는 워크플로에서 작업을 재사용하고 공유하는 메커니즘을 제공합니다. CircleCI는 YAML로 작성된 orbs라는 개념을 사용하여 워크플로에서 다시 사용할 수 있는 작업을 제공합니다. GitHub Actions에는 JavaScript 파일 또는 Docker 이미지로 빌드하는 작업이라는 강력하고 유연하며 재사용 가능한 구성 요소가 있습니다. GitHub의 API와 공개적으로 사용할 수 있는 타사 API와의 통합을 포함하여 원하는 방식으로 리포지토리와 상호 작용을 하는 사용자 지정 코드를 써서 작업을 만들 수 있습니다. 예를 들어 작업은 npm 모듈을 게시할 수 있고 긴급한 이슈가 발생할 때 SMS 알림을 보낼 수 있으며 프로덕션 준비 코드를 배포할 수 있습니다. 자세한 내용은 [자동화 재사용](/ko/actions/creating-actions)을(를) 참조하세요.\n\nCircleCI는 YAML 앵커 및 별칭을 사용하여 워크플로 부분을 다시 사용할 수 있습니다. GitHub Actions는 재사용성을 위해 YAML 앵커와 별칭을 지원하고, 다양한 구성으로 작업을 실행하기 위한 매트릭스도 제공합니다. 행렬에 대한 자세한 내용은 [워크플로에서 작업 변형 실행](/ko/actions/using-jobs/using-a-matrix-for-your-jobs)을(를) 참조하세요.\n\n## Docker 이미지 사용\n\nCircleCI 및 GitHub Actions는 Docker 이미지 내부의 실행 단계를 지원합니다.\n\nCircleCI는 일반적인 종속성이 있는 미리 빌드된 이미지 집합을 제공합니다. 해당 이미지에는 `USER`가 `circleci`로 설정되어 있으며 이로 인해 사용 권한이 GitHub Actions와 충돌합니다.\n\nGitHub Actions로 마이그레이션할 때는 CircleCI의 미리 빌드된 이미지를 사용하지 않는 것이 좋습니다. 대부분의 경우 작업을 사용하여 필요한 추가 종속성을 설치할 수 있습니다.\n\nDocker 파일 시스템에 대한 자세한 내용은 [GitHub 호스팅 실행기](/ko/actions/using-github-hosted-runners/about-github-hosted-runners#docker-container-filesystem)을(를) 참조하세요.\n\nGitHub 호스팅 실행기 이미지에서 사용할 수 있는 도구 및 패키지에 대한 자세한 내용은 [GitHub 호스팅 실행기](/ko/actions/using-github-hosted-runners/about-github-hosted-runners#supported-software)을(를) 참조하세요.\n\n## 변수 및 비밀 사용\n\nCircleCI와 GitHub Actions는 구성 파일에서 환경 변수를 설정하고 CircleCI나 GitHub UI를 사용하여 비밀을 생성할 수 있습니다.\n\n자세한 내용은 [변수 참조](/ko/actions/reference/variables-reference#default-environment-variables) 및 [GitHub Actions에서 비밀 사용](/ko/actions/security-guides/using-secrets-in-github-actions)을(를) 참조하세요.\n\n## 캐싱\n\nCircleCI 및 GitHub Actions는 구성 파일에서 파일을 수동으로 캐시하는 메서드를 제공합니다.\n\n다음은 각 시스템에 대한 구문의 예입니다.\n\n### 캐싱을 위한 CircleCI 구문\n\n```yaml\n- restore_cache:\n    keys:\n      - v1-npm-deps-{{ checksum \"package-lock.json\" }}\n      - v1-npm-deps-\n```\n\n### 캐싱에 대한 GitHub Actions 구문\n\n```yaml\n- name: Cache node modules\n  uses: actions/cache@v4\n  with:\n    path: ~/.npm\n    key: v1-npm-deps-${{ hashFiles('**/package-lock.json') }}\n    restore-keys: v1-npm-deps-\n```\n\nGitHub Actions에는 CircleCI의 Docker 계층 캐싱(또는 DLC)에 해당하는 것이 없습니다.\n\n## 작업 간에 데이터 유지\n\nCircleCI와 GitHub Actions는 작업 간에 데이터를 유지하는 메커니즘을 제공합니다.\n\n다음은 CircleCI 및 GitHub Actions 구성 구문의 예입니다.\n\n### 작업 간에 데이터 유지를 위한 CircleCI 구문\n\n```yaml\n- persist_to_workspace:\n    root: workspace\n    paths:\n      - math-homework.txt\n\n...\n\n- attach_workspace:\n    at: /tmp/workspace\n```\n\n### 작업 간에 데이터를 유지하기 위한 GitHub Actions 구문\n\n```yaml\n- name: Upload math result for job 1\n  uses: actions/upload-artifact@v4\n  with:\n    name: homework\n    path: math-homework.txt\n\n...\n\n- name: Download math result for job 1\n  uses: actions/download-artifact@v5\n  with:\n    name: homework\n```\n\n자세한 내용은 [워크플로 아티팩트와 데이터 저장 및 공유](/ko/actions/using-workflows/storing-workflow-data-as-artifacts)을(를) 참조하세요.\n\n## 데이터베이스 및 서비스 컨테이너 사용\n\n두 시스템 모두 데이터베이스, 캐싱 또는 기타 종속성에 대한 추가 컨테이너를 포함할 수 있습니다.\n\nCircleCI에서 \\_config.yaml\\_에 나열된 첫 번째 이미지는 명령을 실행하는 데 사용되는 기본 이미지입니다. GitHub Actions는 명시적 섹션을 사용합니다. 즉, `container`를 기본 컨테이너에 사용하고 추가 컨테이너를 `services`에 나열합니다.\n\n다음은 CircleCI 및 GitHub Actions 구성 구문의 예입니다.\n\n### 데이터베이스 및 서비스 컨테이너 사용을 위한 CircleCI 구문\n\n```yaml\n---\nversion: 2.1\n\njobs:\n\n  ruby-26:\n    docker:\n      - image: circleci/ruby:2.6.3-node-browsers-legacy\n        environment:\n          PGHOST: localhost\n          PGUSER: administrate\n          RAILS_ENV: test\n      - image: postgres:10.1-alpine\n        environment:\n          POSTGRES_USER: administrate\n          POSTGRES_DB: ruby26\n          POSTGRES_PASSWORD: \"\"\n\n    working_directory: ~/administrate\n\n    steps:\n      - checkout\n\n      # Bundle install dependencies\n      - run: bundle install --path vendor/bundle\n\n      # Wait for DB\n      - run: dockerize -wait tcp://localhost:5432 -timeout 1m\n\n      # Setup the environment\n      - run: cp .sample.env .env\n\n      # Setup the database\n      - run: bundle exec rake db:setup\n\n      # Run the tests\n      - run: bundle exec rake\n\nworkflows:\n  version: 2\n  build:\n    jobs:\n      - ruby-26\n...\n\n- attach_workspace:\n    at: /tmp/workspace\n```\n\n### 데이터베이스 및 서비스 컨테이너를 사용하기 위한 GitHub Actions 구문\n\n<!-- markdownlint-disable search-replace -->\n\n```yaml\nname: Containers\n\non: [push]\n\njobs:\n  build:\n\n    runs-on: ubuntu-latest\n    container: circleci/ruby:2.6.3-node-browsers-legacy\n\n    env:\n      PGHOST: postgres\n      PGUSER: administrate\n      RAILS_ENV: test\n\n    services:\n      postgres:\n        image: postgres:10.1-alpine\n        env:\n          POSTGRES_USER: administrate\n          POSTGRES_DB: ruby25\n          POSTGRES_PASSWORD: \"\"\n        ports:\n          - 5432:5432\n        # Add a health check\n        options: --health-cmd pg_isready --health-interval 10s --health-timeout 5s --health-retries 5\n\n    steps:\n      # This Docker file changes sets USER to circleci instead of using the default user, so we need to update file permissions for this image to work on GH Actions.\n      # See https://docs.github.com/actions/using-github-hosted-runners/about-github-hosted-runners#docker-container-filesystem\n\n      - name: Setup file system permissions\n        run: sudo chmod -R 777 $GITHUB_WORKSPACE /github /__w/_temp\n      - uses: actions/checkout@v6\n      - name: Install dependencies\n        run: bundle install --path vendor/bundle\n      - name: Setup environment configuration\n        run: cp .sample.env .env\n      - name: Setup database\n        run: bundle exec rake db:setup\n      - name: Run tests\n        run: bundle exec rake\n```\n\n<!-- markdownlint-enable search-replace -->\n\n자세한 내용은 [Docker 서비스 컨테이너와 통신](/ko/actions/using-containerized-services/about-service-containers)을(를) 참조하세요.\n\n## 완성된 예시\n\n다음은 실제 사례입니다. 왼쪽은 *thoughtbot/administrator* 리포지토리에 대한 실제 CircleCI [config.yml](https://github.com/thoughtbot/administrate)입니다. 오른쪽은 GitHub Actions의 동일한 항목입니다.\n\n### CircleCI에 대한 전체 예시\n\n```yaml\n---\nversion: 2.1\n\ncommands:\n  shared_steps:\n    steps:\n      - checkout\n\n      # Restore Cached Dependencies\n      - restore_cache:\n          name: Restore bundle cache\n          key: administrate-{{ checksum \"Gemfile.lock\" }}\n\n      # Bundle install dependencies\n      - run: bundle install --path vendor/bundle\n\n      # Cache Dependencies\n      - save_cache:\n          name: Store bundle cache\n          key: administrate-{{ checksum \"Gemfile.lock\" }}\n          paths:\n            - vendor/bundle\n\n      # Wait for DB\n      - run: dockerize -wait tcp://localhost:5432 -timeout 1m\n\n      # Setup the environment\n      - run: cp .sample.env .env\n\n      # Setup the database\n      - run: bundle exec rake db:setup\n\n      # Run the tests\n      - run: bundle exec rake\n\ndefault_job: &default_job\n  working_directory: ~/administrate\n  steps:\n    - shared_steps\n    # Run the tests against multiple versions of Rails\n    - run: bundle exec appraisal install\n    - run: bundle exec appraisal rake\n\njobs:\n  ruby-25:\n    <<: *default_job\n    docker:\n      - image: circleci/ruby:2.5.0-node-browsers\n        environment:\n          PGHOST: localhost\n          PGUSER: administrate\n          RAILS_ENV: test\n      - image: postgres:10.1-alpine\n        environment:\n          POSTGRES_USER: administrate\n          POSTGRES_DB: ruby25\n          POSTGRES_PASSWORD: \"\"\n\n  ruby-26:\n    <<: *default_job\n    docker:\n      - image: circleci/ruby:2.6.3-node-browsers-legacy\n        environment:\n          PGHOST: localhost\n          PGUSER: administrate\n          RAILS_ENV: test\n      - image: postgres:10.1-alpine\n        environment:\n          POSTGRES_USER: administrate\n          POSTGRES_DB: ruby26\n          POSTGRES_PASSWORD: \"\"\n\nworkflows:\n  version: 2\n  multiple-rubies:\n    jobs:\n      - ruby-26\n      - ruby-25\n```\n\n### GitHub Actions 대한 전체 예제\n\n```yaml\n# 이 워크플로는 GitHub에서 인증되지 않은 작업을 사용합니다.\n# 작업은 타사에서 제공하며\n# 별도의 서비스 약관, 개인정보처리방침, 지원 설명서에서 규정됩니다.\n# 참조하세요.\n\n# 커밋 SHA에 작업을 고정하는 것이 좋습니다.\n# 최신 버전을 얻으려면 SHA를 업데이트해야 합니다.\n# 태그 또는 분기를 참조할 수도 있지만 경고 없이 작업이 변경될 수 있습니다.\n\nname: Containers\n\non: [push]\n\njobs:\n  build:\n\n    strategy:\n      matrix:\n        ruby: ['2.5', '2.6.3']\n\n    runs-on: ubuntu-latest\n\n    env:\n      PGHOST: localhost\n      PGUSER: administrate\n      RAILS_ENV: test\n\n    services:\n      postgres:\n        image: postgres:10.1-alpine\n        env:\n          POSTGRES_USER: administrate\n          POSTGRES_DB: ruby25\n          POSTGRES_PASSWORD: \"\"\n        ports:\n          - 5432:5432\n        # Add a health check\n        options: --health-cmd pg_isready --health-interval 10s --health-timeout 5s --health-retries 5\n\n    steps:\n      - uses: actions/checkout@v6\n      - name: Setup Ruby\n        uses: eregon/use-ruby-action@ec02537da5712d66d4d50a0f33b7eb52773b5ed1\n        with:\n          ruby-version: ${{ matrix.ruby }}\n      - name: Cache dependencies\n        uses: actions/cache@v4\n        with:\n          path: vendor/bundle\n          key: administrate-${{ matrix.image }}-${{ hashFiles('Gemfile.lock') }}\n      - name: Install postgres headers\n        run: |\n          sudo apt-get update\n          sudo apt-get install libpq-dev\n      - name: Install dependencies\n        run: bundle install --path vendor/bundle\n      - name: Setup environment configuration\n        run: cp .sample.env .env\n      - name: Setup database\n        run: bundle exec rake db:setup\n      - name: Run tests\n        run: bundle exec rake\n      - name: Install appraisal\n        run: bundle exec appraisal install\n      - name: Run appraisal\n        run: bundle exec appraisal rake\n```"}