최근에는 개발 업무와 더불어 전반적인 서비스의 CI 프로세스를 개선하는 업무에 참여하고 있는데, 이참에 Container Image Scan도 녹여보자 생각이 들었다.
이걸 진행하면서 아래와 같은 결과를 볼 수 이었다.
이번 글에서는 이 내용을 주절주절 써내려보려 한다.
[NOTE]
취약점 검사 및 조치에 대해서는 이미 수 많은 도구와 방법들이 널렸다.
나는 여기서 오픈소스를 이용해 쉽고 빠르게 구축할 수 있는 내용에 대해서 설명하고 싶다.
현재 내가 참여하고 있는 Cloudforet은 Open Source Project로써 소스코드는 모두 github에 공개되어있다.
이에 따라 자연스럽게 CI 과정에서는 아래와 같은 tool(?)을 사용하고 있다.
사실 이전에도 Image Scan을 해보자 하면서 몇 가지 Tool을 건드려본적 있다.
때문에 요렇게 아래와 같은 후보들이 있었는데
Trivy가 Aqura Security라는 곳에서 만든 Open Source Tool인 것 같은데 Target으로 Container Image뿐만 아니라 FileSystem, VM Image, IaC, AWS Resource(!)등 다양한 대상에 대한 검사 기능을 제공해주고 있었다.
또한 Open Source임은 물론이고 다른 Platform이나 Application에 통합할 수 있는 기능을 많이 제공한다고 이야기하고 있었는데 어떻게 내 맘을 알았는지, Github Actions도 제공해주고 있었다.
Trivy Action : https://github.com/aquasecurity/trivy-action
주절주절 말 할 필요없이 사용법은 너무나 간단했다, 예제를 가져와서 몇번 돌려보면 끝.
그런데 Github Actions를 돌려보기 전, CLI를 직접 받아서 한번 굴려봤다.
$ trivy image --format table --exit-code 1 --ignore-unfixed --vuln-type os,library --severity CRITICAL,HIGH {org}/{image}:{tag}
2023-04-21T18:05:31.915+0900 INFO Need to update DB
2023-04-21T18:05:31.915+0900 INFO DB Repository: ghcr.io/aquasecurity/trivy-db
2023-04-21T18:05:31.915+0900 INFO Downloading DB...
36.72 MiB / 36.72 MiB [---------------------------------------------------------------------------------------------------------------------------------------------------------] 100.00% 14.95 MiB p/s 2.7s
2023-04-21T18:05:31.915+0900 INFO Vulnerability scanning is enabled
2023-04-21T18:05:31.915+0900 INFO Secret scanning is enabled
2023-04-21T18:05:31.915+0900 INFO If your scanning is slow, please try '--scanners vuln' to disable secret scanning
2023-04-21T18:05:31.915+0900 INFO Please see also https://aquasecurity.github.io/trivy/v0.39/docs/secret/scanning/#recommendation for faster secret detection
2023-04-21T18:05:31.937+0900 INFO Detected OS: alpine
2023-04-21T18:05:31.937+0900 INFO Detecting Alpine vulnerabilities...
2023-04-21T18:05:31.939+0900 INFO Number of language-specific files: 0
{org}/{image}:{tag} (alpine 3.17.2)
Total: 13 (HIGH: 9, CRITICAL: 4)
┌────────────┬────────────────┬──────────┬───────────────────┬───────────────┬──────────────────────────────────────────────────────────────┐
│ Library │ Vulnerability │ Severity │ Installed Version │ Fixed Version │ Title │
├────────────┼────────────────┼──────────┼───────────────────┼───────────────┼──────────────────────────────────────────────────────────────┤
│ curl │ CVE-2023-23914 │ CRITICAL │ 7.87.0-r1 │ 7.87.0-r2 │ curl: HSTS ignored on multiple requests │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-23914 │
│ ├────────────────┤ │ ├───────────────┼──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27536 │ │ │ 7.88.1-r1 │ curl: GSS delegation too eager connection re-use │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27536 │
│ ├────────────────┼──────────┤ │ ├──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27533 │ HIGH │ │ │ curl: TELNET option IAC injection │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27533 │
│ ├────────────────┤ │ │ ├──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27534 │ │ │ │ curl: SFTP path ~ resolving discrepancy │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27534 │
│ ├────────────────┤ │ │ ├──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27535 │ │ │ │ FTP too eager connection reuse │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27535 │
├────────────┼────────────────┤ ├───────────────────┼───────────────┼──────────────────────────────────────────────────────────────┤
│ libcrypto3 │ CVE-2023-0464 │ │ 3.0.8-r0 │ 3.0.8-r1 │ Denial of service by excessive resource usage in verifying │
│ │ │ │ │ │ X509 policy constraints... │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-0464 │
├────────────┼────────────────┼──────────┼───────────────────┼───────────────┼──────────────────────────────────────────────────────────────┤
│ libcurl │ CVE-2023-23914 │ CRITICAL │ 7.87.0-r1 │ 7.87.0-r2 │ curl: HSTS ignored on multiple requests │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-23914 │
│ ├────────────────┤ │ ├───────────────┼──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27536 │ │ │ 7.88.1-r1 │ curl: GSS delegation too eager connection re-use │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27536 │
│ ├────────────────┼──────────┤ │ ├──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27533 │ HIGH │ │ │ curl: TELNET option IAC injection │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27533 │
│ ├────────────────┤ │ │ ├──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27534 │ │ │ │ curl: SFTP path ~ resolving discrepancy │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27534 │
│ ├────────────────┤ │ │ ├──────────────────────────────────────────────────────────────┤
│ │ CVE-2023-27535 │ │ │ │ FTP too eager connection reuse │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-27535 │
├────────────┼────────────────┤ ├───────────────────┼───────────────┼──────────────────────────────────────────────────────────────┤
│ libssl3 │ CVE-2023-0464 │ │ 3.0.8-r0 │ 3.0.8-r1 │ Denial of service by excessive resource usage in verifying │
│ │ │ │ │ │ X509 policy constraints... │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2023-0464 │
├────────────┼────────────────┤ ├───────────────────┼───────────────┼──────────────────────────────────────────────────────────────┤
│ tiff │ CVE-2022-3970 │ │ 4.4.0-r1 │ 4.4.0-r2 │ integer overflow in function TIFFReadRGBATileExt of the file │
│ │ │ │ │ │ https://avd.aquasec.com/nvd/cve-2022-3970 │
└────────────┴────────────────┴──────────┴───────────────────┴───────────────┴──────────────────────────────────────────────────────────────┘
일단 여러 print 형식을 지원하지만 table을 선택했을때 요로코롬 깔끔하게 출력해주었다. 또 log를 잘 읽어보면 DB를 update하는 내용이 있는데, 취약점 DB도 자동으로 최신화해주는 것 같으니 상당히 긍정적인 생각이 들었다.
이후 document를 조금 더 살펴보다보니, 요런게 눈에 띄었다.
If you have GitHub code scanning available you can use Trivy as a scanning tool as follows
이 말은 즉슨, GitHub code scanning이 활성화 되어있다면 Trivy와 연동 가능하다는 것이 아닐까?!
이렇게 되면, github actions 안에서 굳이 저 결과를 담아서 Slack으로 쏴주거나 할 필요가 없었다.
그냥 result file을 생성해서 github로 던저주면 끝이니까.
이것저것 만져본 결과, 아래와 같이 dev build 단계에서 취약점 검사하고 알려줄 수 있도록 Workflow를 구성했다.
무엇보다 취약점 결과를 Github에 전송해서 볼 수 있다는 것이 너무나 마음에 들었다.
CLI 테스트 후 Actions로 투닥투닥 만지면서 결과를 만들어냈다.
(참고로 이걸 몇몇 repository에 실제로 적용했다. 물론 작업은 Actions로 쉽고 빠르게 ^.~)
Workflow 내용은 아래와 같다.
name: "[Push] Build dev"
on:
workflow_dispatch:
repository_dispatch:
types: [master_push]
env:
SLACK_WEBHOOK_URL: ${{secrets.SLACK_WEBHOOK_URL}}
jobs:
# 생략
docker:
#build...
scan:
needs: [versioning, docker]
runs-on: ubuntu-20.04
env:
VERSION: ${{ needs.versioning.outputs.version }}
steps:
- name: Run Trivy vulnerability scanner
id: trivy-scan
uses: aquasecurity/trivy-action@master
with:
image-ref: pyengine/${{ github.event.repository.name }}:${{ env.VERSION }}
format: 'sarif'
output: 'trivy-results.sarif'
ignore-unfixed: true
vuln-type: 'os,library'
severity: 'CRITICAL,HIGH'
- name: Upload Trivy scan results to GitHub Security tab
uses: github/codeql-action/upload-sarif@v2
with:
sarif_file: 'trivy-results.sarif'
- name: Count vulnerabilities
id: vulnerabilities
run: |
count=$(jq '.runs[].results[].ruleId' ./trivy-results.sarif | wc -c)
echo "result_count=$count" >> $GITHUB_OUTPUT
echo "$count"
- name: slack
if: ${{ steps.vulnerabilities.outputs.result_count != 0 }}
# Notify Slack if vulnerabilities are found
notification:
# Notify Slack when the above steps are successfully completed
취약점 검사 과정에서 결과를 발견하면 요렇게 Slack에도 쏴주도록 했다.
message format을 직접 뚝닥뚝닥 했는데, 재능이 없는 것인지 아주 뭐가 없다 ㅋ...
그리고 실제 결과들은 요렇게 github에서 확인해볼 수 있다.(예제 사진은 모두 closed 되었지만)
우리가 Open Source로써 소스코드를 Github로 관리하고 있는 입장에서 이러한 통합 기능은 아주 큰 힘이 될 것 같다.
더 나아가 Dependabot 등이 잡아낸 결과도 함께 볼 수 있으니 취약점 관련 내용은 모두 Github에 취합하고 한눈에 알아볼 수 있는 것이다.
사실 최근들어 너무나도 게을러진 탓에 아주 이전에 했어야하는 것을 이제서야 하고있는 마음이 들기도 했다.
새삼 느끼지만 뭐 하나라도 놓치면 멀어지는게 특히나 이쪽인 것 같다.
Trivy는 Best는 아닐지 몰라도 이렇게 알게 된 이상 여러 취약점 도구로 활용을 해봐야할 것 같다.
특히나 AWS Scan은 어떤 결과가 나올지 궁금하기도 해서 주기적으로 검사할 수 있는 환경을 한번 또 만들어봐야할 것 같다.