Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
package com.specificlanguages.mops.cli

import com.specificlanguages.mops.protocol.MakeOutcome
import com.specificlanguages.mops.protocol.MakeResponse
import com.specificlanguages.mops.protocol.ProtocolJson
import org.junit.jupiter.api.io.CleanupMode
import org.junit.jupiter.api.io.TempDir
import org.junit.jupiter.api.parallel.ResourceLock
import java.nio.file.Path
import kotlin.io.path.createDirectories
import kotlin.io.path.pathString
import kotlin.io.path.writeText
import kotlin.test.Test
import kotlin.test.assertEquals

/** Creates a solution with `mops create solution`, adds a test to it, and makes and tests it in a worker process. */
@ResourceLock("system-streams")
class CreatedSolutionIntegrationTest {
@TempDir(cleanup = CleanupMode.ON_SUCCESS)
lateinit var tempDir: Path

@Test
fun `a solution created with the java-tests preset makes and runs its tests`() {
val project = copyTestProject("base-language-sandbox", tempDir.resolve("project"))
val home = tempDir.resolve("daemon-home").createDirectories()
fun cli(vararg args: String) = runCommandLine(project, "--daemon-home", home.pathString, *javaAndMpsHomeArgs(), *args)
try {
assertEquals(0, cli("create", "solution", "created.tests", "--usage-preset", "java-tests").exitCode)
assertEquals(0, cli("create", "model", "created.tests.main", "--module", "created.tests").exitCode)
val script = tempDir.resolve("content.groovy")
script.writeText("""
project.command {
def module = mops.lookup.requireModule('created.tests')
def descriptor = module.moduleDescriptor
['49808fad-9d41-4b96-83fa-9231640f6b2b(JUnit)', '6354ebe7-c22a-4a0f-ac54-50b52ab9b065(JDK)'].each {
descriptor.dependencies.add(new jetbrains.mps.project.structure.modules.Dependency(
org.jetbrains.mps.openapi.persistence.PersistenceFacade.instance.createModuleReference(it), false))
}
module.setModuleDescriptor(descriptor)
module.save()
mops.parsing.java.addJavaClassesFromString(mops.lookup.requireModel('created.tests.main'),
'public class CreatedTest extends junit.framework.TestCase { public void testSum() { assertEquals(2, 1 + 1); } }').unresolved
}
""".trimIndent())
val content = cli("code", "run", script.pathString)
assertEquals(0, content.exitCode, content.output)
val unresolvedReferences = content.stdout.trim()
assertEquals("[]", unresolvedReferences, content.output)

val make = cli("make", "module", "created.tests", "--json")
assertEquals(0, make.exitCode, make.output)
assertEquals(MakeOutcome.SUCCESS, (ProtocolJson.decodeResponse(make.stdout) as MakeResponse).outcome, make.output)
val test = cli("test", "created.tests", "--no-build", "--json")
assertEquals(0, test.exitCode, test.output)
val report = ProtocolJson.testReport.decode(test.stdout)
assertEquals("SUCCESS", report.outcome, test.output)
assertEquals(listOf("PASSED"), report.results.filter { it.kind == "TEST" }.map { it.status }, test.output)
} finally { stopDaemons(project, home) }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ class ModuleCreator(private val project: Project) {
moduleFacetDescriptors.add(JavaModuleFacetImpl.forJavaCodeModule(
JavaModuleFacet.Compile.MPS, JavaModuleFacet.LoadClasses.ManagedByMPS, JavaModuleFacet.LoadExtensions.Plugin,
))
outputRoot = "\${module}/source_gen"
outputRoot = DEFAULT_OUTPUT_ROOT
}
return (ModuleRepositoryFacade(mpsProject).instantiate(value, descriptorFile) as Language)
.also { mpsProject.addModule(it); it.setChanged() }
Expand All @@ -167,6 +167,7 @@ class ModuleCreator(private val project: Project) {
JavaModuleFacet.Compile.MPS, JavaModuleFacet.LoadClasses.ManagedByMPS, JavaModuleFacet.LoadExtensions.Plugin,
))
}
if (preset != SolutionUsagePreset.NOT_GENERATED) outputRoot = DEFAULT_OUTPUT_ROOT
}
return (instantiate(value, file(descriptor)) as Solution).also { mpsProject.addModule(it); it.setChanged() }
}
Expand Down Expand Up @@ -279,4 +280,9 @@ class ModuleCreator(private val project: Project) {

private fun file(path: Path) = mpsProject.fileSystem.getFile(path.toString())
private fun fail(code: MpsErrorCode, message: String): Nothing = throw MpsRequestException(code, message)

private companion object {
/** The generator output root that MPS uses when a module descriptor does not name one. */
const val DEFAULT_OUTPUT_ROOT = "\${module}/source_gen"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import com.specificlanguages.mops.protocol.GeneratorPersistence
import com.specificlanguages.mops.protocol.ModuleCreationResponse
import com.specificlanguages.mops.protocol.ModuleKind
import com.specificlanguages.mops.protocol.SolutionUsagePreset
import org.junit.jupiter.params.ParameterizedTest
import org.junit.jupiter.params.provider.EnumSource
import kotlin.io.path.exists
import kotlin.io.path.readText
import kotlin.test.assertIs
Expand Down Expand Up @@ -35,6 +37,18 @@ class ModuleCreationSemanticsTest {
}
}

@ParameterizedTest
@EnumSource(SolutionUsagePreset::class, names = ["TEXT", "JAVA", "JAVA_TESTS", "JAVA_MPS_PLUGIN"])
fun `solution of a generated preset keeps the default generator output path`(preset: SolutionUsagePreset) {
SharedMpsEnvironment.withOpenProjectCopy { project, projectPath ->
DomainRequestHandler(projectPath, SharedMpsEnvironment.mpsAccess(project))
.handleDomainRequest(CreateSolutionRequest("", "example.generated", usagePreset = preset))

val descriptor = projectPath.resolve("solutions/example.generated/example.generated.msd").readText()
assertFalse("generatorOutputPath" in descriptor, descriptor)
}
}

@Test
fun `solution report names the usage preset and the facets it produced`() {
SharedMpsEnvironment.withOpenProjectCopy { project, _ ->
Expand Down
Loading