From 594056f3d0754112d3601f224f98a27a4dcda5e8 Mon Sep 17 00:00:00 2001 From: Geoffrey Challen Date: Mon, 25 Oct 2021 11:42:19 -0500 Subject: [PATCH] Add empty main option to improve complexity estimates. --- build.gradle.kts | 2 +- containerrunner/build.gradle.kts | 2 +- ...nois.cs.cs125.jeed.containerrunner.version | 2 +- core/build.gradle.kts | 4 +-- core/src/main/kotlin/Snippet.kt | 15 +++++++-- .../edu.illinois.cs.cs125.jeed.core.version | 2 +- core/src/test/kotlin/TestKotlinComplexity.kt | 16 ++++++++++ core/src/test/kotlin/TestSnippet.kt | 32 +++++++++++++++++++ .../edu.illinois.cs.cs125.jeed.server.version | 2 +- 9 files changed, 67 insertions(+), 10 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index c5b22933..5fad1950 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -18,7 +18,7 @@ allprojects { } subprojects { group = "com.github.cs125-illinois.jeed" - version = "2021.10.2" + version = "2021.10.3" tasks.withType { useJUnitPlatform() enableAssertions = true diff --git a/containerrunner/build.gradle.kts b/containerrunner/build.gradle.kts index 3900ec91..0a454a5c 100644 --- a/containerrunner/build.gradle.kts +++ b/containerrunner/build.gradle.kts @@ -14,7 +14,7 @@ dependencies { implementation("ch.qos.logback:logback-classic:1.2.6") implementation("io.github.microutils:kotlin-logging:2.0.11") implementation("com.github.ajalt:clikt:2.8.0") - implementation("io.github.classgraph:classgraph:4.8.126") + implementation("io.github.classgraph:classgraph:4.8.128") } application { @Suppress("DEPRECATION") diff --git a/containerrunner/src/main/resources/edu.illinois.cs.cs125.jeed.containerrunner.version b/containerrunner/src/main/resources/edu.illinois.cs.cs125.jeed.containerrunner.version index f07555f5..a3c570b0 100644 --- a/containerrunner/src/main/resources/edu.illinois.cs.cs125.jeed.containerrunner.version +++ b/containerrunner/src/main/resources/edu.illinois.cs.cs125.jeed.containerrunner.version @@ -1 +1 @@ -version=2021.10.2 \ No newline at end of file +version=2021.10.3 \ No newline at end of file diff --git a/core/build.gradle.kts b/core/build.gradle.kts index 800ffe44..68f1b522 100644 --- a/core/build.gradle.kts +++ b/core/build.gradle.kts @@ -30,10 +30,10 @@ dependencies { implementation("org.slf4j:slf4j-api:1.7.32") implementation("ch.qos.logback:logback-classic:1.2.6") implementation("io.github.microutils:kotlin-logging:2.0.11") - implementation("io.github.classgraph:classgraph:4.8.126") + implementation("io.github.classgraph:classgraph:4.8.128") implementation("net.java.dev.jna:jna:5.9.0") implementation("io.github.java-diff-utils:java-diff-utils:4.11") - implementation("com.google.googlejavaformat:google-java-format:1.11.0") + implementation("com.google.googlejavaformat:google-java-format:1.12.0") implementation("net.sf.extjwnl:extjwnl:2.0.3") implementation("net.sf.extjwnl:extjwnl-data-wn31:1.2") diff --git a/core/src/main/kotlin/Snippet.kt b/core/src/main/kotlin/Snippet.kt index 6fb4eaa6..1c16cad7 100644 --- a/core/src/main/kotlin/Snippet.kt +++ b/core/src/main/kotlin/Snippet.kt @@ -14,6 +14,7 @@ import org.antlr.v4.runtime.CharStreams import org.antlr.v4.runtime.CommonTokenStream import org.antlr.v4.runtime.RecognitionException import org.antlr.v4.runtime.Recognizer +import org.jetbrains.kotlin.backend.common.pop const val SNIPPET_SOURCE = "" @@ -120,7 +121,8 @@ class SnippetErrorListener( @JsonClass(generateAdapter = true) data class SnippetArguments( val indent: Int = 4, - var fileType: Source.FileType = Source.FileType.JAVA + var fileType: Source.FileType = Source.FileType.JAVA, + val noEmptyMain: Boolean = false ) @Suppress("LongMethod", "ComplexMethod") @@ -213,6 +215,7 @@ ${" ".repeat(snippetArguments.indent * 2)}@JvmStatic fun main() {""".lines().let klassLines.add(it.start.line..it.stop.line) } + var sawMainLines = false val topLevelStart = parseTree.topLevelObject()?.firstOrNull()?.start?.line ?: 0 val topLevelEnd = parseTree.topLevelObject()?.lastOrNull()?.stop?.line?.inc() ?: 0 @Suppress("MagicNumber") @@ -220,6 +223,7 @@ ${" ".repeat(snippetArguments.indent * 2)}@JvmStatic fun main() {""".lines().let if (methodLines.any { it.contains(lineNumber) } || klassLines.any { it.contains(lineNumber) }) { continue } + sawMainLines = true val indentAmount = if (lineNumber in multilineLines) { 0 } else { @@ -231,8 +235,13 @@ ${" ".repeat(snippetArguments.indent * 2)}@JvmStatic fun main() {""".lines().let currentOutputLineNumber++ } - rewrittenSourceLines.add("""${" ".repeat(snippetArguments.indent * 2)}}""") - currentOutputLineNumber++ + if (sawMainLines || !snippetArguments.noEmptyMain) { + rewrittenSourceLines.add("""${" ".repeat(snippetArguments.indent * 2)}}""") + currentOutputLineNumber++ + } else { + rewrittenSourceLines.pop() + currentOutputLineNumber-- + } @Suppress("MagicNumber") for (methodRange in methodLines) { diff --git a/core/src/main/resources/edu.illinois.cs.cs125.jeed.core.version b/core/src/main/resources/edu.illinois.cs.cs125.jeed.core.version index f07555f5..a3c570b0 100644 --- a/core/src/main/resources/edu.illinois.cs.cs125.jeed.core.version +++ b/core/src/main/resources/edu.illinois.cs.cs125.jeed.core.version @@ -1 +1 @@ -version=2021.10.2 \ No newline at end of file +version=2021.10.3 \ No newline at end of file diff --git a/core/src/test/kotlin/TestKotlinComplexity.kt b/core/src/test/kotlin/TestKotlinComplexity.kt index ecb53f1a..97b56fff 100644 --- a/core/src/test/kotlin/TestKotlinComplexity.kt +++ b/core/src/test/kotlin/TestKotlinComplexity.kt @@ -695,4 +695,20 @@ fun first(first: Int, second: Int): Int { it.lookup("first(Int,Int):Int", "Main.kt").complexity shouldBe 8 } } + "should measure modulus correctly" { + Source.fromKotlin( + """ +class Main { + companion object { + fun sumIsOdd(first: Int, second: Int): Boolean { + return (first + second) % 2 != 0 + } + } +} +""".trim() + ).complexity().also { + it.lookup("Main", "Main.kt").complexity shouldBe 1 + it.lookupFile("Main.kt") shouldBe 1 + } + } }) diff --git a/core/src/test/kotlin/TestSnippet.kt b/core/src/test/kotlin/TestSnippet.kt index 326c654e..65bfcc50 100644 --- a/core/src/test/kotlin/TestSnippet.kt +++ b/core/src/test/kotlin/TestSnippet.kt @@ -695,6 +695,38 @@ class Example { executionResult should haveOutput("") } } + "should parse kotlin snippets without empty main when requested" { + Source.fromSnippet( + """ +fun test() { + i = 0 +} +""".trim(), + SnippetArguments(fileType = Source.FileType.KOTLIN) + ).also { + it.rewrittenSource.lines() shouldHaveSize 9 + val compilerError = shouldThrow { + it.kompile() + } + compilerError.errors shouldHaveSize 1 + compilerError.errors[0].location?.line shouldBe 2 + } + Source.fromSnippet( + """ +fun test() { + i = 0 +} +""".trim(), + SnippetArguments(fileType = Source.FileType.KOTLIN, noEmptyMain = true) + ).also { + it.rewrittenSource.lines() shouldHaveSize 7 + val compilerError = shouldThrow { + it.kompile() + } + compilerError.errors shouldHaveSize 1 + compilerError.errors[0].location?.line shouldBe 2 + } + } }) fun haveParseErrorOnLine(line: Int) = object : Matcher { diff --git a/server/src/main/resources/edu.illinois.cs.cs125.jeed.server.version b/server/src/main/resources/edu.illinois.cs.cs125.jeed.server.version index f07555f5..a3c570b0 100644 --- a/server/src/main/resources/edu.illinois.cs.cs125.jeed.server.version +++ b/server/src/main/resources/edu.illinois.cs.cs125.jeed.server.version @@ -1 +1 @@ -version=2021.10.2 \ No newline at end of file +version=2021.10.3 \ No newline at end of file