diff --git a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/api/client/GradleEnterpriseApiClient.java b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/api/client/GradleEnterpriseApiClient.java index ff452218..4aed4471 100644 --- a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/api/client/GradleEnterpriseApiClient.java +++ b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/api/client/GradleEnterpriseApiClient.java @@ -115,7 +115,8 @@ public BuildValidationData fetchBuildValidationData(String buildScanId) { attributes.getRequestedTasks(), buildOutcomeFrom(attributes), remoteBuildCacheUrlFrom(buildCachePerformance), - summarizeTaskExecutions(buildCachePerformance) + summarizeTaskExecutions(buildCachePerformance), + toDuration(buildCachePerformance.getEffectiveTaskExecutionTime()) ); } if (build.getBuildToolType().equalsIgnoreCase("maven")) { @@ -132,7 +133,8 @@ public BuildValidationData fetchBuildValidationData(String buildScanId) { attributes.getRequestedGoals(), buildOutcomeFrom(attributes), remoteBuildCacheUrlFrom(buildCachePerformance), - summarizeTaskExecutions(buildCachePerformance) + summarizeTaskExecutions(buildCachePerformance), + toDuration(buildCachePerformance.getEffectiveProjectExecutionTime()) ); } throw new UnknownBuildAgentException(baseUrl, buildScanId, build.getBuildToolType()); diff --git a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/FetchBuildValidationDataCommand.java b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/FetchBuildValidationDataCommand.java index a1c0991c..f1818dde 100644 --- a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/FetchBuildValidationDataCommand.java +++ b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/FetchBuildValidationDataCommand.java @@ -14,6 +14,7 @@ import java.net.MalformedURLException; import java.net.URL; import java.nio.file.Path; +import java.time.Duration; import java.util.ArrayList; import java.util.Collections; import java.util.List; @@ -105,7 +106,8 @@ private BuildValidationData fetchBuildScanData(int index, URL buildScanUrl, Cust Collections.emptyList(), "", null, - Collections.emptyMap()); + Collections.emptyMap(), + Duration.ZERO); } } diff --git a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/Fields.java b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/Fields.java index 671d5ece..3f8ce5f3 100644 --- a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/Fields.java +++ b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/cli/Fields.java @@ -30,6 +30,7 @@ public enum Fields { EXECUTED_CACHEABLE_DURATION("Executed cacheable duration", d -> totalDuration(d, "executed_cacheable")), EXECUTED_NOT_CACHEABLE("Executed not cacheable", d -> totalTasks(d, "executed_not_cacheable")), EXECUTED_NOT_CACHEABLE_DURATION("Executed not cacheable duration", d -> totalDuration(d, "executed_not_cacheable")), + EFFECTIVE_TASK_EXECUTION_DURATION("Effective task execution duration", d -> String.valueOf(d.getEffectiveTaskExecutionDuration().toMillis())), ; public final String label; diff --git a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/model/BuildValidationData.java b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/model/BuildValidationData.java index a269eb07..ebcd51a9 100644 --- a/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/model/BuildValidationData.java +++ b/components/fetch-build-scan-data-cmdline-tool/src/main/java/com/gradle/enterprise/model/BuildValidationData.java @@ -2,13 +2,14 @@ import java.net.MalformedURLException; import java.net.URL; +import java.time.Duration; import java.util.List; import java.util.Map; import java.util.regex.Matcher; import java.util.regex.Pattern; public class BuildValidationData { - private static Pattern REMOTE_BUILD_CACHE_SHARD_PATTERN = Pattern.compile(".*/cache/(.+)$"); + private static final Pattern REMOTE_BUILD_CACHE_SHARD_PATTERN = Pattern.compile(".*/cache/(.+)$"); private final String rootProjectName; private final String buildScanId; @@ -20,8 +21,20 @@ public class BuildValidationData { private final String buildOutcome; private final URL remoteBuildCacheUrl; private final Map tasksByAvoidanceOutcome; - - public BuildValidationData(String rootProjectName, String buildScanId, URL gradleEnterpriseServerUrl, String gitUrl, String gitBranch, String gitCommitId, List requestedTasks, String buildOutcome, URL remoteBuildCacheUrl, Map tasksByAvoidanceOutcome) { + private final Duration effectiveTaskExecutionDuration; + + public BuildValidationData( + String rootProjectName, + String buildScanId, + URL gradleEnterpriseServerUrl, + String gitUrl, + String gitBranch, + String gitCommitId, + List requestedTasks, + String buildOutcome, + URL remoteBuildCacheUrl, + Map tasksByAvoidanceOutcome, + Duration effectiveTaskExecutionDuration) { this.rootProjectName = rootProjectName; this.buildScanId = buildScanId; this.gradleEnterpriseServerUrl = gradleEnterpriseServerUrl; @@ -32,6 +45,7 @@ public BuildValidationData(String rootProjectName, String buildScanId, URL gradl this.buildOutcome = buildOutcome; this.remoteBuildCacheUrl = remoteBuildCacheUrl; this.tasksByAvoidanceOutcome = tasksByAvoidanceOutcome; + this.effectiveTaskExecutionDuration = effectiveTaskExecutionDuration; } public String getRootProjectName() { @@ -124,4 +138,8 @@ private static boolean isFound(String value) { public Map getTasksByAvoidanceOutcome() { return tasksByAvoidanceOutcome; } + + public Duration getEffectiveTaskExecutionDuration() { + return effectiveTaskExecutionDuration; + } } diff --git a/components/scripts/gradle/02-validate-local-build-caching-same-location.sh b/components/scripts/gradle/02-validate-local-build-caching-same-location.sh index a331ce83..bbdbe87a 100755 --- a/components/scripts/gradle/02-validate-local-build-caching-same-location.sh +++ b/components/scripts/gradle/02-validate-local-build-caching-same-location.sh @@ -167,7 +167,7 @@ fetch_build_cache_metrics() { # Overrides info.sh#print_performance_metrics print_performance_metrics() { - print_build_caching_leverage_metrics + print_performance_characteristics } print_quick_links() { @@ -313,7 +313,7 @@ two build scans that were published as part of running the experiment. The build scan of the second build is particularly interesting since this is where you can inspect what tasks were not leveraging the local build cache. -$(explain_build_cache_leverage) +$(explain_performance_characteristics) The ‘Investigation Quick Links’ section below allows quick navigation to the most relevant views in build scans to investigate what tasks were avoided due to @@ -335,7 +335,7 @@ The ‘Summary’ section below captures the configuration of the experiment. No build scans are available for inspection since publishing was disabled for the experiment. -$(explain_build_cache_leverage) +$(explain_performance_characteristics) $(explain_command_to_repeat_experiment) @@ -349,12 +349,13 @@ EOF print_wizard_text "${text}" } -explain_build_cache_leverage() { +explain_performance_characteristics() { local text IFS='' read -r -d '' text < 0)); then print_bl warn "Not all cacheable ${BUILD_TOOL_TASK}s' outputs were taken from the build cache in the second build. This reduces the savings in ${BUILD_TOOL_TASK} execution time." @@ -230,3 +263,21 @@ create_receipt_file() { echo "Generated by $(print_version)" } > "${RECEIPT_FILE}" } + +format_duration() { + local duration=$1 + local hours=$((duration/60/60/1000)) + local minutes=$((duration/60/1000%60)) + local seconds=$((duration/1000%60%60)) + local millis=$((duration%1000)) + + if [[ "${hours}" != 0 ]]; then + printf "%dh " "${hours}" + fi + + if [[ "${minutes}" != 0 ]]; then + printf "%dm " "${minutes}" + fi + + printf "%d.%03ds" "${seconds}" "${millis}" +} diff --git a/components/scripts/maven/01-validate-local-build-caching-same-location.sh b/components/scripts/maven/01-validate-local-build-caching-same-location.sh index 7e1b8e0b..50ae293b 100755 --- a/components/scripts/maven/01-validate-local-build-caching-same-location.sh +++ b/components/scripts/maven/01-validate-local-build-caching-same-location.sh @@ -168,7 +168,7 @@ fetch_build_cache_metrics() { # Overrides info.sh#print_performance_metrics print_performance_metrics() { - print_build_caching_leverage_metrics + print_performance_characteristics } print_quick_links() { @@ -314,7 +314,7 @@ two build scans that were published as part of running the experiment. The build scan of the second build is particularly interesting since this is where you can inspect what goals were not leveraging the local build cache. -$(explain_build_cache_leverage) +$(explain_performance_characteristics) The ‘Investigation Quick Links’ section below allows quick navigation to the most relevant views in build scans to investigate what goals were avoided due to @@ -336,7 +336,7 @@ The ‘Summary’ section below captures the configuration of the experiment. No build scans are available for inspection since publishing was disabled for the experiment. -$(explain_build_cache_leverage) +$(explain_performance_characteristics) $(explain_command_to_repeat_experiment) @@ -350,12 +350,13 @@ EOF print_wizard_text "${text}" } -explain_build_cache_leverage() { +explain_performance_characteristics() { local text IFS='' read -r -d '' text <