Skip to content

Merge pull request #552 from nqminds/dependabot/github_actions/action… #3541

Merge pull request #552 from nqminds/dependabot/github_actions/action…

Merge pull request #552 from nqminds/dependabot/github_actions/action… #3541

Workflow file for this run

on:
release:
types:
- created
- edited # can remove once CI is confirmed working
- prereleased
- released
- published
push:
pull_request:
branches: [ main ]
name: Build
jobs:
build:
name: Compile Locally
strategy:
matrix:
cmake-preset:
- linux # Normal linux tests
- linux-with-crypt # Tests whether crypto service works
- linux-with-example-middlewares # tests whether example capture middlewares work
- clang
- openwrt-with-header
- openwrt-21.02.1/bcm27xx/bcm2710 # Raspberry Pi 3 for OpenWRT 21.02.1
- recap # Uses the generic IP service
permissions:
contents: read
runs-on: ubuntu-22.04
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set apt mirror
# GitHub Actions apt proxy is super unstable
# see https://github.com/actions/runner-images/issues/7048
run: |
# make sure there is a `\t` between URL and `priority:*` attributes
printf 'http://azure.archive.ubuntu.com/ubuntu priority:1\n' | sudo tee /etc/apt/mirrors.txt
curl http://mirrors.ubuntu.com/mirrors.txt | sudo tee --append /etc/apt/mirrors.txt
sudo sed -i 's/http:\/\/azure.archive.ubuntu.com\/ubuntu\//mirror+file:\/etc\/apt\/mirrors.txt/' /etc/apt/sources.list
- name: Install Dependencies
shell: bash # we're using bash arrays here
run: |
sudo apt-get update
sudo apt-get install devscripts equivs lcov -y # install mk-build-depends
sudo mk-build-deps --install --tool='apt-get -o Debug::pkgProblemResolver=yes --no-install-recommends --yes' debian/control
- name: Install llvm (if clang)
if: matrix.cmake-preset == 'clang'
run: |
sudo apt-get install llvm -y
- name: Cache CMake build/dl folder
uses: actions/cache@v3
with:
path: ./build/dl
key: ${{ runner.os }}-${{ matrix.cmake-preset }}-${{ hashFiles( 'lib/*' ) }}
# Sometimes the cache step just freezes forever
# so put a limit on it so that we can restart it earlier on failure
timeout-minutes: 10
- name: Configure
run: |
cmake --preset "${{ matrix.cmake-preset }}" -DCONFIGURE_COVERAGE=BOOL:ON
- name: Build
run: |
cmake --build --preset "${{ matrix.cmake-preset }}" --parallel "$(($(nproc) + 1))"
- id: test
name: Test
run: |
if ctest --list-presets | grep -s "${{ matrix.cmake-preset }}"; then
# Temporarily skip running tests, since we will run tests when
# calculating code-coverage in the next step, and there's a race-condition
# when we run tests twice in sucession.
# ctest --preset "${{ matrix.cmake-preset }}" --output-on-failure
echo "tested=true" >> $GITHUB_OUTPUT
else
echo "tested=false" >> $GITHUB_OUTPUT
fi
- name: Code Coverage
if: steps.test.outputs.tested == 'true'
run: |
cmake --build --preset "${{ matrix.cmake-preset }}" --parallel "$(($(nproc) + 1))" --target coverage
mv "build/${{ matrix.cmake-preset }}/coverage.info" "build/${{ matrix.cmake-preset }}/coverage-${{ matrix.cmake-preset }}.info"
env:
# --target coverage runs CTest internally, but it doesn't load our
# custom LD_LIBRARY_PATH from our ctest's cmake-presets file
LD_LIBRARY_PATH: ${{ github.workspace }}/build/${{ matrix.cmake-preset }}/lib/ubox/lib
- name: Archive code coverage results
if: steps.test.outputs.tested == 'true'
uses: actions/upload-artifact@v3
with:
name: code-coverage-lcov
path: build/${{ matrix.cmake-preset }}/coverage-${{ matrix.cmake-preset }}.info
- name: Install to ${{ runner.temp }}/edgesec-${{ matrix.cmake-preset }}/
run: |
cmake --install "build/${{ matrix.cmake-preset }}" --prefix "${{ runner.temp }}/edgesec-${{ matrix.cmake-preset }}"
- name: Escape invalid chars in artifact name
id: escape_preset
run: |
preset='${{ matrix.cmake-preset }}'
# replace `/` with `-`
escaped_preset="${preset////-}"
echo "ESCAPED_CMAKE_PRESET=${escaped_preset}" >> $GITHUB_OUTPUT
- name: Archive Install Output
uses: actions/upload-artifact@v3
with:
name: edgesec-build-${{ steps.escape_preset.outputs.ESCAPED_CMAKE_PRESET }}
# EDGESec is a public repo, so storage is free
# we can always rerun action to regenerate them
retention-days: 7
path: |
${{ runner.temp }}/edgesec-${{ matrix.cmake-preset }}/
coverage:
name: Code Coverage
runs-on: ubuntu-latest
permissions:
contents: read
actions: read # to download artifact
needs:
- build
steps:
- name: Checkout code
# not sure if needed, maybe the codecov action uses it
uses: actions/checkout@v4
- name: Set apt mirror
# GitHub Actions apt proxy is super unstable
# see https://github.com/actions/runner-images/issues/7048
run: |
# make sure there is a `\t` between URL and `priority:*` attributes
printf 'http://azure.archive.ubuntu.com/ubuntu priority:1\n' | sudo tee /etc/apt/mirrors.txt
curl http://mirrors.ubuntu.com/mirrors.txt | sudo tee --append /etc/apt/mirrors.txt
sudo sed -i 's/http:\/\/azure.archive.ubuntu.com\/ubuntu\//mirror+file:\/etc\/apt\/mirrors.txt/' /etc/apt/sources.list
- name: Install Coverage Tools
run: |
sudo apt-get install lcov -y || ( sudo apt-get update && sudo apt-get install lcov -y )
- name: Download Coverage Results
uses: actions/download-artifact@v3
id: download
with:
name: 'code-coverage-lcov'
- name: 'Echo download path'
run: echo ${{steps.download.outputs.download-path}}
- name: 'Combine Coverage Results'
run: |
inputs=('lcov' '--output-file' 'coverage.info' '--rc' 'lcov_branch_coverage=1')
for input in coverage-*.info; do
inputs+=('--add-tracefile' "$input")
done
"${inputs[@]}"
- name: Upload combined coverage to Codecov
uses: codecov/codecov-action@v3
with:
files: coverage.info
# not officially needed for public repos, but we're getting a bunch of API issues
token: ${{ secrets.CODECOV_TOKEN }}
fail_ci_if_error: true
build-recap:
name: Building Recap
# Build on older Ubuntu for better GLIBC compatibility
runs-on: [ubuntu-20.04]
permissions:
contents: write # needed for publishing release artifact
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set apt mirror
# GitHub Actions apt proxy is super unstable
# see https://github.com/actions/runner-images/issues/7048
run: |
# make sure there is a `\t` between URL and `priority:*` attributes
printf 'http://azure.archive.ubuntu.com/ubuntu priority:1\n' | sudo tee /etc/apt/mirrors.txt
curl http://mirrors.ubuntu.com/mirrors.txt | sudo tee --append /etc/apt/mirrors.txt
sudo sed -i 's/http:\/\/azure.archive.ubuntu.com\/ubuntu\//mirror+file:\/etc\/apt\/mirrors.txt/' /etc/apt/sources.list
- name: Install Dependencies
run: |
sudo apt-get update
sudo apt-get install devscripts equivs ninja-build -y # install mk-build-depends
sudo mk-build-deps --install --tool='apt-get -o Debug::pkgProblemResolver=yes --no-install-recommends --yes' debian/control
- name: Configure using Ninja
# Ninja is actually slightly slower than using Make, since then
# the ExternalProjects have to run in invidividual GNU Make sessions
# It's mainly here just to confirm that a Ninja build works.
run: cmake --preset recap -DCMAKE_BUILD_TYPE=Release -G Ninja
- name: Build
run: cmake --build --preset recap -j="$(($(nproc) + 1))"
- name: Archive built recap
uses: actions/upload-artifact@v3
with:
name: recap-linux-x86_64
path: build/recap/src/recap
- name: Upload recap as Release Assets
# only run action if this is being run from a GitHub Release
if: ${{ github.event_name == 'release' }}
uses: actions/github-script@v6
with:
github-token: ${{secrets.GITHUB_TOKEN}}
script: |
const fs = require('fs').promises;
const {basename} = require("path");
const filePath = "build/recap/src/recap";
console.log(`Uploading ${filePath}`);
const filePromise = fs.readFile(filePath);
// Determine content-length for header to upload asset
const {size: contentLength} = await fs.stat(filePath);
// Setup headers for API call, see Octokit Documentation:
// https://octokit.github.io/rest.js/#octokit-routes-repos-upload-release-asset for more information
const headers = {
'content-type': "application/x-pie-executable",
'content-length': contentLength,
};
// Upload a release asset
// API Documentation: https://developer.github.com/v3/repos/releases/#upload-a-release-asset
// Octokit Documentation: https://octokit.github.io/rest.js/v18#repos-upload-release-asset
try {
const uploadAssetResponse = await github.rest.repos.uploadReleaseAsset({
url: context.payload.release.upload_url,
headers,
name: `${basename(filePath)}-linux-x86_64`,
data: await filePromise,
});
} catch (error) {
// upload errors are usually since the file already exists
console.error(`[skipped] Uploading ${basename(filePath)} failed: ${error}`);
}
build-deb:
name: Build Debian Package
# building a deb is super slow, but we're a public repo now, so it's free!!
runs-on: [ubuntu-22.04]
strategy:
matrix:
architecture: [arm64, amd64]
distribution:
# focal and jammy are incompatible due to ABI incompatible libssl versions
- focal # uses libssl1.1
- jammy # uses libssl3
permissions:
contents: write # needed for publishing release artifact
env:
OTHER_MIRROR:
deb [arch=arm64] http://ports.ubuntu.com/ubuntu-ports ${{ matrix.distribution }} main universe | deb [arch=amd64] http://archive.ubuntu.com/ubuntu ${{ matrix.distribution }} main universe
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Create pbuilder cache dir
# The actions/cache action does not have permissions to create the pbuilder
# cache folder if it doesn't exist
run: sudo mkdir -m777 -p /var/cache/pbuilder/
- name: Cache pbuilder base
id: cache-pbuilder-base
uses: actions/cache@v3
with:
path: |
/var/cache/pbuilder/base.tgz
key: ${{ runner.os }}-${{ matrix.distribution }}-${{ matrix.architecture }}
# Sometimes the cache step just freezes forever
# so put a limit on it so that we can restart it earlier on failure
timeout-minutes: 10
- name: Set apt mirror
# GitHub Actions apt proxy is super unstable
# see https://github.com/actions/runner-images/issues/7048
run: |
# make sure there is a `\t` between URL and `priority:*` attributes
printf 'http://azure.archive.ubuntu.com/ubuntu priority:1\n' | sudo tee /etc/apt/mirrors.txt
curl http://mirrors.ubuntu.com/mirrors.txt | sudo tee --append /etc/apt/mirrors.txt
sudo sed -i 's/http:\/\/azure.archive.ubuntu.com\/ubuntu\//mirror+file:\/etc\/apt\/mirrors.txt/' /etc/apt/sources.list
- name: Install dependencies
run: |
sudo apt-get update && sudo apt-get install pbuilder debhelper -y
- name: Setup pdebuilderrc for cross-compiling
env:
PBUILDER_RC: |
# Enable network access, since `cmake` downloads dependencies
USENETWORK=yes
# Faster than default, and is requried if we want to do cross-compiling
PBUILDERSATISFYDEPENDSCMD="/usr/lib/pbuilder/pbuilder-satisfydepends-apt"
run: |
echo "$PBUILDER_RC" | sudo tee -a /etc/pbuilderrc
- name: Build pbuilder base.tgz
if: steps.cache-pbuilder-base.outputs.cache-hit != 'true'
run: |
sudo pbuilder create --debootstrapopts --variant=buildd --distribution ${{ matrix.distribution }} --mirror "" --othermirror "$OTHER_MIRROR"
- name: Build .deb
run: |
mkdir -p '${{ runner.temp }}/pbuilder/result'
pdebuild --buildresult '${{ runner.temp }}/pbuilder/result' --debbuildopts "-us -uc" -- --override-config --distribution ${{ matrix.distribution }} --mirror "" --othermirror "$OTHER_MIRROR" --host-arch ${{ matrix.architecture }}
- name: Load output .deb name
id: load-deb-name
run: |
OLD_DEB_PATH="$(ls -rt '${{ runner.temp }}/pbuilder/result'/edgesec*.deb | head -1)"
NEW_DEB_PATH="$(echo "$OLD_DEB_PATH" | sed -E 's/_(([[:digit:]]\.){0,2}[[:digit:]](-[A-Za-z0-9+.~]+)*)_/_\1_${{ matrix.distribution }}_/')"
mv "$OLD_DEB_PATH" "$NEW_DEB_PATH"
echo "old-deb-path=${OLD_DEB_PATH}" >> $GITHUB_OUTPUT
echo "deb-path=${NEW_DEB_PATH}" >> $GITHUB_OUTPUT
echo "deb-name=$(basename "${NEW_DEB_PATH}")" >> $GITHUB_OUTPUT
- name: Archive built debs
uses: actions/upload-artifact@v3
with:
name: edgesec-built-debs
# EDGESec is a public repo, so storage is free
# we can always rerun action to regenerate them
retention-days: 7
path: |
${{ runner.temp }}/pbuilder/result/*.deb
- name: Upload debs as Release Assets
# only run action if this is being run from a GitHub Release
if: ${{ github.event_name == 'release' }}
uses: actions/github-script@v6
env:
PBUILDER_RESULT_DIR: '${{ runner.temp }}/pbuilder/result'
with:
github-token: ${{secrets.GITHUB_TOKEN}}
script: |
const fs = require('fs').promises;
const {basename, join} = require("path");
const globber = await glob.create(join(process.env.PBUILDER_RESULT_DIR, "*.deb"));
const files = await globber.glob();
for (const filePath of files) {
console.log(`Uploading ${filePath}`);
const filePromise = fs.readFile(filePath);
// Determine content-length for header to upload asset
const {size: contentLength} = await fs.stat(filePath);
// Setup headers for API call, see Octokit Documentation:
// https://octokit.github.io/rest.js/#octokit-routes-repos-upload-release-asset for more information
const headers = {
'content-type': "application/vnd.debian.binary-package",
'content-length': contentLength,
};
// Upload a release asset
// API Documentation: https://developer.github.com/v3/repos/releases/#upload-a-release-asset
// Octokit Documentation: https://octokit.github.io/rest.js/v18#repos-upload-release-asset
try {
const uploadAssetResponse = await github.rest.repos.uploadReleaseAsset({
url: context.payload.release.upload_url,
headers,
name: basename(filePath),
data: await filePromise,
});
} catch (error) {
// upload errors are usually since the file already exists
console.error(`[skipped] Uploading ${basename(filePath)} failed: ${error}`);
}
}