diff --git a/src/main/kotlin/org/jetbrains/research/testspark/appstarter/TestSparkStarter.kt b/src/main/kotlin/org/jetbrains/research/testspark/appstarter/TestSparkStarter.kt index af2bdef41..ff8580ade 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/appstarter/TestSparkStarter.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/appstarter/TestSparkStarter.kt @@ -206,6 +206,7 @@ class TestSparkStarter : ApplicationStarter { projectContext, projectSDKPath, testCompiler, + settingsState.junitVersion, ) } } else { @@ -253,6 +254,7 @@ class TestSparkStarter : ApplicationStarter { projectContext: ProjectContext, projectSDKPath: Path, testCompiler: TestCompiler, + junitVersion: JUnitVersion, ) { val targetDirectory = "$out${File.separator}${packageList.joinToString(File.separator)}" println("Run tests in $targetDirectory") @@ -272,6 +274,7 @@ class TestSparkStarter : ApplicationStarter { out, projectContext, testCompiler, + junitVersion, ) // Saving exception (if exists) thrown during the test execution saveException(testcaseName, targetDirectory, testExecutionError) diff --git a/src/main/kotlin/org/jetbrains/research/testspark/display/TestSparkDisplayManager.kt b/src/main/kotlin/org/jetbrains/research/testspark/display/TestSparkDisplayManager.kt index 710e98f79..56e368cea 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/display/TestSparkDisplayManager.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/display/TestSparkDisplayManager.kt @@ -13,6 +13,7 @@ import org.jetbrains.research.testspark.core.test.SupportedLanguage import org.jetbrains.research.testspark.data.UIContext import org.jetbrains.research.testspark.display.coverage.CoverageVisualisationTabBuilder import org.jetbrains.research.testspark.display.generatedTests.GeneratedTestsTabBuilder +import org.jetbrains.research.testspark.tools.GenerationTool import org.jetbrains.research.testspark.tools.TestsExecutionResultManager import java.awt.Component import javax.swing.JOptionPane @@ -41,14 +42,30 @@ class TestSparkDisplayManager { /** * Fill the panel with the generated test cases. */ - fun display(report: Report, editor: Editor, uiContext: UIContext, language: SupportedLanguage, project: Project, testsExecutionResultManager: TestsExecutionResultManager) { + fun display( + report: Report, + editor: Editor, + uiContext: UIContext, + language: SupportedLanguage, + project: Project, + testsExecutionResultManager: TestsExecutionResultManager, + generationTool: GenerationTool, + ) { this.toolWindow = ToolWindowManager.getInstance(project).getToolWindow("TestSpark") this.contentManager = toolWindow!!.contentManager this.editor = editor coverageVisualisationTabBuilder = CoverageVisualisationTabBuilder(project, editor) - generatedTestsTabBuilder = GeneratedTestsTabBuilder(project, report, editor, uiContext, coverageVisualisationTabBuilder!!, testsExecutionResultManager) + generatedTestsTabBuilder = GeneratedTestsTabBuilder( + project, + report, + editor, + uiContext, + coverageVisualisationTabBuilder!!, + testsExecutionResultManager, + generationTool, + ) generatedTestsTabBuilder!!.show(contentManager!!, language) coverageVisualisationTabBuilder!!.show(report, generatedTestsTabBuilder!!.generatedTestsTabData()) diff --git a/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/GeneratedTestsTabBuilder.kt b/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/GeneratedTestsTabBuilder.kt index bdde60d9b..2f2e07a21 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/GeneratedTestsTabBuilder.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/GeneratedTestsTabBuilder.kt @@ -15,6 +15,7 @@ import org.jetbrains.research.testspark.display.utils.ReportUpdater import org.jetbrains.research.testspark.display.utils.java.JavaDisplayUtils import org.jetbrains.research.testspark.display.utils.kotlin.KotlinDisplayUtils import org.jetbrains.research.testspark.display.utils.template.DisplayUtils +import org.jetbrains.research.testspark.tools.GenerationTool import org.jetbrains.research.testspark.tools.TestsExecutionResultManager import java.awt.BorderLayout import java.awt.Dimension @@ -36,6 +37,7 @@ class GeneratedTestsTabBuilder( private val uiContext: UIContext, private val coverageVisualisationTabBuilder: CoverageVisualisationTabBuilder, private val testsExecutionResultManager: TestsExecutionResultManager, + private val generationTool: GenerationTool, ) { private val generatedTestsTabData: GeneratedTestsTabData = GeneratedTestsTabData() @@ -149,8 +151,17 @@ class GeneratedTestsTabBuilder( val testCasePanelBuilder = TestCasePanelBuilder( - project, language, testCase, editor, checkbox, uiContext, report, - coverageVisualisationTabBuilder, generatedTestsTabData, testsExecutionResultManager, + project, + language, + testCase, + editor, + checkbox, + uiContext, + report, + coverageVisualisationTabBuilder, + generatedTestsTabData, + testsExecutionResultManager, + generationTool, ) testCasePanel.add(testCasePanelBuilder.getUpperPanel(), BorderLayout.NORTH) testCasePanel.add(testCasePanelBuilder.getMiddlePanel(), BorderLayout.CENTER) @@ -238,7 +249,8 @@ class GeneratedTestsTabBuilder( generatedTestsTabData.contentManager?.removeContent(generatedTestsTabData.content!!, true) ToolWindowManager.getInstance(project).getToolWindow("TestSpark")?.hide() coverageVisualisationTabBuilder.closeToolWindowTab() - } catch (_: AlreadyDisposedException) {} // Make sure the process continues if the tool window is already closed + } catch (_: AlreadyDisposedException) { + } // Make sure the process continues if the tool window is already closed } /** diff --git a/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/TestCasePanelBuilder.kt b/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/TestCasePanelBuilder.kt index 09ad48f01..99c5221c7 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/TestCasePanelBuilder.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/display/generatedTests/TestCasePanelBuilder.kt @@ -22,6 +22,7 @@ import com.intellij.util.ui.JBUI import org.jetbrains.research.testspark.bundles.llm.LLMMessagesBundle import org.jetbrains.research.testspark.bundles.plugin.PluginLabelsBundle import org.jetbrains.research.testspark.bundles.plugin.PluginMessagesBundle +import org.jetbrains.research.testspark.core.data.JUnitVersion import org.jetbrains.research.testspark.core.data.Report import org.jetbrains.research.testspark.core.data.TestCase import org.jetbrains.research.testspark.core.generation.llm.getClassWithTestCaseName @@ -42,6 +43,7 @@ import org.jetbrains.research.testspark.helpers.LLMHelper import org.jetbrains.research.testspark.services.LLMSettingsService import org.jetbrains.research.testspark.settings.llm.LLMSettingsState import org.jetbrains.research.testspark.testmanager.TestAnalyzerFactory +import org.jetbrains.research.testspark.tools.GenerationTool import org.jetbrains.research.testspark.tools.TestProcessor import org.jetbrains.research.testspark.tools.TestsExecutionResultManager import org.jetbrains.research.testspark.tools.ToolUtils @@ -76,6 +78,7 @@ class TestCasePanelBuilder( private val coverageVisualisationTabBuilder: CoverageVisualisationTabBuilder, private val generatedTestsTabData: GeneratedTestsTabData, private val testsExecutionResultManager: TestsExecutionResultManager, + private val generationTool: GenerationTool, ) { private val llmSettingsState: LLMSettingsState get() = project.getService(LLMSettingsService::class.java).state @@ -551,10 +554,12 @@ class TestCasePanelBuilder( indicator.setText("Executing ${testCase.testName}") val fileName = TestAnalyzerFactory.create(language).getFileNameFromTestCaseCode(testCase.testCode) + val junitVersion = + if (generationTool.toolId == "EvoSuite") JUnitVersion.JUnit4 else llmSettingsState.junitVersion val testCompiler = TestCompilerFactory.create( project, - llmSettingsState.junitVersion, + junitVersion, language, ) @@ -569,6 +574,7 @@ class TestCasePanelBuilder( uiContext.projectContext, testCompiler, testsExecutionResultManager, + junitVersion, ) testCase.coveredLines = newTestCase.coveredLines @@ -707,7 +713,8 @@ class TestCasePanelBuilder( * Updates the current test case with the specified test name and test code. */ private fun updateTestCaseInformation() { - testCase.testName = TestAnalyzerFactory.create(language).extractFirstTestMethodName(testCase.testName, languageTextField.document.text) + testCase.testName = TestAnalyzerFactory.create(language) + .extractFirstTestMethodName(testCase.testName, languageTextField.document.text) testCase.testCode = languageTextField.document.text } diff --git a/src/main/kotlin/org/jetbrains/research/testspark/tools/GenerationTool.kt b/src/main/kotlin/org/jetbrains/research/testspark/tools/GenerationTool.kt new file mode 100644 index 000000000..38dcceb68 --- /dev/null +++ b/src/main/kotlin/org/jetbrains/research/testspark/tools/GenerationTool.kt @@ -0,0 +1,14 @@ +package org.jetbrains.research.testspark.tools + +/** + * Enum class representing strategy for test generation + */ +enum class GenerationTool(val toolId: String) { + EvoSuite("EvoSuite"), + LLM("LLM"), + ; + + companion object { + fun from(findValue: String): GenerationTool = entries.first { it.toolId == findValue } + } +} diff --git a/src/main/kotlin/org/jetbrains/research/testspark/tools/Pipeline.kt b/src/main/kotlin/org/jetbrains/research/testspark/tools/Pipeline.kt index 31499ec5f..c0aaa2f21 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/tools/Pipeline.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/tools/Pipeline.kt @@ -34,6 +34,7 @@ import java.util.UUID * @param caretOffset the offset of the caret position in the PSI file. * @param fileUrl the URL of the file being processed, if applicable. * @param packageName the package name of the file being processed. + * @param generationToolName the tool name chosen for generation */ class Pipeline( private val project: Project, @@ -44,9 +45,11 @@ class Pipeline( private val testGenerationController: TestGenerationController, private val testSparkDisplayManager: TestSparkDisplayManager, private val testsExecutionResultManager: TestsExecutionResultManager, + generationToolName: String, ) { val projectContext: ProjectContext = ProjectContext() val generatedTestsData = TestGenerationData() + val generationTool = GenerationTool.from(generationToolName) init { val cutPsiClass = psiHelper.getSurroundingClass(caretOffset) @@ -134,6 +137,7 @@ class Pipeline( psiHelper.language, project, testsExecutionResultManager, + generationTool, ) } } @@ -141,14 +145,15 @@ class Pipeline( private fun updateEditor(fileUrl: String) { val documentManager = FileDocumentManager.getInstance() // https://intellij-support.jetbrains.com/hc/en-us/community/posts/360004480599/comments/360000703299 - FileEditorManager.getInstance(project).selectedEditors.map { it as TextEditor }.map { it.editor }.map { - val currentFile = documentManager.getFile(it.document) - if (currentFile != null) { - if (currentFile.presentableUrl == fileUrl) { - editor = it + FileEditorManager.getInstance(project).selectedEditors.map { it as TextEditor }.map { it.editor } + .map { + val currentFile = documentManager.getFile(it.document) + if (currentFile != null) { + if (currentFile.presentableUrl == fileUrl) { + editor = it + } } } - } } }) } diff --git a/src/main/kotlin/org/jetbrains/research/testspark/tools/TestProcessor.kt b/src/main/kotlin/org/jetbrains/research/testspark/tools/TestProcessor.kt index 8b5de49db..b2bdb3bbd 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/tools/TestProcessor.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/tools/TestProcessor.kt @@ -7,15 +7,14 @@ import com.intellij.openapi.project.Project import com.intellij.openapi.roots.CompilerModuleExtension import com.intellij.openapi.roots.ModuleRootManager import com.intellij.openapi.roots.ProjectRootManager +import org.jetbrains.research.testspark.core.data.JUnitVersion import org.jetbrains.research.testspark.core.data.TestCase import org.jetbrains.research.testspark.core.test.TestCompiler import org.jetbrains.research.testspark.core.test.TestsPersistentStorage import org.jetbrains.research.testspark.core.utils.CommandLineRunner import org.jetbrains.research.testspark.core.utils.DataFilesUtil import org.jetbrains.research.testspark.data.ProjectContext -import org.jetbrains.research.testspark.services.LLMSettingsService import org.jetbrains.research.testspark.services.PluginSettingsService -import org.jetbrains.research.testspark.settings.llm.LLMSettingsState import java.io.File import java.nio.file.Path import kotlin.io.path.Path @@ -30,9 +29,6 @@ class TestProcessor( private val log = Logger.getInstance(this::class.java) - private val llmSettingsState: LLMSettingsState - get() = project.getService(LLMSettingsService::class.java).state - override fun saveGeneratedTest( packageString: String, code: String, @@ -75,6 +71,7 @@ class TestProcessor( resultPath: String, projectContext: ProjectContext, testCompiler: TestCompiler, + junitVersion: JUnitVersion, ): String { // find the proper javac val javaRunner = findJavaCompilerInDirectory(homeDirectory) @@ -88,8 +85,6 @@ class TestProcessor( var name = if (generatedTestPackage.isEmpty()) "" else "$generatedTestPackage." name += "$className#$testCaseName" - val junitVersion = llmSettingsState.junitVersion.version - // run the test method with jacoco agent log.info("[TestProcessor] Executing $name") val junitRunnerLibraryPath = LibraryPathsProvider.getJUnitRunnerLibraryPath() @@ -162,6 +157,7 @@ class TestProcessor( projectContext: ProjectContext, testCompiler: TestCompiler, testsExecutionResultManager: TestsExecutionResultManager, + junitVersion: JUnitVersion, ): TestCase { // get buildPath var buildPath: String = ProjectRootManager.getInstance(project).contentRoots.first().path @@ -194,6 +190,7 @@ class TestProcessor( resultPath, projectContext, testCompiler, + junitVersion, ) if (!File("$dataFileName.xml").exists()) { diff --git a/src/main/kotlin/org/jetbrains/research/testspark/tools/evosuite/EvoSuite.kt b/src/main/kotlin/org/jetbrains/research/testspark/tools/evosuite/EvoSuite.kt index b2b03cccd..7539e4d8a 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/tools/evosuite/EvoSuite.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/tools/evosuite/EvoSuite.kt @@ -184,6 +184,7 @@ class EvoSuite(override val name: String = "EvoSuite") : Tool { testGenerationController, testSparkDisplayManager, testsExecutionResultManager, + name, ) } } diff --git a/src/main/kotlin/org/jetbrains/research/testspark/tools/llm/Llm.kt b/src/main/kotlin/org/jetbrains/research/testspark/tools/llm/Llm.kt index 06c24e819..068f433ef 100644 --- a/src/main/kotlin/org/jetbrains/research/testspark/tools/llm/Llm.kt +++ b/src/main/kotlin/org/jetbrains/research/testspark/tools/llm/Llm.kt @@ -218,6 +218,7 @@ class Llm(override val name: String = "LLM") : Tool { testGenerationController, testSparkDisplayManager, testsExecutionResultManager, + name, ) val manager = LLMProcessManager(