diff --git a/.circleci/config.yml b/.circleci/config.yml index ff7eb5002..7a92d1e53 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -16,7 +16,39 @@ # under the License. version: 2.1 + +executors: + jdk11: + docker: + - image: cimg/openjdk:11.0 + resource_class: large + commands: + store_test_artifacts: + description: Store test reports and results + steps: + - store_artifacts: + path: build/test-reports + destination: test-reports + - store_artifacts: + path: build/reports + destination: reports + - store_test_results: + path: build/test-reports + + collect_jacoco: + description: Collect JaCoCo results and persist to workspace for delta coverage + steps: + - run: + name: Move Jacoco results to unique folder + command: | + UNIQUE_ID="${CIRCLE_WORKFLOW_ID}-${CIRCLE_JOB}-${CIRCLE_NODE_INDEX}" + ./scripts/get-jacoco-results.sh "jacoco-results/${UNIQUE_ID}" + - persist_to_workspace: + root: ./jacoco-results + paths: + - "**/*" + install_common: steps: - run: sudo apt-get update @@ -122,9 +154,7 @@ commands: jobs: build-deps-jdk11: - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - install_common - checkout @@ -140,9 +170,7 @@ jobs: - "org/**/*" spark3-2_12-jdk11-big: - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - install_common - checkout @@ -153,23 +181,12 @@ jobs: scala: "2.12" jdk: "11" use_jdk11: "true" - - - store_artifacts: - path: build/test-reports - destination: test-reports - - - store_artifacts: - path: build/reports - destination: reports - - - store_test_results: - path: build/test-reports + - store_test_artifacts + - collect_jacoco int-c4-spark3-2_12-jdk11: parallelism: 8 - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - setup_remote_docker - install_common @@ -182,26 +199,13 @@ jobs: jdk: "11" use_jdk11: "true" cassandra: "4.1.4" - - - store_artifacts: - path: build/test-reports - destination: test-reports - - - store_artifacts: - path: build/reports - destination: reports - + - store_test_artifacts - store_artifacts: path: cassandra-analytics-integration-tests destination: int-tests-misc - - store_test_results: - path: build/test-reports - spark3-2_13-jdk11-big: - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - install_common - checkout @@ -212,22 +216,11 @@ jobs: scala: "2.13" jdk: "11" use_jdk11: "true" - - - store_artifacts: - path: build/test-reports - destination: test-reports - - - store_artifacts: - path: build/reports - destination: reports - - - store_test_results: - path: build/test-reports + - store_test_artifacts + - collect_jacoco spark3-2_13-jdk11-bti: - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - install_common - checkout @@ -239,23 +232,11 @@ jobs: jdk: "11" use_jdk11: "true" sstable_format: "bti" - - - store_artifacts: - path: build/test-reports - destination: test-reports - - - store_artifacts: - path: build/reports - destination: reports - - - store_test_results: - path: build/test-reports + - store_test_artifacts int-c4-spark3-2_13-jdk11: parallelism: 8 - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - setup_remote_docker - install_common @@ -268,23 +249,12 @@ jobs: jdk: "11" use_jdk11: "true" cassandra: "4.1.4" - - - store_artifacts: - path: build/test-reports - destination: test-reports - - - store_artifacts: - path: build/reports - destination: reports - - - store_test_results: - path: build/test-reports + - store_test_artifacts + - collect_jacoco int-c5-spark3-2_13-jdk11: parallelism: 8 - docker: - - image: cimg/openjdk:11.0 - resource_class: large + executor: jdk11 steps: - setup_remote_docker - install_common @@ -297,17 +267,18 @@ jobs: jdk: "11" use_jdk11: "true" cassandra: "5.0.5" + - store_test_artifacts + - collect_jacoco - - store_artifacts: - path: build/test-reports - destination: test-reports - - - store_artifacts: - path: build/reports - destination: reports - - - store_test_results: - path: build/test-reports + # Delta coverage plugin requires java 11 so we only validate in java 11 builds + validate_delta_coverage: + executor: jdk11 + steps: + - install_common + - checkout + - attach_workspace: + at: jacoco-results + - run: ./gradlew --info deltaCoverage workflows: version: 2 @@ -332,3 +303,9 @@ workflows: - int-c5-spark3-2_13-jdk11: requires: - build-deps-jdk11 + - validate_delta_coverage: + requires: + - spark3-2_12-jdk11-big + - spark3-2_13-jdk11-big + - int-c4-spark3-2_12-jdk11 + - int-c4-spark3-2_13-jdk11 diff --git a/CHANGES.txt b/CHANGES.txt index caf58b05a..3ad32c903 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -1,5 +1,6 @@ 0.3.0 ----- + * Integrate delta-coverage-plugin plugin (CASSANALYTICS-1) * Fix ByteBuffer flip() in StreamBuffer.copyBytes() causing data corruption (CASSANALYTICS-116) * Fix race condition in DirectStreamSession#onSSTablesProduced and SortedSStableWriter#close (CASSANALYTICS-107) * Address LZ4 vulnerability (CVE-2025-12183) (CASSANALYTICS-109) diff --git a/build.gradle b/build.gradle index 396806a8c..d6a66c673 100644 --- a/build.gradle +++ b/build.gradle @@ -32,6 +32,8 @@ plugins { // Release Audit Tool (RAT) plugin for checking project licenses id("org.nosphere.apache.rat") version "0.8.1" + id("io.github.surpsg.delta-coverage") version "2.4.0" + id("jacoco") } repositories { @@ -252,6 +254,29 @@ subprojects { println() println(version) } + + deltaCoverageReport { + diffSource { + git.compareWith("refs/remotes/origin/trunk") + git.useNativeGit.set(true) + } + + coverageBinaryFiles = fileTree(".") { include("**/*.exec") } + + violationRules { + failOnViolation.set(true) + rule(io.github.surpsg.deltacoverage.gradle.CoverageEntity.LINE) { + minCoverageRatio.set(0.9d) + } + rule(io.github.surpsg.deltacoverage.gradle.CoverageEntity.BRANCH) { + minCoverageRatio.set(0.7d) + } + } + + reports { + html.set(true) + } + } } distributions { diff --git a/cassandra-analytics-cdc/build.gradle b/cassandra-analytics-cdc/build.gradle index cd4a2dc29..23af10bcf 100644 --- a/cassandra-analytics-cdc/build.gradle +++ b/cassandra-analytics-cdc/build.gradle @@ -22,6 +22,7 @@ import java.nio.file.Paths plugins { id('java-library') id('maven-publish') + id('jacoco') } if (propertyWithDefault("artifactType", null) == "spark") diff --git a/cassandra-analytics-common/build.gradle b/cassandra-analytics-common/build.gradle index 96b7e7f60..e0a6657d7 100644 --- a/cassandra-analytics-common/build.gradle +++ b/cassandra-analytics-common/build.gradle @@ -22,6 +22,7 @@ import java.nio.file.Paths plugins { id('java-library') id('maven-publish') + id('jacoco') } if (propertyWithDefault("artifactType", null) == "common") diff --git a/scripts/get-jacoco-results.sh b/scripts/get-jacoco-results.sh new file mode 100755 index 000000000..333a729ea --- /dev/null +++ b/scripts/get-jacoco-results.sh @@ -0,0 +1,32 @@ +#!/bin/bash +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +search_dir="." + +target_folder="${1}" + +mkdir -p "$target_folder" + +find "$search_dir" -type d -path "*/build/jacoco" -print0 | while IFS= read -r -d '' dir; do + destination_path="$target_folder/${dir:2}" + mkdir -p "$destination_path" + cp -r "$dir" "$destination_path" + echo "Copied folder $dir to $destination_path" +done +