Repository: cristianadam/HelloWorld Branch: master Commit: f1f9814e010b Files: 5 Total size: 11.8 KB Directory structure: gitextract_n4aisezb/ ├── .github/ │ └── workflows/ │ └── build_cmake.yml ├── CMakeLists.txt ├── LICENSE.md ├── README.md └── main.cpp ================================================ FILE CONTENTS ================================================ ================================================ FILE: .github/workflows/build_cmake.yml ================================================ name: CMake Build Matrix on: [push, pull_request] env: CMAKE_VERSION: "3.29.6" NINJA_VERSION: "1.12.1" BUILD_TYPE: Release CCACHE_VERSION: "4.10" jobs: build: name: ${{ matrix.config.name }} runs-on: ${{ matrix.config.os }} outputs: tag: ${{ steps.git.outputs.tag }} strategy: fail-fast: false matrix: config: - { name: "Windows Latest MSVC", artifact: "Windows-MSVC", os: windows-latest, cc: "cl", cxx: "cl", environment_script: "C:/Program Files/Microsoft Visual Studio/2022/Enterprise/VC/Auxiliary/Build/vcvars64.bat" } - { name: "Windows Latest MinGW", artifact: "Windows-MinGW", os: windows-latest, cc: "gcc", cxx: "g++" } - { name: "Ubuntu Latest GCC", artifact: "Linux", os: ubuntu-latest, cc: "gcc", cxx: "g++" } - { name: "macOS Latest Clang", artifact: "macOS", os: macos-latest, cc: "clang", cxx: "clang++" } steps: - uses: actions/checkout@v4 - name: Checkout submodules id: git shell: cmake -P {0} run: | if (${{github.ref}} MATCHES "tags/v(.*)") file(APPEND "$ENV{GITHUB_OUTPUT}" "tag=${CMAKE_MATCH_1}\n") else() file(APPEND "$ENV{GITHUB_OUTPUT}" "tag=${{github.run_id}}\n") endif() - name: Download Ninja and CMake shell: cmake -P {0} run: | set(cmake_version $ENV{CMAKE_VERSION}) set(ninja_version $ENV{NINJA_VERSION}) message(STATUS "Using host CMake version: ${CMAKE_VERSION}") if ("${{ runner.os }}" STREQUAL "Windows") set(ninja_suffix "win.zip") set(cmake_suffix "windows-x86_64.zip") set(cmake_dir "cmake-${cmake_version}-windows-x86_64/bin") elseif ("${{ runner.os }}" STREQUAL "Linux") set(ninja_suffix "linux.zip") set(cmake_suffix "linux-x86_64.tar.gz") set(cmake_dir "cmake-${cmake_version}-linux-x86_64/bin") elseif ("${{ runner.os }}" STREQUAL "macOS") set(ninja_suffix "mac.zip") set(cmake_suffix "macos-universal.tar.gz") set(cmake_dir "cmake-${cmake_version}-macos-universal/CMake.app/Contents/bin") endif() set(ninja_url "https://github.com/ninja-build/ninja/releases/download/v${ninja_version}/ninja-${ninja_suffix}") file(DOWNLOAD "${ninja_url}" ./ninja.zip SHOW_PROGRESS) execute_process(COMMAND ${CMAKE_COMMAND} -E tar xvf ./ninja.zip) set(cmake_url "https://github.com/Kitware/CMake/releases/download/v${cmake_version}/cmake-${cmake_version}-${cmake_suffix}") file(DOWNLOAD "${cmake_url}" ./cmake.zip SHOW_PROGRESS) execute_process(COMMAND ${CMAKE_COMMAND} -E tar xvf ./cmake.zip) # Add to PATH environment variable file(TO_CMAKE_PATH "$ENV{GITHUB_WORKSPACE}/${cmake_dir}" cmake_dir) set(path_separator ":") if ("${{ runner.os }}" STREQUAL "Windows") set(path_separator ";") endif() file(APPEND "$ENV{GITHUB_PATH}" "$ENV{GITHUB_WORKSPACE}${path_separator}${cmake_dir}") if (NOT "${{ runner.os }}" STREQUAL "Windows") execute_process( COMMAND chmod +x ninja COMMAND chmod +x ${cmake_dir}/cmake ) endif() - name: Download ccache id: ccache shell: cmake -P {0} run: | if ("${{ runner.os }}" STREQUAL "Windows") set(ccache_dir "ccache-$ENV{CCACHE_VERSION}-windows-x86_64") set(ccache_archive "${ccache_dir}.zip") elseif ("${{ runner.os }}" STREQUAL "Linux") set(ccache_dir "ccache-$ENV{CCACHE_VERSION}-linux-x86_64") set(ccache_archive "${ccache_dir}.tar.xz") elseif ("${{ runner.os }}" STREQUAL "macOS") set(ccache_dir "ccache-$ENV{CCACHE_VERSION}-darwin") set(ccache_archive "${ccache_dir}.tar.gz") endif() set(ccache_url "https://github.com/ccache/ccache/releases/download/v$ENV{CCACHE_VERSION}/${ccache_archive}") file(DOWNLOAD "${ccache_url}" ./${ccache_archive} SHOW_PROGRESS) execute_process(COMMAND ${CMAKE_COMMAND} -E tar xvf ./${ccache_archive}) # Add to PATH environment variable file(TO_CMAKE_PATH "$ENV{GITHUB_WORKSPACE}/${ccache_dir}" ccache_dir) set(path_separator ":") if ("${{ runner.os }}" STREQUAL "Windows") set(path_separator ";") endif() file(APPEND "$ENV{GITHUB_PATH}" "$ENV{GITHUB_WORKSPACE}${path_separator}${ccache_dir}") if (NOT "${{ runner.os }}" STREQUAL "Windows") execute_process(COMMAND chmod +x ${ccache_dir}/ccache) endif() - name: Prepare ccache timestamp id: ccache_cache_timestamp shell: cmake -P {0} run: | string(TIMESTAMP current_date "%Y-%m-%d-%H;%M;%S" UTC) file(APPEND "$ENV{GITHUB_OUTPUT}" "timestamp=${current_date}") - name: ccache cache files uses: actions/cache@v4 with: path: .ccache key: ${{ matrix.config.name }}-ccache-${{ steps.ccache_cache_timestamp.outputs.timestamp }} restore-keys: | ${{ matrix.config.name }}-ccache- - name: Configure shell: cmake -P {0} run: | set(ENV{CC} ${{ matrix.config.cc }}) set(ENV{CXX} ${{ matrix.config.cxx }}) if ("${{ runner.os }}" STREQUAL "Windows" AND NOT "x${{ matrix.config.environment_script }}" STREQUAL "x") execute_process( COMMAND "${{ matrix.config.environment_script }}" && set OUTPUT_FILE environment_script_output.txt ) file(STRINGS environment_script_output.txt output_lines) foreach(line IN LISTS output_lines) if (line MATCHES "^([a-zA-Z0-9_-]+)=(.*)$") set(ENV{${CMAKE_MATCH_1}} "${CMAKE_MATCH_2}") endif() endforeach() endif() set(path_separator ":") if ("${{ runner.os }}" STREQUAL "Windows") set(path_separator ";") endif() set(ENV{PATH} "$ENV{GITHUB_WORKSPACE}${path_separator}$ENV{PATH}") execute_process( COMMAND cmake -S . -B build -D CMAKE_BUILD_TYPE=$ENV{BUILD_TYPE} -G Ninja -D CMAKE_MAKE_PROGRAM=ninja -D CMAKE_C_COMPILER_LAUNCHER=ccache -D CMAKE_CXX_COMPILER_LAUNCHER=ccache RESULT_VARIABLE result ) if (NOT result EQUAL 0) message(FATAL_ERROR "Bad exit status") endif() - name: Build shell: cmake -P {0} run: | set(ENV{NINJA_STATUS} "[%f/%t %o/sec] ") if ("${{ runner.os }}" STREQUAL "Windows" AND NOT "x${{ matrix.config.environment_script }}" STREQUAL "x") file(STRINGS environment_script_output.txt output_lines) foreach(line IN LISTS output_lines) if (line MATCHES "^([a-zA-Z0-9_-]+)=(.*)$") set(ENV{${CMAKE_MATCH_1}} "${CMAKE_MATCH_2}") endif() endforeach() endif() file(TO_CMAKE_PATH "$ENV{GITHUB_WORKSPACE}" ccache_basedir) set(ENV{CCACHE_BASEDIR} "${ccache_basedir}") set(ENV{CCACHE_DIR} "${ccache_basedir}/.ccache") set(ENV{CCACHE_COMPRESS} "true") set(ENV{CCACHE_COMPRESSLEVEL} "6") set(ENV{CCACHE_MAXSIZE} "400M") if ("${{ matrix.config.cxx }}" STREQUAL "cl") set(ENV{CCACHE_MAXSIZE} "600M") endif() execute_process(COMMAND ccache -p) execute_process(COMMAND ccache -z) execute_process( COMMAND cmake --build build RESULT_VARIABLE result OUTPUT_VARIABLE output ERROR_VARIABLE output ECHO_OUTPUT_VARIABLE ECHO_ERROR_VARIABLE ) if (NOT result EQUAL 0) string(REGEX MATCH "FAILED:.*$" error_message "${output}") string(REPLACE "\n" "%0A" error_message "${error_message}") message("::error::${error_message}") message(FATAL_ERROR "Build failed") endif() - name: ccache statistics shell: cmake -P {0} run: | file(TO_CMAKE_PATH "$ENV{GITHUB_WORKSPACE}" ccache_basedir) set(ENV{CCACHE_BASEDIR} "${ccache_basedir}") set(ENV{CCACHE_DIR} "${ccache_basedir}/.ccache") execute_process(COMMAND ccache -s) - name: Run tests shell: cmake -P {0} run: | include(ProcessorCount) ProcessorCount(N) set(ENV{CTEST_OUTPUT_ON_FAILURE} "ON") execute_process( COMMAND ctest -j ${N} WORKING_DIRECTORY build RESULT_VARIABLE result OUTPUT_VARIABLE output ERROR_VARIABLE output ECHO_OUTPUT_VARIABLE ECHO_ERROR_VARIABLE ) if (NOT result EQUAL 0) string(REGEX MATCH "[0-9]+% tests.*[0-9.]+ sec.*$" test_results "${output}") string(REPLACE "\n" "%0A" test_results "${test_results}") message("::error::${test_results}") message(FATAL_ERROR "Running tests failed!") endif() - name: Install Strip run: cmake --install build --prefix instdir --strip - name: Pack working-directory: instdir run: cmake -E tar cfv ../${{ matrix.config.artifact }}-${{ steps.git.outputs.tag }}.7z --format=7zip . - name: Upload uses: actions/upload-artifact@v4 with: path: ./${{ matrix.config.artifact }}-${{ steps.git.outputs.tag }}.7z name: ${{ matrix.config.artifact }}-${{ steps.git.outputs.tag }}.7z release: if: contains(github.ref, 'tags/v') runs-on: ubuntu-latest needs: build steps: - name: Download artifacts uses: actions/download-artifact@v4 with: path: release-with-dirs - name: Fixup artifacts run: | mkdir release mv release-with-dirs/*/* release/ - name: Create Release id: create_release uses: softprops/action-gh-release@v2 env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} with: tag_name: v${{ needs.build.outputs.tag }} files: release/* draft: false prerelease: false ================================================ FILE: CMakeLists.txt ================================================ cmake_minimum_required(VERSION 3.16) project(main) add_executable(main main.cpp) install(TARGETS main) enable_testing() add_test(NAME main COMMAND main) ================================================ FILE: LICENSE.md ================================================ MIT License Copyright (c) 2019-2024 Cristian Adam Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. ================================================ FILE: README.md ================================================ # HelloWorld A C++ Hello World project, using CMake, ninja, ccache, and GitHub Actions. # Documentation This project was used as an example for these two blog entries: * [Using GitHub Actions with C++ and CMake](https://cristianadam.eu/20191222/using-github-actions-with-c-plus-plus-and-cmake/) * [Speeding up C++ GitHub Actions using ccache](https://cristianadam.eu/20200113/speeding-up-c-plus-plus-github-actions-using-ccache/) ================================================ FILE: main.cpp ================================================ #include int main() { std::cout << "Hello world\n"; }