From 5e1bdd63eb7a51ca8fe53e7075985a5531722eac Mon Sep 17 00:00:00 2001 From: Dmytro Rodionov Date: Sat, 24 May 2025 11:07:25 +0200 Subject: [PATCH 1/3] Introduce the build report service --- .../build/insights/GradleInsightsPlugin.kt | 20 +++++- .../insights/modules/load/SystemLoadModule.kt | 26 ++------ .../modules/load/SystemLoadService.kt | 12 +++- .../timing/ExecutionTimeMeasurementModule.kt | 17 ++---- .../timing/ExecutionTimeMeasurementService.kt | 6 +- .../report/ConsoleExecutionTimeReporter.kt | 35 +++++++---- .../reporters/CompositeReportBuildService.kt | 61 +++++++++++++++++++ .../insights/reporters/CompositeReporter.kt | 18 ------ .../build/insights/reporters/IReporter.kt | 4 +- .../insights/reporters/html/HTMLReporter.kt | 10 +-- 10 files changed, 129 insertions(+), 80 deletions(-) create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReporter.kt diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt b/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt index 95dff6c..73d1079 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt @@ -3,6 +3,9 @@ package com.smplio.gradle.build.insights import com.smplio.gradle.build.insights.modules.graph.GraphBuilder import com.smplio.gradle.build.insights.modules.load.SystemLoadModule import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementModule +import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementService +import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService +import com.smplio.gradle.build.insights.reporters.html.HTMLReporter import org.gradle.api.Plugin import org.gradle.api.Project import org.gradle.api.plugins.ReportingBasePlugin @@ -20,17 +23,30 @@ class GradleInsightsPlugin @Inject constructor(private val registry: BuildEvents project, ) + val compositeReportBuildService = project.gradle.sharedServices.registerIfAbsent( + CompositeReportBuildService::class.java.simpleName, + CompositeReportBuildService::class.java, + ) { + it.parameters.reporters.set(mutableListOf( + pluginConfig.getExecutionTimeMeasurementConfiguration().executionTimeReporter.get(), + ).also { list -> + if (pluginConfig.gatherHtmlReport.get()) { + list.add(HTMLReporter(project)) + } + }) + } + ExecutionTimeMeasurementModule( project, registry, pluginConfig.getExecutionTimeMeasurementConfiguration(), - pluginConfig.gatherHtmlReport, + compositeReportBuildService, ).initialize() SystemLoadModule( project, registry, - pluginConfig.gatherHtmlReport, + compositeReportBuildService, ).initialize() GraphBuilder().also { diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt index 45e15af..9b05ede 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt @@ -1,15 +1,14 @@ package com.smplio.gradle.build.insights.modules.load -import com.smplio.gradle.build.insights.reporters.CompositeReporter -import com.smplio.gradle.build.insights.reporters.html.HTMLReporter +import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService import org.gradle.api.Project -import org.gradle.api.provider.Property +import org.gradle.api.provider.Provider import org.gradle.build.event.BuildEventsListenerRegistry class SystemLoadModule( private val project: Project, private val registry: BuildEventsListenerRegistry, - private val gatherHtmlReport: Property, + private val reportBuildService: Provider, ) { fun initialize() { @@ -17,23 +16,10 @@ class SystemLoadModule( val systemLoadService = sharedServices.registerIfAbsent( SystemLoadService::class.java.simpleName, SystemLoadService::class.java, - ) {} - - project.gradle.taskGraph.whenReady { - val compositeReporter = CompositeReporter( - if (gatherHtmlReport.get()) { - listOf( - HTMLReporter( - project, - ), - ) - } else { - emptyList() - } - ) - val service = systemLoadService.get() - service.reporter = compositeReporter + ) { + it.parameters.reporter.set(reportBuildService) } + registry.onTaskCompletion(systemLoadService) } } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt index d200249..5d9f0b7 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt @@ -1,20 +1,26 @@ package com.smplio.gradle.build.insights.modules.load import com.codahale.metrics.* +import com.smplio.gradle.build.insights.reporters.IReporter +import org.gradle.api.provider.ListProperty +import org.gradle.api.provider.Property import org.gradle.api.services.BuildService import org.gradle.api.services.BuildServiceParameters import org.gradle.tooling.events.FinishEvent import org.gradle.tooling.events.OperationCompletionListener import java.util.concurrent.TimeUnit -abstract class SystemLoadService: BuildService, +abstract class SystemLoadService: BuildService, OperationCompletionListener, AutoCloseable { + interface Parameters: BuildServiceParameters { + val reporter: Property + } + private val registry: MetricRegistry = MetricRegistry() private val metricsReporter: LocalCacheReporter - var reporter: ISystemLoadReporter? = null init { registry.register(SystemLoadMetric.SystemLoadAverageMetric()) @@ -34,7 +40,7 @@ abstract class SystemLoadService: BuildService, override fun onFinish(event: FinishEvent?) {} override fun close() { - reporter?.let { + parameters.reporter.orNull?.let { metricsReporter.close(it) } ?: kotlin.run { metricsReporter.close() diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt index a19c194..b339eff 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt @@ -1,20 +1,19 @@ package com.smplio.gradle.build.insights.modules.timing -import com.smplio.gradle.build.insights.reporters.CompositeReporter -import com.smplio.gradle.build.insights.reporters.html.HTMLReporter +import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService import org.gradle.api.Project -import org.gradle.api.provider.Property import org.gradle.build.event.BuildEventsListenerRegistry import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementService.SerializableStartParameter import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo import com.smplio.gradle.build.insights.modules.timing.models.Measured +import org.gradle.api.provider.Provider import java.util.concurrent.ConcurrentHashMap class ExecutionTimeMeasurementModule( private val project: Project, private val registry: BuildEventsListenerRegistry, private val configuration: ExecutionTimeMeasurementConfiguration, - private val gatherHtmlReport: Property, + private val reportBuildService: Provider, ) { fun initialize() { val buildStartTime = System.currentTimeMillis() @@ -39,14 +38,6 @@ class ExecutionTimeMeasurementModule( } project.gradle.taskGraph.whenReady { - val default = CompositeReporter(mutableListOf( - configuration.executionTimeReporter.get(), - ).also { list -> - if (gatherHtmlReport.get()) { - list.add(HTMLReporter(project)) - } - }) - if (configuration.enabled.get()) { val startParameter = SerializableStartParameter.create( @@ -60,7 +51,7 @@ class ExecutionTimeMeasurementModule( ExecutionTimeMeasurementService::class.java, ) { it.parameters.startParameters.set(startParameter) - it.parameters.reporter.set(default) + it.parameters.reporter.set(reportBuildService) it.parameters.buildStartTime.set(buildStartTime) it.parameters.configurationsTimeline.set(configurationTimeline) } diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt index aceada7..46c6972 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt @@ -4,7 +4,9 @@ import com.smplio.gradle.build.insights.modules.timing.models.BuildInfo import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo import com.smplio.gradle.build.insights.modules.timing.models.Measured import com.smplio.gradle.build.insights.modules.timing.models.TaskInfo -import com.smplio.gradle.build.insights.modules.timing.report.* +import com.smplio.gradle.build.insights.modules.timing.report.BuildHostInfo +import com.smplio.gradle.build.insights.modules.timing.report.ExecutionTimeReport +import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService import org.gradle.StartParameter import org.gradle.api.execution.TaskExecutionGraph import org.gradle.api.provider.ListProperty @@ -27,7 +29,7 @@ abstract class ExecutionTimeMeasurementService : BuildService - val reporter: Property + val reporter: Property val buildStartTime: Property val configurationsTimeline: ListProperty> } diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt index 7404eae..4dff20b 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt @@ -2,25 +2,34 @@ package com.smplio.gradle.build.insights.modules.timing.report import java.time.Duration class ConsoleExecutionTimeReporter: IExecutionTimeReporter { - override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { - val firstTaskStartTime = executionTimeReport.taskExecutionTimeline.minOf { it.startTime } - val lastTaskEndTime = executionTimeReport.taskExecutionTimeline.maxOf { it.endTime } - val totalTaskExecutionTime: Long = lastTaskEndTime - firstTaskStartTime - val longestTaskName: Int = executionTimeReport.taskExecutionTimeline.maxOf { it.measuredInstance.path.length } + 1 - println("Build took: ${Duration.ofMillis(executionTimeReport.buildInfo.duration).seconds}s") + private var executionTimeReport: ExecutionTimeReport? = null - for (measuredTaskInfo in executionTimeReport.taskExecutionTimeline) { - val taskInfo = measuredTaskInfo.measuredInstance - val taskDuration = Duration.ofMillis(measuredTaskInfo.duration).seconds - val progress = createProgressBar((measuredTaskInfo.duration) * 1.0f / totalTaskExecutionTime) - val taskNamePadded = taskInfo.path.padStart(longestTaskName).padEnd(longestTaskName + 1) - println("|${progress}| $taskNamePadded | ${"${taskDuration}s".padStart(4)}") - } + override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { + this.executionTimeReport = executionTimeReport } private fun createProgressBar(progress: Float): String { val numberOfBars = ((progress * 25).toInt() - 1).coerceAtLeast(0) return "${"=".repeat(numberOfBars)}>${" ".repeat(24 - numberOfBars)}" } + + override fun submitReport() { + executionTimeReport?.let { report -> + val firstTaskStartTime = report.taskExecutionTimeline.minOf { it.startTime } + val lastTaskEndTime = report.taskExecutionTimeline.maxOf { it.endTime } + val totalTaskExecutionTime: Long = lastTaskEndTime - firstTaskStartTime + val longestTaskName: Int = report.taskExecutionTimeline.maxOf { it.measuredInstance.path.length } + 1 + + println("Build took: ${Duration.ofMillis(report.buildInfo.duration).seconds}s") + + for (measuredTaskInfo in report.taskExecutionTimeline) { + val taskInfo = measuredTaskInfo.measuredInstance + val taskDuration = Duration.ofMillis(measuredTaskInfo.duration).seconds + val progress = createProgressBar((measuredTaskInfo.duration) * 1.0f / totalTaskExecutionTime) + val taskNamePadded = taskInfo.path.padStart(longestTaskName).padEnd(longestTaskName + 1) + println("|${progress}| $taskNamePadded | ${"${taskDuration}s".padStart(4)}") + } + } + } } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt new file mode 100644 index 0000000..84ac887 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt @@ -0,0 +1,61 @@ +package com.smplio.gradle.build.insights.reporters + +import com.smplio.gradle.build.insights.modules.load.ISystemLoadReporter +import com.smplio.gradle.build.insights.modules.timing.report.ExecutionTimeReport +import com.smplio.gradle.build.insights.modules.timing.report.IExecutionTimeReporter +import org.gradle.StartParameter +import org.gradle.api.execution.TaskExecutionGraph +import org.gradle.api.provider.ListProperty +import org.gradle.api.services.BuildService +import org.gradle.api.services.BuildServiceParameters +import java.io.Serializable +import java.util.concurrent.ConcurrentLinkedQueue + +abstract class CompositeReportBuildService : BuildService, + ISystemLoadReporter, + IExecutionTimeReporter, + AutoCloseable +{ + + interface Parameters: BuildServiceParameters { + val reporters: ListProperty + } + + override fun close() { + submitReport() + } + + override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { + parameters.reporters.orNull?.filterIsInstance()?.forEach { reporter -> + reporter.reportExecutionTime(executionTimeReport) + } + } + + override fun reportSystemLoad(measurements: ConcurrentLinkedQueue>>>) { + parameters.reporters.orNull?.filterIsInstance()?.forEach { reporter -> + reporter.reportSystemLoad(measurements) + } + } + + override fun submitReport() { + parameters.reporters.orNull?.forEach { reporter -> + reporter.submitReport() + } + } + + class SerializableStartParameter private constructor(val taskNames: List) : Serializable { + companion object { + fun create( + startParameter: StartParameter, + taskExecutionGraph: TaskExecutionGraph? = null, + ): SerializableStartParameter { + val taskNameToPathMapping = HashMap() + taskExecutionGraph?.allTasks?.forEach { taskNameToPathMapping[it.name] = it.path } + val startTaskNames = startParameter.taskNames.map { taskName -> taskNameToPathMapping[taskName] ?: taskName } + return SerializableStartParameter( + taskNames = startTaskNames, + ) + } + } + } +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReporter.kt deleted file mode 100644 index 0cbefc2..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReporter.kt +++ /dev/null @@ -1,18 +0,0 @@ -package com.smplio.gradle.build.insights.reporters - -import com.smplio.gradle.build.insights.modules.load.ISystemLoadReporter -import com.smplio.gradle.build.insights.modules.timing.report.ExecutionTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.IExecutionTimeReporter -import java.util.concurrent.ConcurrentLinkedQueue - -class CompositeReporter( - private val reporters: List, -): IExecutionTimeReporter, ISystemLoadReporter { - override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { - reporters.filterIsInstance().forEach { reporter -> reporter.reportExecutionTime(executionTimeReport) } - } - - override fun reportSystemLoad(measurements: ConcurrentLinkedQueue>>>) { - reporters.filterIsInstance().forEach { reporter -> reporter.reportSystemLoad(measurements) } - } -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt index d2d8946..6240899 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt @@ -2,4 +2,6 @@ package com.smplio.gradle.build.insights.reporters import java.io.Serializable -interface IReporter: Serializable \ No newline at end of file +interface IReporter: Serializable { + fun submitReport() +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt index bda1ec8..b42a9e6 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt @@ -60,8 +60,6 @@ class HTMLReporter( tasksFile.bufferedWriter(Charsets.UTF_8).use { it.write(tasks.toString(4)) } - - tryGenerateReport() } override fun reportSystemLoad(measurements: ConcurrentLinkedQueue>>>) { @@ -78,13 +76,9 @@ class HTMLReporter( systemLoadFile.bufferedWriter(Charsets.UTF_8).use { it.write(systemLoadJson.toString(4)) } - - tryGenerateReport() } - private fun tryGenerateReport() { - if (!tasksFile.exists() || !systemLoadFile.exists()) return - + override fun submitReport() { uniqueReportFolder.mkdirs() val scriptJsText = javaClass.getResourceAsStream("/script.js")?.reader()?.use { it.readText() } @@ -112,6 +106,6 @@ class HTMLReporter( tasksFile.delete() systemLoadFile.delete() - println("Report is available in ${reportHtmlFile.absolutePath}") + println("Build insights report is available in ${reportHtmlFile.absolutePath}") } } \ No newline at end of file From 157817b08c347563af7314d6cfae405344165e7d Mon Sep 17 00:00:00 2001 From: Dmytro Rodionov Date: Sun, 25 May 2025 10:27:27 +0200 Subject: [PATCH 2/3] Refactor codebase --- .../build/insights/GradleInsightsPlugin.kt | 41 +++--- .../modules/load/ISystemLoadReportProvider.kt | 7 + .../modules/load/ISystemLoadReporter.kt | 3 +- .../modules/load/LocalCacheReporter.kt | 6 +- .../insights/modules/load/SystemLoadModule.kt | 19 +-- .../insights/modules/load/SystemLoadReport.kt | 5 + .../modules/load/SystemLoadService.kt | 19 +-- .../ExecutionTimeMeasurementConfiguration.kt | 8 +- .../timing/ExecutionTimeMeasurementModule.kt | 63 ++++----- .../report/ConsoleExecutionTimeReporter.kt | 53 ++++++-- ...cutionTimeReport.kt => ExecutionReport.kt} | 10 +- .../IConfigurationTimeReportProvider.kt | 7 + .../report/IConfigurationTimeReporter.kt | 5 + .../timing/report/IExecutionTimeReporter.kt | 7 - .../ITaskExecutionTimeReportProvider.kt | 7 + .../report/ITaskExecutionTimeReporter.kt | 7 + .../ConfigurationTimeReportProvider.kt | 33 +++++ ...askTaskExecutionTimeMeasurementService.kt} | 67 ++-------- .../reporters/CompositeReportBuildService.kt | 89 ++++++++----- .../insights/reporters/IReportProvider.kt | 5 + .../insights/reporters/html/HTMLReporter.kt | 61 ++++----- src/main/resources/index.html | 1 + src/main/resources/script.js | 123 ++++++++++-------- 23 files changed, 358 insertions(+), 288 deletions(-) create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadReport.kt rename src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/{ExecutionTimeReport.kt => ExecutionReport.kt} (76%) create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IExecutionTimeReporter.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt rename src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/{ExecutionTimeMeasurementService.kt => report_providers/TaskTaskExecutionTimeMeasurementService.kt} (51%) create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt b/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt index 73d1079..2625bdd 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt @@ -3,7 +3,6 @@ package com.smplio.gradle.build.insights import com.smplio.gradle.build.insights.modules.graph.GraphBuilder import com.smplio.gradle.build.insights.modules.load.SystemLoadModule import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementModule -import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementService import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService import com.smplio.gradle.build.insights.reporters.html.HTMLReporter import org.gradle.api.Plugin @@ -23,31 +22,41 @@ class GradleInsightsPlugin @Inject constructor(private val registry: BuildEvents project, ) + val executionTimeMeasurementModule = ExecutionTimeMeasurementModule( + project, + registry, + pluginConfig.getExecutionTimeMeasurementConfiguration(), + ) + executionTimeMeasurementModule.initialize() + + val systemLoadModule = SystemLoadModule( + project, + registry, + ) + systemLoadModule.initialize() + val compositeReportBuildService = project.gradle.sharedServices.registerIfAbsent( CompositeReportBuildService::class.java.simpleName, CompositeReportBuildService::class.java, - ) { - it.parameters.reporters.set(mutableListOf( + ) { buildServiceSpec -> + buildServiceSpec.parameters.reporters.set(mutableListOf( pluginConfig.getExecutionTimeMeasurementConfiguration().executionTimeReporter.get(), ).also { list -> if (pluginConfig.gatherHtmlReport.get()) { list.add(HTMLReporter(project)) } }) + executionTimeMeasurementModule.getConfigurationTimeReportProvider().let { + buildServiceSpec.parameters.configurationTimeReportProvider.set(it) + } + executionTimeMeasurementModule.getExecutionTimeReportProvider()?.let { + buildServiceSpec.parameters.executionTimeReportService.set(it) + } + systemLoadModule.getSystemLoadReportProvider()?.let { + buildServiceSpec.parameters.systemLoadReportService.set(it) + } } - - ExecutionTimeMeasurementModule( - project, - registry, - pluginConfig.getExecutionTimeMeasurementConfiguration(), - compositeReportBuildService, - ).initialize() - - SystemLoadModule( - project, - registry, - compositeReportBuildService, - ).initialize() + registry.onTaskCompletion(compositeReportBuildService) GraphBuilder().also { it.buildProjectDependencyGraph(project) diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt new file mode 100644 index 0000000..ac4cb2c --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt @@ -0,0 +1,7 @@ +package com.smplio.gradle.build.insights.modules.load + +import com.smplio.gradle.build.insights.reporters.IReportProvider + +interface ISystemLoadReportProvider: IReportProvider { + fun provideSystemLoadReport(): SystemLoadReport? +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt index 5eb66ac..644287c 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt @@ -1,8 +1,7 @@ package com.smplio.gradle.build.insights.modules.load import com.smplio.gradle.build.insights.reporters.IReporter -import java.util.concurrent.ConcurrentLinkedQueue interface ISystemLoadReporter: IReporter { - fun reportSystemLoad(measurements: ConcurrentLinkedQueue>>>) + fun reportSystemLoad(measurements: SystemLoadReport) } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt index 6b458a8..21aa464 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt @@ -18,7 +18,7 @@ class LocalCacheReporter( filter, rateUnit, durationUnit, -) { +), ISystemLoadReportProvider { private val measurements: ConcurrentLinkedQueue>>> = ConcurrentLinkedQueue() override fun report( @@ -42,8 +42,8 @@ class LocalCacheReporter( measurements.add(measurementTime to measurementsValues) } - fun close(reporter: ISystemLoadReporter) { + override fun provideSystemLoadReport(): SystemLoadReport? { super.close() - reporter.reportSystemLoad(measurements) + return measurements } } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt index 9b05ede..64a3c78 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadModule.kt @@ -1,6 +1,5 @@ package com.smplio.gradle.build.insights.modules.load -import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService import org.gradle.api.Project import org.gradle.api.provider.Provider import org.gradle.build.event.BuildEventsListenerRegistry @@ -8,18 +7,20 @@ import org.gradle.build.event.BuildEventsListenerRegistry class SystemLoadModule( private val project: Project, private val registry: BuildEventsListenerRegistry, - private val reportBuildService: Provider, ) { + private var systemLoadService: Provider? = null + fun initialize() { - val sharedServices = project.gradle.sharedServices - val systemLoadService = sharedServices.registerIfAbsent( + systemLoadService = project.gradle.sharedServices.registerIfAbsent( SystemLoadService::class.java.simpleName, - SystemLoadService::class.java, - ) { - it.parameters.reporter.set(reportBuildService) + SystemLoadService::class.java + ) {}.also { + registry.onTaskCompletion(it) } + } - registry.onTaskCompletion(systemLoadService) + fun getSystemLoadReportProvider(): Provider? { + return systemLoadService } -} \ No newline at end of file +} diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadReport.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadReport.kt new file mode 100644 index 0000000..515a084 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadReport.kt @@ -0,0 +1,5 @@ +package com.smplio.gradle.build.insights.modules.load + +import java.util.concurrent.ConcurrentLinkedQueue + +typealias SystemLoadReport = ConcurrentLinkedQueue>>> diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt index 5d9f0b7..0dc5084 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt @@ -1,24 +1,17 @@ package com.smplio.gradle.build.insights.modules.load import com.codahale.metrics.* -import com.smplio.gradle.build.insights.reporters.IReporter -import org.gradle.api.provider.ListProperty -import org.gradle.api.provider.Property import org.gradle.api.services.BuildService import org.gradle.api.services.BuildServiceParameters import org.gradle.tooling.events.FinishEvent import org.gradle.tooling.events.OperationCompletionListener import java.util.concurrent.TimeUnit -abstract class SystemLoadService: BuildService, +abstract class SystemLoadService: BuildService, OperationCompletionListener, - AutoCloseable + ISystemLoadReportProvider { - interface Parameters: BuildServiceParameters { - val reporter: Property - } - private val registry: MetricRegistry = MetricRegistry() private val metricsReporter: LocalCacheReporter @@ -39,11 +32,7 @@ abstract class SystemLoadService: BuildService, override fun onFinish(event: FinishEvent?) {} - override fun close() { - parameters.reporter.orNull?.let { - metricsReporter.close(it) - } ?: kotlin.run { - metricsReporter.close() - } + override fun provideSystemLoadReport(): SystemLoadReport? { + return metricsReporter.provideSystemLoadReport() } } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt index 37f6c05..9754a8e 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt @@ -1,7 +1,7 @@ package com.smplio.gradle.build.insights.modules.timing import com.smplio.gradle.build.insights.modules.timing.report.ConsoleExecutionTimeReporter -import com.smplio.gradle.build.insights.modules.timing.report.IExecutionTimeReporter +import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReporter import org.gradle.api.model.ObjectFactory import org.gradle.api.provider.Property import javax.inject.Inject @@ -9,9 +9,9 @@ import javax.inject.Inject abstract class ExecutionTimeMeasurementConfiguration @Inject constructor(objects: ObjectFactory) { val enabled: Property = objects.property(Boolean::class.java).convention(true) - val executionTimeReporter: Property = (objects.property( - IExecutionTimeReporter::class.java - ) as Property).convention( + val executionTimeReporter: Property = (objects.property( + ITaskExecutionTimeReporter::class.java + ) as Property).convention( ConsoleExecutionTimeReporter() ) } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt index b339eff..614b507 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt @@ -1,62 +1,49 @@ package com.smplio.gradle.build.insights.modules.timing -import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService +import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReportProvider import org.gradle.api.Project import org.gradle.build.event.BuildEventsListenerRegistry -import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementService.SerializableStartParameter -import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo -import com.smplio.gradle.build.insights.modules.timing.models.Measured +import com.smplio.gradle.build.insights.modules.timing.report_providers.ConfigurationTimeReportProvider +import com.smplio.gradle.build.insights.modules.timing.report_providers.TaskTaskExecutionTimeMeasurementService import org.gradle.api.provider.Provider -import java.util.concurrent.ConcurrentHashMap class ExecutionTimeMeasurementModule( private val project: Project, private val registry: BuildEventsListenerRegistry, private val configuration: ExecutionTimeMeasurementConfiguration, - private val reportBuildService: Provider, ) { - fun initialize() { - val buildStartTime = System.currentTimeMillis() - val configurationStartTimes = ConcurrentHashMap() + private var taskExecutionTimeMeasurementService: Provider? = null + private val configurationTimeReportProvider = ConfigurationTimeReportProvider() - val configurationTimeline = mutableListOf>() + fun initialize() { + val buildStartTime = System.currentTimeMillis() project.gradle.beforeProject { - configurationStartTimes[it.displayName] = System.currentTimeMillis() + configurationTimeReportProvider.onBeforeProject(it) } project.gradle.afterProject { - val startTime = configurationStartTimes[it.displayName] ?: return@afterProject - configurationTimeline.add(Measured( - measuredInstance = ConfigurationInfo( - projectName = it.path, - ), - startTime = startTime, - endTime = System.currentTimeMillis(), - )) + configurationTimeReportProvider.onAfterProject(it) } - project.gradle.taskGraph.whenReady { - if (configuration.enabled.get()) { - - val startParameter = SerializableStartParameter.create( - startParameter = project.gradle.startParameter, - taskExecutionGraph = it, - ) - - val sharedServices = project.gradle.sharedServices - val timerService = sharedServices.registerIfAbsent( - ExecutionTimeMeasurementService::class.java.simpleName, - ExecutionTimeMeasurementService::class.java, - ) { - it.parameters.startParameters.set(startParameter) - it.parameters.reporter.set(reportBuildService) - it.parameters.buildStartTime.set(buildStartTime) - it.parameters.configurationsTimeline.set(configurationTimeline) - } - registry.onTaskCompletion(timerService) + if (configuration.enabled.get()) { + taskExecutionTimeMeasurementService = project.gradle.sharedServices.registerIfAbsent( + TaskTaskExecutionTimeMeasurementService::class.java.simpleName, + TaskTaskExecutionTimeMeasurementService::class.java, + ) { + it.parameters.buildStartTime.set(buildStartTime) + }.also { + registry.onTaskCompletion(it) } } } + + fun getConfigurationTimeReportProvider(): IConfigurationTimeReportProvider { + return configurationTimeReportProvider + } + + fun getExecutionTimeReportProvider(): Provider? { + return taskExecutionTimeMeasurementService + } } diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt index 4dff20b..af3ff69 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt @@ -1,12 +1,17 @@ package com.smplio.gradle.build.insights.modules.timing.report import java.time.Duration -class ConsoleExecutionTimeReporter: IExecutionTimeReporter { +class ConsoleExecutionTimeReporter: IConfigurationTimeReporter, ITaskExecutionTimeReporter { - private var executionTimeReport: ExecutionTimeReport? = null + private var configurationTimeReport: ConfigurationTimeReport? = null + private var taskExecutionTimeReport: TaskExecutionTimeReport? = null - override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { - this.executionTimeReport = executionTimeReport + override fun reportConfigurationTime(configurationTimeReport: ConfigurationTimeReport) { + this.configurationTimeReport = configurationTimeReport + } + + override fun reportTaskExecutionTime(taskExecutionTimeReport: TaskExecutionTimeReport) { + this.taskExecutionTimeReport = taskExecutionTimeReport } private fun createProgressBar(progress: Float): String { @@ -15,15 +20,37 @@ class ConsoleExecutionTimeReporter: IExecutionTimeReporter { } override fun submitReport() { - executionTimeReport?.let { report -> - val firstTaskStartTime = report.taskExecutionTimeline.minOf { it.startTime } - val lastTaskEndTime = report.taskExecutionTimeline.maxOf { it.endTime } - val totalTaskExecutionTime: Long = lastTaskEndTime - firstTaskStartTime - val longestTaskName: Int = report.taskExecutionTimeline.maxOf { it.measuredInstance.path.length } + 1 + var firstConfigurationStartTime = 0L + var lastTaskEndTime = 0L + configurationTimeReport?.let { report -> + println("Configuration time:") + firstConfigurationStartTime = report.minOf { it.startTime } + val lastConfigurationEndTime = report.maxOf { it.endTime } + val totalConfigurationTime: Long = lastConfigurationEndTime - firstConfigurationStartTime + val longestProjectName: Int = report.maxOf { it.measuredInstance.projectName.length } + 1 + + for (measuredConfigurationInfo in report) { + val projectInfo = measuredConfigurationInfo.measuredInstance + val configurationDuration = Duration.ofMillis(measuredConfigurationInfo.duration).seconds + val progress = createProgressBar((measuredConfigurationInfo.duration) * 1.0f / totalConfigurationTime) + val projectNamePadded = projectInfo.projectName.padStart(longestProjectName).padEnd(longestProjectName + 1) + println("|${progress}| $projectNamePadded | ${"${configurationDuration}s".padStart(4)}") + } + } - println("Build took: ${Duration.ofMillis(report.buildInfo.duration).seconds}s") + taskExecutionTimeReport?.let { report -> + println("Task execution time:") + val firstTaskStartTime = report.minOf { it.startTime } - for (measuredTaskInfo in report.taskExecutionTimeline) { + if (firstConfigurationStartTime == 0L) { + firstConfigurationStartTime = firstTaskStartTime + } + + lastTaskEndTime = report.maxOf { it.endTime } + val totalTaskExecutionTime: Long = lastTaskEndTime - firstTaskStartTime + val longestTaskName: Int = report.maxOf { it.measuredInstance.path.length } + 1 + + for (measuredTaskInfo in report) { val taskInfo = measuredTaskInfo.measuredInstance val taskDuration = Duration.ofMillis(measuredTaskInfo.duration).seconds val progress = createProgressBar((measuredTaskInfo.duration) * 1.0f / totalTaskExecutionTime) @@ -31,5 +58,9 @@ class ConsoleExecutionTimeReporter: IExecutionTimeReporter { println("|${progress}| $taskNamePadded | ${"${taskDuration}s".padStart(4)}") } } + + if (firstConfigurationStartTime != 0L && lastTaskEndTime != 0L) { + println("Build took: ${Duration.ofMillis(lastTaskEndTime - firstConfigurationStartTime).seconds}s") + } } } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionTimeReport.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionReport.kt similarity index 76% rename from src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionTimeReport.kt rename to src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionReport.kt index 55e3f71..71c391d 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionTimeReport.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionReport.kt @@ -6,12 +6,14 @@ import com.smplio.gradle.build.insights.modules.timing.models.Measured import com.smplio.gradle.build.insights.modules.timing.models.TaskInfo import java.net.InetAddress -data class ExecutionTimeReport( - val requestedTasks: List, +typealias ConfigurationTimeReport = List> +typealias TaskExecutionTimeReport = List> + +data class ExecutionReport( val buildHostInfo: BuildHostInfo, val buildInfo: Measured, - val configurationTimeline: List>, - val taskExecutionTimeline: List>, + val configurationTimeline: ConfigurationTimeReport, + val taskExecutionTimeline: TaskExecutionTimeReport, ) data class BuildHostInfo( diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt new file mode 100644 index 0000000..95edef2 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt @@ -0,0 +1,7 @@ +package com.smplio.gradle.build.insights.modules.timing.report + +import com.smplio.gradle.build.insights.reporters.IReportProvider + +interface IConfigurationTimeReportProvider: IReportProvider { + fun provideConfigurationTimeReport(): ConfigurationTimeReport? +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt new file mode 100644 index 0000000..3c9db23 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt @@ -0,0 +1,5 @@ +package com.smplio.gradle.build.insights.modules.timing.report + +interface IConfigurationTimeReporter { + fun reportConfigurationTime(configurationTimeReport: ConfigurationTimeReport) +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IExecutionTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IExecutionTimeReporter.kt deleted file mode 100644 index 7ee622f..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IExecutionTimeReporter.kt +++ /dev/null @@ -1,7 +0,0 @@ -package com.smplio.gradle.build.insights.modules.timing.report - -import com.smplio.gradle.build.insights.reporters.IReporter - -interface IExecutionTimeReporter: IReporter { - fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt new file mode 100644 index 0000000..90eee33 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt @@ -0,0 +1,7 @@ +package com.smplio.gradle.build.insights.modules.timing.report + +import com.smplio.gradle.build.insights.reporters.IReportProvider + +interface ITaskExecutionTimeReportProvider: IReportProvider { + fun provideTaskExecutionTimeReport(): TaskExecutionTimeReport? +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt new file mode 100644 index 0000000..67f24f2 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt @@ -0,0 +1,7 @@ +package com.smplio.gradle.build.insights.modules.timing.report + +import com.smplio.gradle.build.insights.reporters.IReporter + +interface ITaskExecutionTimeReporter: IReporter { + fun reportTaskExecutionTime(taskExecutionTimeReport: TaskExecutionTimeReport) +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt new file mode 100644 index 0000000..aa2bc4d --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt @@ -0,0 +1,33 @@ +package com.smplio.gradle.build.insights.modules.timing.report_providers + +import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo +import com.smplio.gradle.build.insights.modules.timing.models.Measured +import com.smplio.gradle.build.insights.modules.timing.report.ConfigurationTimeReport +import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReportProvider +import org.gradle.api.Project +import java.util.concurrent.ConcurrentHashMap + +class ConfigurationTimeReportProvider: IConfigurationTimeReportProvider { + + private val configurationStartTimes = ConcurrentHashMap() + private val configurationTimeline = mutableListOf>() + + override fun provideConfigurationTimeReport(): ConfigurationTimeReport? { + return configurationTimeline + } + + fun onBeforeProject(project: Project) { + configurationStartTimes[project.displayName] = System.currentTimeMillis() + } + + fun onAfterProject(project: Project) { + val startTime = configurationStartTimes[project.displayName] ?: return + configurationTimeline.add(Measured( + measuredInstance = ConfigurationInfo( + projectName = project.path, + ), + startTime = startTime, + endTime = System.currentTimeMillis(), + )) + } +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt similarity index 51% rename from src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt rename to src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt index 46c6972..cef60ee 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt @@ -1,15 +1,10 @@ -package com.smplio.gradle.build.insights.modules.timing +package com.smplio.gradle.build.insights.modules.timing.report_providers -import com.smplio.gradle.build.insights.modules.timing.models.BuildInfo -import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo import com.smplio.gradle.build.insights.modules.timing.models.Measured import com.smplio.gradle.build.insights.modules.timing.models.TaskInfo -import com.smplio.gradle.build.insights.modules.timing.report.BuildHostInfo -import com.smplio.gradle.build.insights.modules.timing.report.ExecutionTimeReport -import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService -import org.gradle.StartParameter -import org.gradle.api.execution.TaskExecutionGraph -import org.gradle.api.provider.ListProperty +import com.smplio.gradle.build.insights.modules.timing.report.TaskExecutionTimeReport +import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReportProvider +import com.smplio.gradle.build.insights.reporters.IReportProvider import org.gradle.api.provider.Property import org.gradle.api.services.BuildService import org.gradle.api.services.BuildServiceParameters @@ -19,19 +14,16 @@ import org.gradle.tooling.events.task.TaskFailureResult import org.gradle.tooling.events.task.TaskFinishEvent import org.gradle.tooling.events.task.TaskSkippedResult import org.gradle.tooling.events.task.TaskSuccessResult -import java.io.Serializable import java.util.concurrent.ConcurrentLinkedQueue -abstract class ExecutionTimeMeasurementService : BuildService, +abstract class TaskTaskExecutionTimeMeasurementService : BuildService, OperationCompletionListener, - AutoCloseable + ITaskExecutionTimeReportProvider, + IReportProvider { interface Parameters: BuildServiceParameters { - val startParameters: Property - val reporter: Property val buildStartTime: Property - val configurationsTimeline: ListProperty> } private var firstTaskStartTime: Long? = null @@ -88,46 +80,15 @@ abstract class ExecutionTimeMeasurementService : BuildService) : Serializable { - companion object { - fun create( - startParameter: StartParameter, - taskExecutionGraph: TaskExecutionGraph? = null, - ): SerializableStartParameter { - val taskNameToPathMapping = HashMap() - taskExecutionGraph?.allTasks?.forEach { taskNameToPathMapping[it.name] = it.path } - val startTaskNames = startParameter.taskNames.map { taskName -> taskNameToPathMapping[taskName] ?: taskName } - return SerializableStartParameter( - taskNames = startTaskNames, - ) - } - } + override fun provideTaskExecutionTimeReport(): TaskExecutionTimeReport? { + return taskExecutionTimeline.toList() } } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt index 84ac887..2f2ec8e 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt @@ -1,61 +1,78 @@ package com.smplio.gradle.build.insights.reporters import com.smplio.gradle.build.insights.modules.load.ISystemLoadReporter -import com.smplio.gradle.build.insights.modules.timing.report.ExecutionTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.IExecutionTimeReporter -import org.gradle.StartParameter -import org.gradle.api.execution.TaskExecutionGraph +import com.smplio.gradle.build.insights.modules.load.SystemLoadService +import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReportProvider +import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReporter +import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReporter +import com.smplio.gradle.build.insights.modules.timing.report_providers.TaskTaskExecutionTimeMeasurementService import org.gradle.api.provider.ListProperty +import org.gradle.api.provider.Property import org.gradle.api.services.BuildService import org.gradle.api.services.BuildServiceParameters -import java.io.Serializable -import java.util.concurrent.ConcurrentLinkedQueue +import org.gradle.tooling.events.FinishEvent +import org.gradle.tooling.events.OperationCompletionListener abstract class CompositeReportBuildService : BuildService, - ISystemLoadReporter, - IExecutionTimeReporter, + OperationCompletionListener, AutoCloseable { - interface Parameters: BuildServiceParameters { val reporters: ListProperty + val configurationTimeReportProvider: Property + val systemLoadReportService: Property + val executionTimeReportService: Property } override fun close() { - submitReport() - } + val reporters = parameters.reporters.orNull ?: return + val systemLoadService = parameters.systemLoadReportService.orNull ?: return + val executionTimeReportService = parameters.executionTimeReportService.orNull ?: return + val configurationTimeReportProvider = parameters.configurationTimeReportProvider.orNull ?: return - override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { - parameters.reporters.orNull?.filterIsInstance()?.forEach { reporter -> - reporter.reportExecutionTime(executionTimeReport) + reporters.filterIsInstance().forEach { reporter -> + systemLoadService.provideSystemLoadReport()?.let { + reporter.reportSystemLoad(it) + } } - } - override fun reportSystemLoad(measurements: ConcurrentLinkedQueue>>>) { - parameters.reporters.orNull?.filterIsInstance()?.forEach { reporter -> - reporter.reportSystemLoad(measurements) + reporters.filterIsInstance().forEach { reporter -> + executionTimeReportService.provideTaskExecutionTimeReport()?.let { + reporter.reportTaskExecutionTime(it) + } } - } - override fun submitReport() { - parameters.reporters.orNull?.forEach { reporter -> - reporter.submitReport() + reporters.filterIsInstance().forEach { reporter -> + configurationTimeReportProvider.provideConfigurationTimeReport()?.let { + reporter.reportConfigurationTime(it) + } } - } - class SerializableStartParameter private constructor(val taskNames: List) : Serializable { - companion object { - fun create( - startParameter: StartParameter, - taskExecutionGraph: TaskExecutionGraph? = null, - ): SerializableStartParameter { - val taskNameToPathMapping = HashMap() - taskExecutionGraph?.allTasks?.forEach { taskNameToPathMapping[it.name] = it.path } - val startTaskNames = startParameter.taskNames.map { taskName -> taskNameToPathMapping[taskName] ?: taskName } - return SerializableStartParameter( - taskNames = startTaskNames, - ) - } + // val reportProviders = parameters.reportProviders.orNull ?: return + // + // reportProviders.forEach { reportProvider -> + // when (reportProvider) { + // is ISystemLoadReportProvider -> { + // reporters.filterIsInstance().forEach { reporter -> + // reportProvider.provideSystemLoadReport()?.let { + // reporter.reportSystemLoad(it) + // } + // } + // } + // is IExecutionTimeReportProvider -> { + // reporters.filterIsInstance().forEach { reporter -> + // reportProvider.provideExecutionTimeReport()?.let { + // reporter.reportExecutionTime(it) + // } + // } + // } + // } + // } + + reporters.forEach { reporter -> + reporter.submitReport() } } + + override fun onFinish(event: FinishEvent?) {} } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt new file mode 100644 index 0000000..0e4dac7 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt @@ -0,0 +1,5 @@ +package com.smplio.gradle.build.insights.reporters + +import java.io.Serializable + +interface IReportProvider: Serializable \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt index b42a9e6..b077f20 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt @@ -1,11 +1,10 @@ package com.smplio.gradle.build.insights.reporters.html import com.smplio.gradle.build.insights.modules.load.ISystemLoadReporter -import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo -import com.smplio.gradle.build.insights.modules.timing.models.Measured -import com.smplio.gradle.build.insights.modules.timing.models.TaskInfo -import com.smplio.gradle.build.insights.modules.timing.report.ExecutionTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.IExecutionTimeReporter +import com.smplio.gradle.build.insights.modules.timing.report.ConfigurationTimeReport +import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReporter +import com.smplio.gradle.build.insights.modules.timing.report.TaskExecutionTimeReport +import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReporter import org.gradle.api.Project import org.json.JSONArray import org.json.JSONObject @@ -18,24 +17,18 @@ import kotlin.io.path.absolutePathString class HTMLReporter( project: Project, -): IExecutionTimeReporter, ISystemLoadReporter { - private val baseReportFolder = project.layout.buildDirectory.get().dir("build-report").asFile - private val tasksFile = baseReportFolder.toPath().resolve("tasks.json").toFile() - private val systemLoadFile = baseReportFolder.toPath().resolve("systemLoad.json").toFile() - +): IConfigurationTimeReporter, ITaskExecutionTimeReporter, ISystemLoadReporter { private val uniqueReportFolder = project.layout.buildDirectory.get().dir("build-report").dir(UUID.randomUUID().toString()).asFile private val styleCssPath = uniqueReportFolder.toPath().resolve("style.css").absolutePathString() private val reportHtmlFile = uniqueReportFolder.toPath().resolve("index.html").toFile() - private var taskExecutionTimeline: List>? = null - private var configurationTimeline: List>? = null - - override fun reportExecutionTime(executionTimeReport: ExecutionTimeReport) { - taskExecutionTimeline = executionTimeReport.taskExecutionTimeline - configurationTimeline = executionTimeReport.configurationTimeline + private var configurationTimeJson: String? = null + private var executionTimeJson: String? = null + private var systemLoadJson: String? = null + override fun reportTaskExecutionTime(taskExecutionTimeReport: TaskExecutionTimeReport) { val tasks = JSONArray() - for (measuredTaskInfo in executionTimeReport.taskExecutionTimeline) { + for (measuredTaskInfo in taskExecutionTimeReport) { val task = measuredTaskInfo.measuredInstance tasks.put(JSONObject().apply { put("type", "task") @@ -46,36 +39,32 @@ class HTMLReporter( put("status_description", task.status.description) }) } - for (measuredConfigurationInfo in executionTimeReport.configurationTimeline) { + executionTimeJson = tasks.toString(4) + } + + override fun reportConfigurationTime(configurationTimeReport: ConfigurationTimeReport) { + val projects = JSONArray() + for (measuredConfigurationInfo in configurationTimeReport) { val configurationInfo = measuredConfigurationInfo.measuredInstance - tasks.put(JSONObject().apply { + projects.put(JSONObject().apply { put("type", "configuration") put("name", configurationInfo.projectName) put("start", measuredConfigurationInfo.startTime) put("end", measuredConfigurationInfo.endTime) }) } - - baseReportFolder.mkdirs() - tasksFile.bufferedWriter(Charsets.UTF_8).use { - it.write(tasks.toString(4)) - } + configurationTimeJson = projects.toString(4) } override fun reportSystemLoad(measurements: ConcurrentLinkedQueue>>>) { - val systemLoadJson = JSONArray().also { + systemLoadJson = JSONArray().also { measurements.forEach { measurementSet -> it.put(JSONObject().also { it.put("timestamp", measurementSet.first) for (measurement in measurementSet.second) { it.put(measurement.first, measurement.second) } })} - } - - baseReportFolder.mkdirs() - systemLoadFile.bufferedWriter(Charsets.UTF_8).use { - it.write(systemLoadJson.toString(4)) - } + }.toString(4) } override fun submitReport() { @@ -86,8 +75,9 @@ class HTMLReporter( val buildChartsJsText = javaClass.getResourceAsStream("/build_charts.js")?.reader()?.use { it.readText() } val html = javaClass.getResourceAsStream("/index.html")?.reader()?.readText()?.format( - tasksFile.reader().use { it.readText() }, - systemLoadFile.reader().use { it.readText() }, + configurationTimeJson ?: "", + executionTimeJson ?: "", + systemLoadJson ?: "", scriptJsText, chartJsText, buildChartsJsText, @@ -103,8 +93,9 @@ class HTMLReporter( StandardCopyOption.REPLACE_EXISTING, ) - tasksFile.delete() - systemLoadFile.delete() + configurationTimeJson = null + executionTimeJson = null + systemLoadJson = null println("Build insights report is available in ${reportHtmlFile.absolutePath}") } diff --git a/src/main/resources/index.html b/src/main/resources/index.html index 3a44a8e..062880a 100644 --- a/src/main/resources/index.html +++ b/src/main/resources/index.html @@ -31,6 +31,7 @@ diff --git a/src/main/resources/script.js b/src/main/resources/script.js index d5c9407..c6144b1 100644 --- a/src/main/resources/script.js +++ b/src/main/resources/script.js @@ -1,6 +1,6 @@ let timeScale = 1; -let timeWindowStart = Math.min(...tasks.map(value => value.start)); -let timeWindowEnd = Math.max(...tasks.map(value => value.end)); +let timeWindowStart = Math.min(...tasks.map(value => value.start), ...configurations.map(value => value.start)); +let timeWindowEnd = Math.max(...tasks.map(value => value.end), ...configurations.map(value => value.end)); const durationMs = timeWindowEnd - timeWindowStart; // Draggable time window and handles @@ -32,71 +32,82 @@ function formatTime(timestamp) { return dtFormat.format(new Date(timestamp)); } +// Render configurations based on the time window +function createConfigurations() { + configurations.forEach(project => { + createTimelineBlock(project) + }) +} + // Render tasks based on the time window function createTasks() { tasks.forEach(task => { - let taskEl; - if (task.name in taskToDivMap) { - taskEl = taskToDivMap[task.name]; - } else { - taskEl = document.createElement("div"); - taskEl.className = "timeline-item"; - taskEl.classList.add(task.type); - if (task.type === "task") { - let taskClass = ""; - switch(task.status) { - case "SKIPPED": - if (task.status_description === "FROM-CACHE") { - taskClass = "cached-task"; - } else { - taskClass = "skipped-task"; - } - break; - case "FAILED": - taskClass = "failed-task"; - break; - default: - taskClass = "successful-task"; - break; - } - taskEl.classList.add(taskClass); + createTimelineBlock(task) + }) +} + +function createTimelineBlock(task) { + let taskEl; + if (task.name in taskToDivMap) { + taskEl = taskToDivMap[task.name]; + } else { + taskEl = document.createElement("div"); + taskEl.className = "timeline-item"; + taskEl.classList.add(task.type); + if (task.type === "task") { + let taskClass = ""; + switch(task.status) { + case "SKIPPED": + if (task.status_description === "FROM-CACHE") { + taskClass = "cached-task"; + } else { + taskClass = "skipped-task"; + } + break; + case "FAILED": + taskClass = "failed-task"; + break; + default: + taskClass = "successful-task"; + break; } - taskEl.classList.add("tooltip"); - taskEl.style.top = `${task.rowIdx * 25}px`; + taskEl.classList.add(taskClass); + } + taskEl.classList.add("tooltip"); + taskEl.style.top = `${task.rowIdx * 25}px`; - taskNameEl = document.createElement("span"); - taskNameEl.textContent = task.name; - taskEl.appendChild(taskNameEl) + taskNameEl = document.createElement("span"); + taskNameEl.textContent = task.name; + taskEl.appendChild(taskNameEl) - tooltipEl = document.createElement("div"); - tooltipEl.className = "tooltiptext"; + tooltipEl = document.createElement("div"); + tooltipEl.className = "tooltiptext"; - let detailedStatus = task.status_description; - if (task.status === "SUCCESS") { - detailedStatus = ""; - } - let statusBadge = `Status: ${task.status}
${detailedStatus}

`; - if (task.type !== "task") { - statusBadge = ""; - } + let detailedStatus = task.status_description; + if (task.status === "SUCCESS") { + detailedStatus = ""; + } + let statusBadge = `Status: ${task.status}
${detailedStatus}

`; + if (task.type !== "task") { + statusBadge = ""; + } - tooltipEl.innerHTML = `${task.name}\n
${statusBadge}Started: ${formatTime(task.start)}\nFinished: ${formatTime(task.end)}`; + tooltipEl.innerHTML = `${task.name}\n
${statusBadge}Started: ${formatTime(task.start)}\nFinished: ${formatTime(task.end)}`; - taskEl.appendChild(tooltipEl); + taskEl.appendChild(tooltipEl); - taskToDivMap[task.name] = taskEl; - taskTimeline.appendChild(taskEl); - } + taskToDivMap[task.name] = taskEl; + taskTimeline.appendChild(taskEl); + } - taskEl.style.left = `${(task.start - timeWindowStart) * timeScale}px`; - taskEl.style.width = `${(task.end - task.start) * timeScale}px`; + taskEl.style.left = `${(task.start - timeWindowStart) * timeScale}px`; + taskEl.style.width = `${(task.end - task.start) * timeScale}px`; - if (task.end < timeWindowStart || task.start > timeWindowEnd) { - taskEl.style.visibility = "hidden"; - } else { - taskEl.style.visibility = "visible"; - } - }) + if (task.end < timeWindowStart || task.start > timeWindowEnd) { + taskEl.style.visibility = "hidden"; + } else { + taskEl.style.visibility = "visible"; + } } // Calculate overlapping task rows @@ -244,6 +255,7 @@ function updateTimeWindow() { // Render tasks updateRuler(); updateCharts(); + createConfigurations(); createTasks(); } @@ -313,5 +325,6 @@ window.addEventListener ("resize", e => { }); // Initial render +configurations = calculateRows(configurations); tasks = calculateRows(tasks); updateTimeWindow(); From 99b90d0a9b0b253d10a4f2fc1c161c4a75cbe07e Mon Sep 17 00:00:00 2001 From: Dmytro Rodionov Date: Sun, 25 May 2025 10:58:06 +0200 Subject: [PATCH 3/3] Refactor codebase --- .../build/insights/GradleInsightsPlugin.kt | 4 +- .../modules/load/ISystemLoadReportProvider.kt | 7 -- .../modules/load/ISystemLoadReporter.kt | 7 -- .../modules/load/LocalCacheReporter.kt | 1 + .../modules/load/SystemLoadService.kt | 1 + .../ExecutionTimeMeasurementConfiguration.kt | 8 +- .../timing/ExecutionTimeMeasurementModule.kt | 2 +- .../report/ConsoleExecutionTimeReporter.kt | 4 +- .../{ExecutionReport.kt => ExecutionStats.kt} | 6 +- .../IConfigurationTimeReportProvider.kt | 7 -- .../report/IConfigurationTimeReporter.kt | 5 -- .../ITaskExecutionTimeReportProvider.kt | 7 -- .../report/ITaskExecutionTimeReporter.kt | 7 -- .../ConfigurationTimeReportProvider.kt | 2 +- ...TaskTaskExecutionTimeMeasurementService.kt | 4 +- .../report/CompositeReportBuildService.kt | 84 +++++++++++++++++++ .../{reporters => report}/IReportProvider.kt | 2 +- .../{reporters => report}/IReporter.kt | 2 +- .../execution/IExecutionStatsProvider.kt | 8 ++ .../execution/IExecutionStatsReceiver.kt | 7 ++ .../impl}/html/HTMLReporter.kt | 10 +-- .../report/load/ISystemLoadReportProvider.kt | 8 ++ .../report/load/ISystemLoadReportReceiver.kt | 8 ++ .../IConfigurationTimeReportProvider.kt | 8 ++ .../IConfigurationTimeReportReceiver.kt | 7 ++ .../ITaskExecutionTimeReportProvider.kt | 8 ++ .../ITaskExecutionTimeReportReceiver.kt | 8 ++ .../reporters/CompositeReportBuildService.kt | 78 ----------------- 28 files changed, 171 insertions(+), 139 deletions(-) delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt rename src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/{ExecutionReport.kt => ExecutionStats.kt} (87%) delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/CompositeReportBuildService.kt rename src/main/kotlin/com/smplio/gradle/build/insights/{reporters => report}/IReportProvider.kt (57%) rename src/main/kotlin/com/smplio/gradle/build/insights/{reporters => report}/IReporter.kt (63%) create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsReceiver.kt rename src/main/kotlin/com/smplio/gradle/build/insights/{reporters => report/impl}/html/HTMLReporter.kt (90%) create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportReceiver.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportReceiver.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportProvider.kt create mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportReceiver.kt delete mode 100644 src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt b/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt index 2625bdd..b536cb8 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/GradleInsightsPlugin.kt @@ -3,8 +3,8 @@ package com.smplio.gradle.build.insights import com.smplio.gradle.build.insights.modules.graph.GraphBuilder import com.smplio.gradle.build.insights.modules.load.SystemLoadModule import com.smplio.gradle.build.insights.modules.timing.ExecutionTimeMeasurementModule -import com.smplio.gradle.build.insights.reporters.CompositeReportBuildService -import com.smplio.gradle.build.insights.reporters.html.HTMLReporter +import com.smplio.gradle.build.insights.report.CompositeReportBuildService +import com.smplio.gradle.build.insights.report.impl.html.HTMLReporter import org.gradle.api.Plugin import org.gradle.api.Project import org.gradle.api.plugins.ReportingBasePlugin diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt deleted file mode 100644 index ac4cb2c..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReportProvider.kt +++ /dev/null @@ -1,7 +0,0 @@ -package com.smplio.gradle.build.insights.modules.load - -import com.smplio.gradle.build.insights.reporters.IReportProvider - -interface ISystemLoadReportProvider: IReportProvider { - fun provideSystemLoadReport(): SystemLoadReport? -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt deleted file mode 100644 index 644287c..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/ISystemLoadReporter.kt +++ /dev/null @@ -1,7 +0,0 @@ -package com.smplio.gradle.build.insights.modules.load - -import com.smplio.gradle.build.insights.reporters.IReporter - -interface ISystemLoadReporter: IReporter { - fun reportSystemLoad(measurements: SystemLoadReport) -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt index 21aa464..97cc201 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/LocalCacheReporter.kt @@ -2,6 +2,7 @@ package com.smplio.gradle.build.insights.modules.load import com.codahale.metrics.* import com.codahale.metrics.Timer +import com.smplio.gradle.build.insights.report.load.ISystemLoadReportProvider import java.util.SortedMap import java.util.concurrent.ConcurrentLinkedQueue import java.util.concurrent.TimeUnit diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt index 0dc5084..3d85c85 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/load/SystemLoadService.kt @@ -1,6 +1,7 @@ package com.smplio.gradle.build.insights.modules.load import com.codahale.metrics.* +import com.smplio.gradle.build.insights.report.load.ISystemLoadReportProvider import org.gradle.api.services.BuildService import org.gradle.api.services.BuildServiceParameters import org.gradle.tooling.events.FinishEvent diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt index 9754a8e..0d10f8d 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementConfiguration.kt @@ -1,7 +1,7 @@ package com.smplio.gradle.build.insights.modules.timing import com.smplio.gradle.build.insights.modules.timing.report.ConsoleExecutionTimeReporter -import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReporter +import com.smplio.gradle.build.insights.report.timing.ITaskExecutionTimeReportReceiver import org.gradle.api.model.ObjectFactory import org.gradle.api.provider.Property import javax.inject.Inject @@ -9,9 +9,9 @@ import javax.inject.Inject abstract class ExecutionTimeMeasurementConfiguration @Inject constructor(objects: ObjectFactory) { val enabled: Property = objects.property(Boolean::class.java).convention(true) - val executionTimeReporter: Property = (objects.property( - ITaskExecutionTimeReporter::class.java - ) as Property).convention( + val executionTimeReporter: Property = (objects.property( + ITaskExecutionTimeReportReceiver::class.java + ) as Property).convention( ConsoleExecutionTimeReporter() ) } \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt index 614b507..0aae5df 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/ExecutionTimeMeasurementModule.kt @@ -1,6 +1,6 @@ package com.smplio.gradle.build.insights.modules.timing -import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReportProvider +import com.smplio.gradle.build.insights.report.timing.IConfigurationTimeReportProvider import org.gradle.api.Project import org.gradle.build.event.BuildEventsListenerRegistry import com.smplio.gradle.build.insights.modules.timing.report_providers.ConfigurationTimeReportProvider diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt index af3ff69..878edaf 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ConsoleExecutionTimeReporter.kt @@ -1,7 +1,9 @@ package com.smplio.gradle.build.insights.modules.timing.report +import com.smplio.gradle.build.insights.report.timing.IConfigurationTimeReportReceiver +import com.smplio.gradle.build.insights.report.timing.ITaskExecutionTimeReportReceiver import java.time.Duration -class ConsoleExecutionTimeReporter: IConfigurationTimeReporter, ITaskExecutionTimeReporter { +class ConsoleExecutionTimeReporter: IConfigurationTimeReportReceiver, ITaskExecutionTimeReportReceiver { private var configurationTimeReport: ConfigurationTimeReport? = null private var taskExecutionTimeReport: TaskExecutionTimeReport? = null diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionReport.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionStats.kt similarity index 87% rename from src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionReport.kt rename to src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionStats.kt index 71c391d..04ce41c 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionReport.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ExecutionStats.kt @@ -9,11 +9,11 @@ import java.net.InetAddress typealias ConfigurationTimeReport = List> typealias TaskExecutionTimeReport = List> -data class ExecutionReport( +data class ExecutionStats( val buildHostInfo: BuildHostInfo, val buildInfo: Measured, - val configurationTimeline: ConfigurationTimeReport, - val taskExecutionTimeline: TaskExecutionTimeReport, + val configurationTimeline: ConfigurationTimeReport?, + val taskExecutionTimeline: TaskExecutionTimeReport?, ) data class BuildHostInfo( diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt deleted file mode 100644 index 95edef2..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReportProvider.kt +++ /dev/null @@ -1,7 +0,0 @@ -package com.smplio.gradle.build.insights.modules.timing.report - -import com.smplio.gradle.build.insights.reporters.IReportProvider - -interface IConfigurationTimeReportProvider: IReportProvider { - fun provideConfigurationTimeReport(): ConfigurationTimeReport? -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt deleted file mode 100644 index 3c9db23..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/IConfigurationTimeReporter.kt +++ /dev/null @@ -1,5 +0,0 @@ -package com.smplio.gradle.build.insights.modules.timing.report - -interface IConfigurationTimeReporter { - fun reportConfigurationTime(configurationTimeReport: ConfigurationTimeReport) -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt deleted file mode 100644 index 90eee33..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReportProvider.kt +++ /dev/null @@ -1,7 +0,0 @@ -package com.smplio.gradle.build.insights.modules.timing.report - -import com.smplio.gradle.build.insights.reporters.IReportProvider - -interface ITaskExecutionTimeReportProvider: IReportProvider { - fun provideTaskExecutionTimeReport(): TaskExecutionTimeReport? -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt deleted file mode 100644 index 67f24f2..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report/ITaskExecutionTimeReporter.kt +++ /dev/null @@ -1,7 +0,0 @@ -package com.smplio.gradle.build.insights.modules.timing.report - -import com.smplio.gradle.build.insights.reporters.IReporter - -interface ITaskExecutionTimeReporter: IReporter { - fun reportTaskExecutionTime(taskExecutionTimeReport: TaskExecutionTimeReport) -} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt index aa2bc4d..a935c57 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/ConfigurationTimeReportProvider.kt @@ -3,7 +3,7 @@ package com.smplio.gradle.build.insights.modules.timing.report_providers import com.smplio.gradle.build.insights.modules.timing.models.ConfigurationInfo import com.smplio.gradle.build.insights.modules.timing.models.Measured import com.smplio.gradle.build.insights.modules.timing.report.ConfigurationTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReportProvider +import com.smplio.gradle.build.insights.report.timing.IConfigurationTimeReportProvider import org.gradle.api.Project import java.util.concurrent.ConcurrentHashMap diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt index cef60ee..ded1bc3 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/modules/timing/report_providers/TaskTaskExecutionTimeMeasurementService.kt @@ -3,8 +3,8 @@ package com.smplio.gradle.build.insights.modules.timing.report_providers import com.smplio.gradle.build.insights.modules.timing.models.Measured import com.smplio.gradle.build.insights.modules.timing.models.TaskInfo import com.smplio.gradle.build.insights.modules.timing.report.TaskExecutionTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReportProvider -import com.smplio.gradle.build.insights.reporters.IReportProvider +import com.smplio.gradle.build.insights.report.timing.ITaskExecutionTimeReportProvider +import com.smplio.gradle.build.insights.report.IReportProvider import org.gradle.api.provider.Property import org.gradle.api.services.BuildService import org.gradle.api.services.BuildServiceParameters diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/CompositeReportBuildService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/CompositeReportBuildService.kt new file mode 100644 index 0000000..43b00ba --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/CompositeReportBuildService.kt @@ -0,0 +1,84 @@ +package com.smplio.gradle.build.insights.report + +import com.smplio.gradle.build.insights.report.load.ISystemLoadReportReceiver +import com.smplio.gradle.build.insights.modules.load.SystemLoadService +import com.smplio.gradle.build.insights.modules.timing.models.BuildInfo +import com.smplio.gradle.build.insights.modules.timing.models.Measured +import com.smplio.gradle.build.insights.modules.timing.models.TaskInfo +import com.smplio.gradle.build.insights.modules.timing.report.BuildHostInfo +import com.smplio.gradle.build.insights.modules.timing.report.ExecutionStats +import com.smplio.gradle.build.insights.report.timing.IConfigurationTimeReportProvider +import com.smplio.gradle.build.insights.report.timing.IConfigurationTimeReportReceiver +import com.smplio.gradle.build.insights.report.timing.ITaskExecutionTimeReportReceiver +import com.smplio.gradle.build.insights.modules.timing.report_providers.TaskTaskExecutionTimeMeasurementService +import com.smplio.gradle.build.insights.report.execution.IExecutionStatsReceiver +import org.gradle.api.provider.ListProperty +import org.gradle.api.provider.Property +import org.gradle.api.services.BuildService +import org.gradle.api.services.BuildServiceParameters +import org.gradle.tooling.events.FinishEvent +import org.gradle.tooling.events.OperationCompletionListener +import kotlin.math.max +import kotlin.math.min + +abstract class CompositeReportBuildService : BuildService, + OperationCompletionListener, + AutoCloseable +{ + interface Parameters: BuildServiceParameters { + val reporters: ListProperty + val configurationTimeReportProvider: Property + val systemLoadReportService: Property + val executionTimeReportService: Property + } + + override fun close() { + val reporters = parameters.reporters.orNull ?: return + val systemLoadService = parameters.systemLoadReportService.orNull ?: return + val executionTimeReportService = parameters.executionTimeReportService.orNull ?: return + val configurationTimeReportProvider = parameters.configurationTimeReportProvider.orNull ?: return + + reporters.filterIsInstance().forEach { reporter -> + systemLoadService.provideSystemLoadReport()?.let { + reporter.reportSystemLoad(it) + } + } + + reporters.filterIsInstance().forEach { reporter -> + executionTimeReportService.provideTaskExecutionTimeReport()?.let { + reporter.reportTaskExecutionTime(it) + } + } + + reporters.filterIsInstance().forEach { reporter -> + configurationTimeReportProvider.provideConfigurationTimeReport()?.let { + reporter.reportConfigurationTime(it) + } + } + + reporters.filterIsInstance().forEach { reporter -> + val configurationTimeline = configurationTimeReportProvider.provideConfigurationTimeReport() + val taskExecutionTimeline = executionTimeReportService.provideTaskExecutionTimeReport() + reporter.reportExecutionStats(ExecutionStats( + buildHostInfo = BuildHostInfo(), + buildInfo = Measured( + measuredInstance = BuildInfo( + status = BuildInfo.ExecutionStatus.Success().takeIf { + !taskExecutionTimeline.isNullOrEmpty() && taskExecutionTimeline.none { it.measuredInstance.status is TaskInfo.ExecutionStatus.Failed } + } ?: BuildInfo.ExecutionStatus.Failed() + ), + startTime = min(configurationTimeline?.minOfOrNull { it.startTime } ?: 0L, taskExecutionTimeline?.minOfOrNull { it.startTime } ?: 0L), + endTime = max(configurationTimeline?.maxOfOrNull { it.endTime } ?: 0L, taskExecutionTimeline?.maxOfOrNull { it.endTime } ?: 0L), + ), + configurationTimeline = configurationTimeline, + taskExecutionTimeline = taskExecutionTimeline, + )) + } + + reporters.forEach { reporter -> + reporter.submitReport() + } + } + + override fun onFinish(event: FinishEvent?) {} +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/IReportProvider.kt similarity index 57% rename from src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt rename to src/main/kotlin/com/smplio/gradle/build/insights/report/IReportProvider.kt index 0e4dac7..95db679 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReportProvider.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/IReportProvider.kt @@ -1,4 +1,4 @@ -package com.smplio.gradle.build.insights.reporters +package com.smplio.gradle.build.insights.report import java.io.Serializable diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/IReporter.kt similarity index 63% rename from src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt rename to src/main/kotlin/com/smplio/gradle/build/insights/report/IReporter.kt index 6240899..d4cca61 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/IReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/IReporter.kt @@ -1,4 +1,4 @@ -package com.smplio.gradle.build.insights.reporters +package com.smplio.gradle.build.insights.report import java.io.Serializable diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsProvider.kt new file mode 100644 index 0000000..c933160 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsProvider.kt @@ -0,0 +1,8 @@ +package com.smplio.gradle.build.insights.report.execution + +import com.smplio.gradle.build.insights.modules.timing.report.ExecutionStats +import com.smplio.gradle.build.insights.report.IReportProvider + +interface IExecutionStatsProvider: IReportProvider { + fun provideExecutionReport(): ExecutionStats +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsReceiver.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsReceiver.kt new file mode 100644 index 0000000..84d84e8 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/execution/IExecutionStatsReceiver.kt @@ -0,0 +1,7 @@ +package com.smplio.gradle.build.insights.report.execution + +import com.smplio.gradle.build.insights.modules.timing.report.ExecutionStats + +interface IExecutionStatsReceiver { + fun reportExecutionStats(stats: ExecutionStats) +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/impl/html/HTMLReporter.kt similarity index 90% rename from src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt rename to src/main/kotlin/com/smplio/gradle/build/insights/report/impl/html/HTMLReporter.kt index b077f20..1215b1f 100644 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/html/HTMLReporter.kt +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/impl/html/HTMLReporter.kt @@ -1,10 +1,10 @@ -package com.smplio.gradle.build.insights.reporters.html +package com.smplio.gradle.build.insights.report.impl.html -import com.smplio.gradle.build.insights.modules.load.ISystemLoadReporter +import com.smplio.gradle.build.insights.report.load.ISystemLoadReportReceiver import com.smplio.gradle.build.insights.modules.timing.report.ConfigurationTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReporter +import com.smplio.gradle.build.insights.report.timing.IConfigurationTimeReportReceiver import com.smplio.gradle.build.insights.modules.timing.report.TaskExecutionTimeReport -import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReporter +import com.smplio.gradle.build.insights.report.timing.ITaskExecutionTimeReportReceiver import org.gradle.api.Project import org.json.JSONArray import org.json.JSONObject @@ -17,7 +17,7 @@ import kotlin.io.path.absolutePathString class HTMLReporter( project: Project, -): IConfigurationTimeReporter, ITaskExecutionTimeReporter, ISystemLoadReporter { +): IConfigurationTimeReportReceiver, ITaskExecutionTimeReportReceiver, ISystemLoadReportReceiver { private val uniqueReportFolder = project.layout.buildDirectory.get().dir("build-report").dir(UUID.randomUUID().toString()).asFile private val styleCssPath = uniqueReportFolder.toPath().resolve("style.css").absolutePathString() private val reportHtmlFile = uniqueReportFolder.toPath().resolve("index.html").toFile() diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportProvider.kt new file mode 100644 index 0000000..91f94cf --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportProvider.kt @@ -0,0 +1,8 @@ +package com.smplio.gradle.build.insights.report.load + +import com.smplio.gradle.build.insights.modules.load.SystemLoadReport +import com.smplio.gradle.build.insights.report.IReportProvider + +interface ISystemLoadReportProvider: IReportProvider { + fun provideSystemLoadReport(): SystemLoadReport? +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportReceiver.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportReceiver.kt new file mode 100644 index 0000000..1b6d309 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/load/ISystemLoadReportReceiver.kt @@ -0,0 +1,8 @@ +package com.smplio.gradle.build.insights.report.load + +import com.smplio.gradle.build.insights.modules.load.SystemLoadReport +import com.smplio.gradle.build.insights.report.IReporter + +interface ISystemLoadReportReceiver: IReporter { + fun reportSystemLoad(measurements: SystemLoadReport) +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportProvider.kt new file mode 100644 index 0000000..5d0bb47 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportProvider.kt @@ -0,0 +1,8 @@ +package com.smplio.gradle.build.insights.report.timing + +import com.smplio.gradle.build.insights.modules.timing.report.ConfigurationTimeReport +import com.smplio.gradle.build.insights.report.IReportProvider + +interface IConfigurationTimeReportProvider: IReportProvider { + fun provideConfigurationTimeReport(): ConfigurationTimeReport? +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportReceiver.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportReceiver.kt new file mode 100644 index 0000000..a0fbcda --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/IConfigurationTimeReportReceiver.kt @@ -0,0 +1,7 @@ +package com.smplio.gradle.build.insights.report.timing + +import com.smplio.gradle.build.insights.modules.timing.report.ConfigurationTimeReport + +interface IConfigurationTimeReportReceiver { + fun reportConfigurationTime(configurationTimeReport: ConfigurationTimeReport) +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportProvider.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportProvider.kt new file mode 100644 index 0000000..1dc32c8 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportProvider.kt @@ -0,0 +1,8 @@ +package com.smplio.gradle.build.insights.report.timing + +import com.smplio.gradle.build.insights.modules.timing.report.TaskExecutionTimeReport +import com.smplio.gradle.build.insights.report.IReportProvider + +interface ITaskExecutionTimeReportProvider: IReportProvider { + fun provideTaskExecutionTimeReport(): TaskExecutionTimeReport? +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportReceiver.kt b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportReceiver.kt new file mode 100644 index 0000000..3ca2490 --- /dev/null +++ b/src/main/kotlin/com/smplio/gradle/build/insights/report/timing/ITaskExecutionTimeReportReceiver.kt @@ -0,0 +1,8 @@ +package com.smplio.gradle.build.insights.report.timing + +import com.smplio.gradle.build.insights.modules.timing.report.TaskExecutionTimeReport +import com.smplio.gradle.build.insights.report.IReporter + +interface ITaskExecutionTimeReportReceiver: IReporter { + fun reportTaskExecutionTime(taskExecutionTimeReport: TaskExecutionTimeReport) +} \ No newline at end of file diff --git a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt b/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt deleted file mode 100644 index 2f2ec8e..0000000 --- a/src/main/kotlin/com/smplio/gradle/build/insights/reporters/CompositeReportBuildService.kt +++ /dev/null @@ -1,78 +0,0 @@ -package com.smplio.gradle.build.insights.reporters - -import com.smplio.gradle.build.insights.modules.load.ISystemLoadReporter -import com.smplio.gradle.build.insights.modules.load.SystemLoadService -import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReportProvider -import com.smplio.gradle.build.insights.modules.timing.report.IConfigurationTimeReporter -import com.smplio.gradle.build.insights.modules.timing.report.ITaskExecutionTimeReporter -import com.smplio.gradle.build.insights.modules.timing.report_providers.TaskTaskExecutionTimeMeasurementService -import org.gradle.api.provider.ListProperty -import org.gradle.api.provider.Property -import org.gradle.api.services.BuildService -import org.gradle.api.services.BuildServiceParameters -import org.gradle.tooling.events.FinishEvent -import org.gradle.tooling.events.OperationCompletionListener - -abstract class CompositeReportBuildService : BuildService, - OperationCompletionListener, - AutoCloseable -{ - interface Parameters: BuildServiceParameters { - val reporters: ListProperty - val configurationTimeReportProvider: Property - val systemLoadReportService: Property - val executionTimeReportService: Property - } - - override fun close() { - val reporters = parameters.reporters.orNull ?: return - val systemLoadService = parameters.systemLoadReportService.orNull ?: return - val executionTimeReportService = parameters.executionTimeReportService.orNull ?: return - val configurationTimeReportProvider = parameters.configurationTimeReportProvider.orNull ?: return - - reporters.filterIsInstance().forEach { reporter -> - systemLoadService.provideSystemLoadReport()?.let { - reporter.reportSystemLoad(it) - } - } - - reporters.filterIsInstance().forEach { reporter -> - executionTimeReportService.provideTaskExecutionTimeReport()?.let { - reporter.reportTaskExecutionTime(it) - } - } - - reporters.filterIsInstance().forEach { reporter -> - configurationTimeReportProvider.provideConfigurationTimeReport()?.let { - reporter.reportConfigurationTime(it) - } - } - - // val reportProviders = parameters.reportProviders.orNull ?: return - // - // reportProviders.forEach { reportProvider -> - // when (reportProvider) { - // is ISystemLoadReportProvider -> { - // reporters.filterIsInstance().forEach { reporter -> - // reportProvider.provideSystemLoadReport()?.let { - // reporter.reportSystemLoad(it) - // } - // } - // } - // is IExecutionTimeReportProvider -> { - // reporters.filterIsInstance().forEach { reporter -> - // reportProvider.provideExecutionTimeReport()?.let { - // reporter.reportExecutionTime(it) - // } - // } - // } - // } - // } - - reporters.forEach { reporter -> - reporter.submitReport() - } - } - - override fun onFinish(event: FinishEvent?) {} -} \ No newline at end of file