Skip to content

Commit

Permalink
optional input to validate checksum
Browse files Browse the repository at this point in the history
  • Loading branch information
eifinger committed Jul 23, 2023
1 parent 7c1cc82 commit ca56dd7
Show file tree
Hide file tree
Showing 10 changed files with 136 additions and 14 deletions.
15 changes: 14 additions & 1 deletion .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ jobs:
npm install
- run: |
npm run all
test: # make sure the action works on a clean machine without building
test-latest:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
Expand All @@ -27,9 +27,22 @@ jobs:
uses: ./
- run: |
which rye
test-specific-version:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Install specific version
uses: ./
with:
version: '0.11.0'
- run: |
which rye
test-checksum:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Checksum matches expected
uses: ./
with:
version: '0.11.0'
checksum: '00e795573477a2fe2b3c0ac748240364c3369218d314d1df47d2653764e9bfb1'
8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,14 @@ You can also specify a specific version of rye
version: '0.11.0'
```
```yaml
- name: Install a specific version and validate the checksum
uses: eifinger/setup-rye@v1
with:
version: '0.11.0'
checksum: '00e795573477a2fe2b3c0ac748240364c3369218d314d1df47d2653764e9bfb1'
```
## How it works
This action downloads rye from the releases of the [rye repo](https://github.com/mitsuhiko/rye) and uses the [GitHub Actions Toolkit](https://github.com/actions/toolkit) to cache it as a tool to speed up consecutive runs especially on self-hosted runners.
Expand Down
1 change: 1 addition & 0 deletions __tests__/fixtures/checksumfile
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Random file content
11 changes: 11 additions & 0 deletions __tests__/utils.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import {expect, test} from '@jest/globals'

import * as utils from '../src/utils'

test('checksum should match', async () => {
const validChecksum =
'f3da96ec7e995debee7f5d52ecd034dfb7074309a1da42f76429ecb814d813a3'
const filePath = '__tests__/fixtures/checksumfile'
const isValid = await utils.validateCheckSum(filePath, validChecksum)
expect(isValid).toBeTruthy()
})
3 changes: 3 additions & 0 deletions action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,9 @@ inputs:
version:
description: 'The version of rye to install'
default: 'latest'
checksum:
description: 'The checksum of the rye version to install'
required: false
runs:
using: 'node16'
main: 'dist/setup/index.js'
Expand Down
68 changes: 62 additions & 6 deletions dist/setup/index.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion dist/setup/index.js.map

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
"lint": "eslint src/**/*.ts",
"package": "ncc build -o dist/setup src/setup-rye.ts --source-map --license licenses.txt",
"test": "jest",
"act": "act -j test --container-architecture linux/amd64 -s GITHUB_TOKEN=\"$(gh auth token)\"",
"act": "act pull_request -W .github/workflows/test.yml --container-architecture linux/amd64 -s GITHUB_TOKEN=\"$(gh auth token)\"",
"all": "npm run build && npm run format && npm run lint && npm run package && npm test"
},
"repository": {
Expand Down
21 changes: 16 additions & 5 deletions src/setup-rye.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,20 +5,21 @@ import * as io from '@actions/io'
import * as octokit from '@octokit/rest'
import * as path from 'path'
import fetch from 'node-fetch'
import {OWNER, REPO} from './utils'
import {OWNER, REPO, validateCheckSum} from './utils'

async function run(): Promise<void> {
const platform = 'linux'
const arch = 'x64'
const versionInput = core.getInput('version')
const checkSum = core.getInput('checksum')

try {
const version = await resolveVersion(versionInput)
let cachedPath = tryGetFromCache(arch, version)
if (cachedPath) {
core.info(`Found Rye in cache for ${version}`)
} else {
cachedPath = await setupRye(platform, arch, version)
cachedPath = await setupRye(platform, arch, version, checkSum)
}
addRyeToPath(cachedPath)
addMatchers()
Expand Down Expand Up @@ -65,24 +66,34 @@ function tryGetFromCache(arch: string, version: string): string | undefined {
async function setupRye(
platform: string,
arch: string,
version: string
version: string,
checkSum: string | undefined
): Promise<string> {
const downloadPath = await downloadVersion(platform, arch, version)
const downloadPath = await downloadVersion(platform, arch, version, checkSum)
const cachedPath = await installRye(downloadPath, arch, version)
return cachedPath
}

async function downloadVersion(
platform: string,
arch: string,
version: string
version: string,
checkSum: string | undefined
): Promise<string> {
const binary = `rye-x86_64-${platform}`
const downloadUrl = `https://github.com/mitsuhiko/rye/releases/download/${version}/${binary}.gz`
core.info(`Downloading Rye from "${downloadUrl}" ...`)

try {
const downloadPath = await tc.downloadTool(downloadUrl)
if (checkSum !== undefined && checkSum !== '') {
const isValid = await validateCheckSum(downloadPath, checkSum)
if (!isValid) {
throw new Error(
`Checksum for ${downloadPath} did not match ${checkSum}.`
)
}
}

await extract(downloadPath)
return downloadPath
Expand Down
19 changes: 19 additions & 0 deletions src/utils.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
import * as fs from 'fs'
import * as crypto from 'crypto'

export const IS_WINDOWS = process.platform === 'win32'
export const IS_LINUX = process.platform === 'linux'
export const IS_MAC = process.platform === 'darwin'
Expand All @@ -6,3 +9,19 @@ export const WINDOWS_PLATFORMS = ['win32', 'win64']

export const REPO = 'rye'
export const OWNER = 'mitsuhiko'

export async function validateCheckSum(
filePath: string,
expected: string
): Promise<boolean> {
return new Promise((resolve, reject) => {
const hash = crypto.createHash('sha256')
const stream = fs.createReadStream(filePath)
stream.on('error', err => reject(err))
stream.on('data', chunk => hash.update(chunk))
stream.on('end', () => {
const actual = hash.digest('hex')
resolve(actual === expected)
})
})
}

0 comments on commit ca56dd7

Please sign in to comment.