Sonarcloud on request #80
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
name: Sonarcloud on request | |
on: | |
workflow_dispatch: | |
jobs: | |
select_environment: | |
name: 'Prepare Environment' | |
runs-on: ubuntu-22.04 | |
outputs: | |
timestamp: ${{ steps.select.outputs.timestamp }} | |
repository_owner: ${{ steps.select.outputs.repository_owner }} | |
repository_name: ${{ steps.select.outputs.repository_name }} | |
repository: ${{ steps.select.outputs.repository }} | |
ref: ${{ steps.select.outputs.ref }} | |
environment: ${{ steps.select.outputs.environment }} | |
sha: ${{ steps.select.outputs.sha }} | |
head_ref: ${{ steps.select.outputs.head_ref }} | |
base_ref: ${{ steps.select.outputs.base_ref }} | |
pr_number: ${{ steps.select.outputs.pr_number }} | |
yarp_version: ${{ steps.select.outputs.yarp_version }} | |
steps: | |
- name: "Set output variables" | |
id: select | |
run: | | |
echo "timestamp=$(/bin/date -u +%Y%m%d-%H%M%S)" >> $GITHUB_OUTPUT | |
echo "repository_owner=${{ github.repository_owner }}" >> $GITHUB_OUTPUT | |
echo "repository_name=$(cat $GITHUB_EVENT_PATH | jq -r .repository.name)" >> $GITHUB_OUTPUT | |
echo "repository=${{ github.repository }}" >> $GITHUB_OUTPUT | |
if [[ "$GITHUB_EVENT_NAME" = "pull_request_target" ]]; then | |
echo "environment=code-analysis_unsafe" >> $GITHUB_OUTPUT | |
echo "ref=refs/pull/$(cat $GITHUB_EVENT_PATH | jq -r .number)/merge" >> $GITHUB_OUTPUT | |
else | |
echo "environment=code-analysis" >> $GITHUB_OUTPUT | |
echo "ref=${{ github.ref }}" >> $GITHUB_OUTPUT | |
fi | |
if [[ "$GITHUB_EVENT_NAME" = "pull_request" || "$GITHUB_EVENT_NAME" == "pull_request_target" ]]; then | |
echo "sha=${{ github.event.pull_request.head.sha }}" >> $GITHUB_OUTPUT | |
echo "head_ref=${GITHUB_HEAD_REF}" >> $GITHUB_OUTPUT | |
echo "base_ref=${GITHUB_BASE_REF}" >> $GITHUB_OUTPUT | |
echo "pr_number=$(cat $GITHUB_EVENT_PATH | jq -r .number)" >> $GITHUB_OUTPUT | |
else | |
echo "sha=${{ github.sha }}" >> $GITHUB_OUTPUT | |
fi | |
# Get YARP Project Version | |
if [[ "$GITHUB_EVENT_NAME" = "release" ]]; then | |
echo "yarp_version=$(awk '/ VERSION /{print $2}' CMakeLists.txt)" >> $GITHUB_OUTPUT | |
fi | |
- name: 'Debug output variables' | |
env: | |
TIMESTAMP: ${{ steps.select.outputs.timestamp }} | |
REPOSITORY_OWNER: ${{ steps.select.outputs.repository_owner }} | |
REPOSITORY_NAME: ${{ steps.select.outputs.repository_name }} | |
REPOSITORY: ${{ steps.select.outputs.repository }} | |
REF: ${{ steps.select.outputs.ref }} | |
ENVIRONMENT: ${{ steps.select.outputs.environment }} | |
SHA: ${{ steps.select.outputs.sha }} | |
HEAD_REF: ${{ steps.select.outputs.head_ref }} | |
BASE_REF: ${{ steps.select.outputs.base_ref }} | |
PR_NUMBER: ${{ steps.select.outputs.pr_number }} | |
YARP_VERSION: ${{ steps.select.outputs.yarp_version }} | |
run: | | |
echo "TIMESTAMP = ${TIMESTAMP}" | |
echo "REPOSITORY_OWNER = ${REPOSITORY_OWNER}" | |
echo "REPOSITORY_NAME = ${REPOSITORY_NAME}" | |
echo "REPOSITORY = ${REPOSITORY}" | |
echo "REF = ${REF}" | |
echo "ENVIRONMENT = ${ENVIRONMENT}" | |
echo "SHA = ${SHA}" | |
echo "HEAD_REF = ${HEAD_REF}" | |
echo "BASE_REF = ${BASE_REF}" | |
echo "PR_NUMBER = ${PR_NUMBER}" | |
echo "YARP_VERSION = ${YARP_VERSION}" | |
- name: "Print Environment" | |
run: | | |
env | |
- name: "Print Event Json" | |
run: | | |
echo "::group::install jq" | |
sudo apt-get update -qq | |
sudo apt-get install -qq -y jq | |
echo "::endgroup::" | |
cat $GITHUB_EVENT_PATH | jq -C | |
sonarcloud: | |
environment: code-analysis | |
name: 'SonarCloud' | |
needs: [select_environment] | |
runs-on: ubuntu-22.04 | |
steps: | |
- name: Clone repository | |
uses: actions/checkout@v3 | |
with: | |
repository: ${{ needs.select_environment.outputs.repository }} | |
ref: ${{ needs.select_environment.outputs.ref }} | |
fetch-depth: 0 # Shallow clones should be disabled for a better relevancy of analysis | |
- name: Get Sonar and Prepare Environment | |
id: get_sonar | |
env: | |
SONAR_ORGANIZATION: ${{ needs.select_environment.outputs.repository_owner }} | |
SONAR_PROJECT_KEY: ${{ needs.select_environment.outputs.repository_owner }}_${{ needs.select_environment.outputs.repository_name }} | |
SONAR_PROJECT_NAME: ${{ needs.select_environment.outputs.repository_name }} | |
SONAR_PROJECT_DESCRIPTION: 'Yet Another Robot Platform' | |
SONAR_PROJECT_VERSION: ${{ needs.select_environment.outputs.yarp_version }} | |
SONAR_LINKS_HOMEPAGE: 'https://www.yarp.it/' | |
SONAR_SOURCES: 'src' | |
SONAR_TESTS: 'tests' | |
SONAR_CFAMILY_GCOV_REPORTSPATH: 'build/coverage.info' | |
SONAR_CFAMILY_CACHE_ENABLED: true | |
SONAR_SCANNER_VERSION: '5.0.1.3006' | |
SONAR_THREADS: 2 | |
run: | | |
# Internal variables | |
SONAR_HOME_PATH=.sonar | |
SONAR_CACHE_PATH=${SONAR_HOME_PATH}/cache | |
SONAR_HOME=${HOME}/${SONAR_HOME_PATH} | |
# project name from SonarCloud projet creation page -Dsonar.projectKey=XXXX | |
echo "SONAR_PROJECT_KEY=${SONAR_PROJECT_KEY}" >> $GITHUB_ENV | |
# project name from SonarCloud projet creation page -Dsonar.projectKey=XXXX | |
echo "SONAR_PROJECT_NAME=${SONAR_PROJECT_NAME}" >> $GITHUB_ENV | |
# project name from SonarCloud projet creation page -Dsonar.projectName=XXXX | |
echo "SONAR_ORGANIZATION=${SONAR_ORGANIZATION}" >> $GITHUB_ENV | |
# project version | |
[[ ! -z "${SONAR_PROJECT_VERSION}" ]] && echo "SONAR_PROJECT_VERSION=${SONAR_PROJECT_VERSION}" >> $GITHUB_ENV | |
# Links | |
echo "SONAR_LINKS_HOMEPAGE=${SONAR_LINKS_HOMEPAGE:-https://github.com/${GITHUB_REPOSITORY}/}" >> $GITHUB_ENV | |
echo "SONAR_LINKS_CI=${SONAR_LINKS_CI:-https://github.com/${GITHUB_REPOSITORY}/actions/}" >> $GITHUB_ENV | |
echo "SONAR_LINKS_ISSUE=${SONAR_LINKS_ISSUE:-https://github.com/${GITHUB_REPOSITORY}/issues/}" >> $GITHUB_ENV | |
echo "SONAR_LINKS_SCM=${SONAR_LINKS_SCM:-https://github.com/${GITHUB_REPOSITORY}/}" >> $GITHUB_ENV | |
# Set default to SONAR_HOST_URL in not provided | |
echo "SONAR_HOST_URL=${SONAR_HOST_URL:-https://sonarcloud.io}" >> $GITHUB_ENV | |
echo "SONAR_SCANNER_VERSION=${SONAR_SCANNER_VERSION}" >> $GITHUB_ENV | |
SONAR_SCANNER_HOME=${SONAR_HOME}/sonar-scanner-${SONAR_SCANNER_VERSION}-linux | |
echo "SONAR_SCANNER_HOME=${SONAR_SCANNER_HOME}" >> $GITHUB_ENV | |
echo "SONAR_SCANNER_OPTS=${SONAR_SCANNER_OPTS:--server}" >> $GITHUB_ENV | |
echo "SONAR_SOURCES=${SONAR_SOURCES:-src}" >> $GITHUB_ENV | |
[[ -v SONAR_TESTS ]] && echo "SONAR_TESTS=${SONAR_TESTS}" >> $GITHUB_ENV | |
echo "SONAR_SOURCEENCODING=${SONAR_SOURCEENCODING:-UTF-8}" >> $GITHUB_ENV | |
echo "SONAR_THREADS=${SONAR_THREADS:-1}" >> $GITHUB_ENV | |
echo "SONAR_CFAMILY_CACHE_ENABLED=$([[ $SONAR_CFAMILY_CACHE_ENABLED = true ]] && echo true || echo false)" >> $GITHUB_ENV | |
[[ $SONAR_CFAMILY_CACHE_ENABLED = true ]] && echo "SONAR_CFAMILY_CACHE_PATH=${SONAR_CACHE_PATH}" >> $GITHUB_ENV | |
echo "PATH=${SONAR_HOME}/build-wrapper-linux-x86:${SONAR_SCANNER_HOME}/bin:${PATH}" >> $GITHUB_ENV | |
mkdir -p ${SONAR_HOME} | |
mkdir -p ${SONAR_CACHE_PATH} | |
cat $GITHUB_ENV | |
# Download sonar-scanner | |
curl -sSLo ${SONAR_HOME}/sonar-scanner.zip https://binaries${SONAR_HOME_PATH}source.com/Distribution/sonar-scanner-cli/sonar-scanner-cli-$SONAR_SCANNER_VERSION-linux.zip | |
unzip -o ${SONAR_HOME}/sonar-scanner.zip -d ${SONAR_HOME}/ | |
# Download build-wrapper | |
curl -sSLo ${SONAR_HOME}/build-wrapper-linux-x86.zip https://sonarcloud.io/static/cpp/build-wrapper-linux-x86.zip | |
unzip -o ${SONAR_HOME}/build-wrapper-linux-x86.zip -d ${SONAR_HOME}/ | |
echo "sonar_path=${SONAR_HOME_PATH}" >> $GITHUB_OUTPUT | |
echo "sonar_cache_path=${SONAR_CACHE_PATH}" >> $GITHUB_OUTPUT | |
# This step is copied from the build step, please keep them in sync until we | |
# find a better way to do it automatically | |
- name: Dependencies [Linux] | |
if: runner.os == 'Linux' | |
shell: bash | |
run: | | |
# Install dep for gstreamer. It must be the first one. | |
sudo apt-get update | |
sudo apt-get install -y libunwind-dev | |
# Install Robotology dependencies from robotology ppa | |
sudo apt-add-repository -y ppa:robotology/ppa | |
sudo apt-get install -qq -y librobottestingframework-dev | |
# Install cmake | |
sudo apt-get install -qq -y cmake | |
which cmake | |
cmake --version | |
/usr/bin/cmake --version | |
# Install ycm | |
wget -nv https://github.com/robotology/ycm/releases/download/v0.15.3/ycm-cmake-modules-0.15.3-all.deb | |
sudo dpkg -i ycm-cmake-modules-0.15.3-all.deb | |
# Install build tools | |
sudo apt-get install -qq -y ccache \ | |
ninja-build \ | |
valgrind \ | |
openjdk-17-jdk \ | |
openjdk-17-jre | |
sudo apt-get install -qq -y libace-dev \ | |
libsqlite3-dev \ | |
libtinyxml-dev \ | |
libedit-dev \ | |
qtbase5-dev \ | |
qtdeclarative5-dev \ | |
qtmultimedia5-dev \ | |
libqt5opengl5-dev \ | |
libqcustomplot-dev \ | |
libopencv-dev \ | |
libeigen3-dev \ | |
libgraphviz-dev \ | |
libgstreamer1.0-dev \ | |
libgstreamer-plugins-base1.0-dev \ | |
libpng-dev \ | |
libv4l-dev \ | |
libavcodec-dev \ | |
libavdevice-dev \ | |
libavformat-dev \ | |
libavutil-dev \ | |
portaudio19-dev \ | |
libsdl1.2-dev \ | |
libopenni2-dev \ | |
libftdi-dev \ | |
libi2c-dev \ | |
libjpeg-dev \ | |
libpcl-dev | |
# Install SWIG and bindings dependencies | |
sudo apt-get install -qq -y swig \ | |
mono-mcs \ | |
liblua5.3-dev \ | |
lua5.3 \ | |
tcl-dev \ | |
tk-dev \ | |
python3-dev \ | |
liboctave-dev \ | |
ruby-dev \ | |
ruby \ | |
perl | |
# Other tools useful in github actions | |
sudo apt-get install -qq -y jq \ | |
wget \ | |
curl \ | |
lcov \ | |
gcovr \ | |
wget \ | |
curl \ | |
xsltproc \ | |
libxml2-utils \ | |
source-highlight | |
# Remove old packages from apt cache | |
sudo apt-get autoclean -qq | |
- name: Prepare ccache environment variables | |
id: init_ccache | |
run: | | |
CCACHE_HOME_PATH=.ccache | |
CCACHE_BASEDIR=$GITHUB_WORKSPACE | |
echo "CCACHE_BASEDIR=${CCACHE_BASEDIR}" >> $GITHUB_ENV | |
echo "CCACHE_HOME_PATH=.ccache" >> $GITHUB_ENV | |
echo "CCACHE_DIR=${CCACHE_BASEDIR}/${CCACHE_HOME_PATH}" >> $GITHUB_ENV | |
echo "CCACHE_COMPRESS=true" >> $GITHUB_ENV | |
echo "CCACHE_COMPRESSLEVEL=6" >> $GITHUB_ENV | |
echo "CCACHE_MAXSIZE=400M" >> $GITHUB_ENV | |
echo "CCACHE_CPP2=yes" >> $GITHUB_ENV | |
echo "PATH=/usr/lib/ccache::${PATH}" >> $GITHUB_ENV | |
cat $GITHUB_ENV | |
echo "ccache_path=${CCACHE_HOME_PATH}" >> $GITHUB_OUTPUT | |
- name: Print info and reset stats before build | |
run: | | |
set -x | |
which ccache | |
ccache --version | |
ccache -p | |
ls -la --color=always /usr/lib/ccache | |
# Reset ccache stats before starting | |
ccache -z | |
gcov --version | |
gcovr --version | |
- name: Handle cache | |
uses: actions/cache@v3 | |
with: | |
path: | | |
${{ steps.init_ccache.outputs.ccache_path }} | |
${{ steps.get_sonar.outputs.sonar_cache_path }} | |
key: sonar-cache-${{ needs.select_environment.outputs.timestamp }} | |
restore-keys: | | |
sonar-cache- | |
- name: Run CMake | |
run: | | |
export CLICOLOR_FORCE=1 | |
export YARP_COLORED_OUTPUT=1 | |
/usr/bin/cmake -S. -Bbuild \ | |
-C .ci/initial-cache.gh.linux.cmake \ | |
-DCMAKE_C_FLAGS=-fdiagnostics-color=always \ | |
-DCMAKE_CXX_FLAGS=-fdiagnostics-color=always \ | |
-DCMAKE_BUILD_TYPE=Profile \ | |
"-DCMAKE_C_FLAGS_PROFILE=-pg -g3 -ggdb -fno-inline -ftest-coverage -fprofile-arcs -DNDEBUG" \ | |
"-DCMAKE_CXX_FLAGS_PROFILE=-pg -g3 -ggdb -fno-inline -ftest-coverage -fprofile-arcs -DNDEBUG" \ | |
-DCMAKE_EXE_LINKER_FLAGS_PROFILE=-lgcov \ | |
-DCMAKE_MODULE_LINKER_FLAGS_PROFILE=-lgcov \ | |
-DCMAKE_SHARED_LINKER_FLAGS_PROFILE=-lgcov \ | |
-DCMAKE_STATIC_LINKER_FLAGS_PROFILE= \ | |
-DCMAKE_EXPORT_COMPILE_COMMANDS:BOOL=ON \ | |
-DYARP_NO_DEPRECATED:BOOL=ON \ | |
-DYARP_COMPILE_BINDINGS:BOOL=OFF | |
- name: Link compile_commands.json in the source directory | |
run: | | |
ln -s build/compile_commands.json . | |
- name: Build inside the build-wrapper | |
run: | | |
build-wrapper-linux-x86-64 --out-dir build_wrapper_output_directory cmake --build build --config Profile | |
- name: Run tests | |
run: | | |
# Download CTest2JUnit.xsl | |
wget https://raw.githubusercontent.com/zanata/zanata-tests/master/scripts/CTest2JUnit.xsl -O CTest2JUnit.xsl | |
# -T Test produces the xml output with the results | |
(cd build && ctest -T test --rerun-failed --output-on-failure --verbose) | |
xsltproc CTest2JUnit.xsl build/Testing/$(head -n 1 < build/Testing/TAG)/Test.xml > build/JUnitTestResults.xml | |
- name: Print tests results file | |
run: | | |
xmllint --format build/JUnitTestResults.xml | source-highlight -s xml --out-format=esc -o STDOUT | |
- name: Print ccache stats after build | |
run: | | |
set -x | |
# Print ccache stats | |
ccache -s | |
- name: Capture coverage info | |
run: | | |
cd build | |
gcovr --exclude="../extern/*" --sonarqube --branches --output coverage.xml --root .. .) | |
- name: Print coverage info file | |
run: | | |
xmllint --format build/coverage.xml | source-highlight -s xml --out-format=esc -o STDOUT | |
- name: Run sonar scanner | |
env: | |
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }} | |
run: | | |
# Run sonar scanner (here, arguments are passed through the command line but most of them can be written in the sonar-project.properties file) | |
[[ -v SONAR_TOKEN ]] && SONAR_TOKEN_CMD_ARG="-Dsonar.login=${SONAR_TOKEN}" | |
[[ -v SONAR_ORGANIZATION ]] && SONAR_ORGANIZATION_CMD_ARG="-Dsonar.organization=${SONAR_ORGANIZATION}" | |
[[ -v SONAR_PROJECT_NAME ]] && SONAR_PROJECT_NAME_CMD_ARG="-Dsonar.projectName=${SONAR_PROJECT_NAME}" | |
[[ -v SONAR_PROJECT_DESCRIPTION ]] && SONAR_PROJECT_DESCRIPTION_CMD_ARG="-Dsonar.projectDescription=${SONAR_PROJECT_DESCRIPTION}" | |
[[ -v SONAR_PROJECT_VERSION ]] && SONAR_PROJECT_VERSION_CMD_ARG="-Dsonar.projectVersion=${SONAR_PROJECT_VERSION}" | |
if [[ "$GITHUB_EVENT_NAME" = "pull_request" || "$GITHUB_EVENT_NAME" == "pull_request_target" ]]; then | |
SONAR_PR_CMD_ARGS="\ | |
-Dsonar.pullrequest.provider=github \ | |
-Dsonar.pullrequest.github.repository=${SONAR_ORGANIZATION}/${SONAR_PROJECT_NAME} \ | |
-Dsonar.pullrequest.branch=${{ needs.select_environment.outputs.head_ref }} \ | |
-Dsonar.pullrequest.key=${{ needs.select_environment.outputs.pr_number }} \ | |
-Dsonar.pullrequest.base=${{ needs.select_environment.outputs.base_ref }} \ | |
-Dsonar.pullrequest.github.endpoint=https://api.github.com" | |
fi | |
# Paths to test files | |
[[ -v SONAR_TESTS ]] && SONAR_TESTS_CMD_ARG="-Dsonar.tests=${SONAR_TESTS}" | |
# Path to cache | |
[[ -v SONAR_CFAMILY_CACHE_PATH ]] && SONAR_CFAMILY_CACHE_PATH_CMD_ARG="-Dsonar.cfamily.cache.path=${SONAR_CFAMILY_CACHE_PATH}" | |
set -x | |
sonar-scanner \ | |
-Dsonar.host.url="${SONAR_HOST_URL}" \ | |
-Dsonar.projectKey=${SONAR_PROJECT_KEY} \ | |
-Dsonar.language=c++ \ | |
-Dsonar.sources=${SONAR_SOURCES} \ | |
-Dsonar.links.homepage=${SONAR_LINKS_HOMEPAGE} \ | |
-Dsonar.links.ci=${SONAR_LINKS_CI} \ | |
-Dsonar.links.issue=${SONAR_LINKS_ISSUE} \ | |
-Dsonar.links.scm=${SONAR_LINKS_SCM} \ | |
-Dsonar.cfamily.build-wrapper-output=build_wrapper_output_directory \ | |
-Dsonar.sourceEncoding=${SONAR_SOURCEENCODING} \ | |
-Dsonar.cfamily.threads=${SONAR_THREADS} \ | |
-Dsonar.cfamily.cache.enabled=${SONAR_CFAMILY_CACHE_ENABLED} \ | |
-Dsonar.coverageReportPaths=build/coverage.xml \ | |
-Dsonar.junit.reportPaths=build/JUnitTestResults.xml \ | |
-Dsonar.exclusions="src/yarp*/**/* src/carriers/**/* src/devices/**/* src/idls/**/* src/libyarp*/**/* src/robottestingframework-plugins/**/* tests/**/*" \ | |
-Dsonar.coverage.exclusions="\ | |
src/devices/*/tests/*,\ | |
src/carriers/*/tests/*,\ | |
src/portmonitors/*/tests/*,\ | |
tests/**/*,\ | |
src/yarp*/**/*,\ | |
robottestingframework-plugins/**/*\ | |
" \ | |
-Dsonar.branch.longLivedBranches.regex="^(master|yarp-.+)$" \ | |
${SONAR_TESTS_CMD_ARG} \ | |
${SONAR_PROJECT_NAME_CMD_ARG} \ | |
${SONAR_PROJECT_DESCRIPTION_CMD_ARG} \ | |
${SONAR_PROJECT_VERSION_CMD_ARG} \ | |
${SONAR_PR_CMD_ARGS} \ | |
${SONAR_TOKEN_CMD_ARG} \ | |
${SONAR_ORGANIZATION_CMD_ARG} \ | |
${SONAR_CFAMILY_CACHE_PATH_CMD_ARG} |