introduce a micro stdlib for testing (#3531)

This introduces a tiny alternative to our stdlib, that can be used for testing the interpreter. There are 2 main advantages of such a solution:
1. Performance: on my machine, `runtime-with-intstruments/test` drops from 146s to 65s, while `runtime/test` drops from 165s to 51s. >6 mins total becoming <2 mins total is awesome. This alone means I'll drink less coffee in these breaks and will be healthier.
2. Better separation of concepts – currently working on a feature that breaks _all_ enso code. The dependency of interpreter tests on the stdlib means I have no means of incremental testing – ALL of stdlib must compile. This is horrible, rendered my work impossible, and resulted in this PR.
This commit is contained in:
Marcin Kostrzewa 2022-06-16 12:25:24 +02:00 committed by GitHub
parent 71b3a9f40a
commit ec3fa32fec
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
34 changed files with 218 additions and 15 deletions

View File

@ -246,6 +246,7 @@
- [Added a full-blown DSL for builtins][3471]
- [Lazy evaluation of RHS argument for || and &&][3492]
- [Drop Core implementation of IR][3512]
- [Introduce a smaller version of the standard library, just for testing][3531]
[3227]: https://github.com/enso-org/enso/pull/3227
[3248]: https://github.com/enso-org/enso/pull/3248
@ -273,6 +274,7 @@
[3493]: https://github.com/enso-org/enso/pull/3493
[3505]: https://github.com/enso-org/enso/pull/3505
[3512]: https://github.com/enso-org/enso/pull/3512
[3531]: https://github.com/enso-org/enso/pull/3531
# Enso 2.0.0-alpha.18 (2021-10-12)

View File

@ -66,6 +66,11 @@ public class RuntimeOptions {
private static final OptionDescriptor LANGUAGE_HOME_OVERRIDE_DESCRIPTOR =
OptionDescriptor.newBuilder(LANGUAGE_HOME_OVERRIDE_KEY, LANGUAGE_HOME_OVERRIDE).build();
public static final String EDITION_OVERRIDE = optionName("editionOverride");
public static final OptionKey<String> EDITION_OVERRIDE_KEY = new OptionKey<>("");
private static final OptionDescriptor EDITION_OVERRIDE_DESCRIPTOR =
OptionDescriptor.newBuilder(EDITION_OVERRIDE_KEY, EDITION_OVERRIDE).build();
public static final String DISABLE_IR_CACHES = optionName("disableIrCaches");
public static final OptionKey<Boolean> DISABLE_IR_CACHES_KEY = new OptionKey<>(false);
private static final OptionDescriptor DISABLE_IR_CACHES_DESCRIPTOR =
@ -98,6 +103,7 @@ public class RuntimeOptions {
ENABLE_GLOBAL_SUGGESTIONS_DESCRIPTOR,
INTERACTIVE_MODE_DESCRIPTOR,
LANGUAGE_HOME_OVERRIDE_DESCRIPTOR,
EDITION_OVERRIDE_DESCRIPTOR,
INTERPRETER_SEQUENTIAL_COMMAND_EXECUTION_DESCRIPTOR,
DISABLE_IR_CACHES_DESCRIPTOR,
WAIT_FOR_PENDING_SERIALIZATION_JOBS_DESCRIPTOR,

View File

@ -69,8 +69,12 @@ class RuntimeErrorsTest
.option(RuntimeOptions.INTERACTIVE_MODE, "true")
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.out(out)
.serverTransport(runtimeServerEmulator.makeServerTransport)
.build()

View File

@ -62,8 +62,12 @@ class RuntimeInstrumentTest
.option(RuntimeOptions.INTERACTIVE_MODE, "true")
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.out(out)
.serverTransport(runtimeServerEmulator.makeServerTransport)
.build()

View File

@ -22,8 +22,12 @@ class RuntimeProjectContextTest extends AnyWordSpec with Matchers {
)
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.option(RuntimeOptions.LOG_LEVEL, "WARNING")
.build()
context.initialize(LanguageInfo.ID)

View File

@ -67,8 +67,12 @@ class RuntimeServerTest
.option(RuntimeOptions.INTERACTIVE_MODE, "true")
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.logHandler(logOut)
.out(out)
.serverTransport(runtimeServerEmulator.makeServerTransport)

View File

@ -55,8 +55,12 @@ class RuntimeSuggestionUpdatesTest
.option(RuntimeOptions.INTERACTIVE_MODE, "true")
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.out(out)
.serverTransport(runtimeServerEmulator.makeServerTransport)
.build()

View File

@ -34,4 +34,13 @@ public class OptionsHelper {
return Optional.of(option);
}
}
public static Optional<String> getEditionOverride(TruffleLanguage.Env env) {
String option = env.getOptions().get(RuntimeOptions.EDITION_OVERRIDE_KEY);
if (option.equals("")) {
return Optional.empty();
} else {
return Optional.of(option);
}
}
}

View File

@ -128,12 +128,14 @@ public class Context {
Optional<String> languageHome =
OptionsHelper.getLanguageHomeOverride(environment).or(() -> Optional.ofNullable(home));
var editionOverride = OptionsHelper.getEditionOverride(environment);
var resourceManager = new org.enso.distribution.locking.ResourceManager(lockManager);
packageRepository =
PackageRepository.initializeRepository(
OptionConverters.toScala(projectPackage),
OptionConverters.toScala(languageHome),
OptionConverters.toScala(editionOverride),
distributionManager,
resourceManager,
this,

View File

@ -5,7 +5,7 @@ import com.typesafe.scalalogging.Logger
import org.enso.distribution.locking.ResourceManager
import org.enso.distribution.{DistributionManager, LanguageHome}
import org.enso.editions.updater.EditionManager
import org.enso.editions.{DefaultEdition, LibraryName, LibraryVersion}
import org.enso.editions.{DefaultEdition, Editions, LibraryName, LibraryVersion}
import org.enso.interpreter.instrument.NotificationHandler
import org.enso.interpreter.runtime.builtin.Builtins
import org.enso.interpreter.runtime.util.TruffleFileSystem
@ -27,7 +27,6 @@ import org.enso.pkg.{
}
import java.nio.file.Path
import scala.collection.immutable.ListSet
import scala.util.Try
@ -537,14 +536,19 @@ object PackageRepository {
def initializeRepository(
projectPackage: Option[Package[TruffleFile]],
languageHome: Option[String],
editionOverride: Option[String],
distributionManager: DistributionManager,
resourceManager: ResourceManager,
context: Context,
builtins: Builtins,
notificationHandler: NotificationHandler
): PackageRepository = {
val rawEdition = projectPackage
.flatMap(_.config.edition)
val rawEdition = editionOverride
.map(v => Editions.Raw.Edition(parent = Some(v)))
.orElse(
projectPackage
.flatMap(_.config.edition)
)
.getOrElse(DefaultEdition.getDefaultEdition)
val homeManager = languageHome.map { home => LanguageHome(Path.of(home)) }

View File

@ -109,8 +109,12 @@ class InterpreterContext(
.in(in)
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.serverTransport { (uri, peer) =>
if (uri.toString == DebugServerInfo.URI) {
new DebuggerSessionManagerEndpoint(sessionManager, peer)

View File

@ -25,8 +25,12 @@ trait PackageTest extends AnyFlatSpec with Matchers with ValueEquality {
.option(RuntimeOptions.PROJECT_ROOT, pkgPath.getAbsolutePath)
.option(
RuntimeOptions.LANGUAGE_HOME_OVERRIDE,
Paths.get("../../distribution/component").toFile.getAbsolutePath
Paths
.get("../../test/micro-distribution/component")
.toFile
.getAbsolutePath
)
.option(RuntimeOptions.EDITION_OVERRIDE, "0.0.0-dev")
.option(RuntimeOptions.STRICT_ERRORS, "true")
.option(RuntimeOptions.DISABLE_IR_CACHES, "true")
.out(output)

View File

@ -105,16 +105,15 @@ class TextTest extends InterpreterTest {
"support converting values to display texts" in {
val code =
"""
|from Standard.Base.Data.List import Cons
|from Standard.Base.Data.List import Cons, Nil
|from Standard.Base.Error.Common import all
|import Standard.Base.Data.Text
|import Standard.Base.IO
|import Standard.Base.Nothing
|
|main =
| IO.println (Cons Nothing Nothing).to_display_text
| IO.println (Syntax_Error "foo").to_display_text
| IO.println (Type_Error Nothing Text "myvar").to_display_text
| IO.println (Type_Error Nothing Nil "myvar").to_display_text
| IO.println (Compile_Error "error :(").to_display_text
| IO.println (Inexhaustive_Pattern_Match_Error 32).to_display_text
| IO.println (Arithmetic_Error "cannot frobnicate quaternions").to_display_text
@ -126,7 +125,7 @@ class TextTest extends InterpreterTest {
consumeOut shouldEqual List(
"Cons",
"Syntax error: foo",
"Type error: expected `myvar` to be Nothing, but got Text.",
"Type error: expected `myvar` to be Nothing, but got Nil.",
"Compile error: error :(",
"Inexhaustive pattern match: no branch matches 32 (Integer).",
"Arithmetic error: cannot frobnicate quaternions",

View File

@ -0,0 +1,8 @@
engine-version: 0.0.0-dev
repositories:
- name: main
url: https://libraries.release.enso.org/libraries
libraries:
- name: Standard.Base
repository: main
version: 0.0.0-dev

View File

@ -0,0 +1,3 @@
archives:
- main.tgz
dependencies: []

View File

@ -0,0 +1,10 @@
name: Base
namespace: Standard
version: 0.0.0-dev
license: APLv2
authors:
- name: Enso Team
email: contact@enso.org
maintainers:
- name: Enso Team
email: contact@enso.org

View File

@ -0,0 +1,3 @@
type Any
@Builtin_Type
type Any

View File

@ -0,0 +1,7 @@
type Array
@Builtin_Type
type Array
new_1 item_1 = @Builtin_Method "Array.new_1"
new_2 item_1 item_2 = @Builtin_Method "Array.new_2"
empty = @Builtin_Method "Array.empty"

View File

@ -0,0 +1,11 @@
type Boolean
@Builtin_Type
type Boolean
if_then_else ~on_true ~on_false = @Builtin_Method "Boolean.if_then_else"
@Builtin_Type
type True
@Builtin_Type
type False

View File

@ -0,0 +1,3 @@
type List
type Nil
type Cons x xs

View File

@ -0,0 +1,7 @@
type Number
@Builtin_Type
type Number
type Integer
@Builtin_Type
type Integer

View File

@ -0,0 +1,3 @@
type Text
@Builtin_Type
type Text

View File

@ -0,0 +1,11 @@
polyglot java import java.time.LocalDate
polyglot java import java.time.format.DateTimeFormatter
new year (month = 1) (day = 1) = LocalDate.of year month day
type Date
type Date internal_local_date
year = this . internal_local_date . getYear
month = this . internal_local_date . getMonthValue
day = this . internal_local_date . getDayOfMonth
to_text = DateTimeFormatter.ISO_LOCAL_DATE.format this.internal_local_date

View File

@ -0,0 +1,27 @@
type Panic
@Builtin_Type
type Panic
throw payload = @Builtin_Method "Panic.throw"
catch_primitive ~action handler = @Builtin_Method "Panic.catch_primitive"
@Builtin_Type
type Syntax_Error message
@Builtin_Type
type Polyglot_Error cause
@Builtin_Type
type Arithmetic_Error message
@Builtin_Type
type Type_Error expected actual name
@Builtin_Type
type Compile_Error message
@Builtin_Type
type Inexhaustive_Pattern_Match_Error scrutinee
@Builtin_Type
type Arity_Error expected_min expected_max actual
type Error
@Builtin_Type
type Error
throw payload = @Builtin_Method "Error.throw"
catch_primitive handler = @Builtin_Method "Error.catch_primitive"
catch (handler = x->x) = this.catch_primitive handler

View File

@ -0,0 +1,3 @@
print_err message = @Builtin_Method "IO.print_err"
println message = @Builtin_Method "IO.println"
readln = @Builtin_Method "IO.readln"

View File

@ -0,0 +1,20 @@
import project.IO
export project.IO
import project.Data.List
from project.Data.List export Nil, Cons, List
import project.Polyglot
from project.Polyglot export all
export project.Polyglot.Java
import project.Polyglot.Java
import project.Data.Array
from project.Data.Array export Array
import project.Error.Common
from project.Error.Common export all
import project.Data.Numbers
from project.Data.Numbers export Number

View File

@ -0,0 +1,3 @@
type Nothing
@Builtin_Type
type Nothing

View File

@ -0,0 +1,13 @@
type Polyglot
@Builtin_Type
type Polyglot
get_array_size array = @Builtin_Method "Polyglot.get_array_size"
execute callable arguments = @Builtin_Method "Polyglot.execute"
get_member object member_name = @Builtin_Method "Polyglot.get_member"
get_members object = @Builtin_Method "Polyglot.get_members"
new constructor arguments = @Builtin_Method "Polyglot.new"
invoke target name arguments = @Builtin_Method "Polyglot.invoke"
has_source_location value = @Builtin_Method "Polyglot.has_source_location"
get_source_location value = @Builtin_Method "Polyglot.get_source_location"
is_language_installed language_name = @Builtin_Method "Polyglot.is_language_installed"
get_executable_name = @Builtin_Method "Polyglot.get_executable_name"

View File

@ -0,0 +1 @@
lookup_class name = @Builtin_Method "Java.lookup_class"

View File

@ -0,0 +1,2 @@
eval expression = @Builtin_Method "Debug.eval"
breakpoint = @Builtin_Method "Debug.breakpoint"

View File

@ -0,0 +1,10 @@
bracket : Any -> (Any -> Nothing) -> (Any -> Any) -> Any
bracket ~constructor ~destructor ~action = @Builtin_Method "Resource.bracket"
type Managed_Resource
@Builtin_Type
type Managed_Resource
register resource function = @Builtin_Method "Managed_Resource.register"
finalize = @Builtin_Method "Managed_Resource.finalize"
with ~action = @Builtin_Method "Managed_Resource.with"
take = @Builtin_Method "Managed_Resource.take"

View File

@ -0,0 +1,3 @@
run key local_state ~computation = @Builtin_Method "State.run"
get key = @Builtin_Method "State.get"
put key new_state = @Builtin_Method "State.put"

View File

@ -0,0 +1 @@
with_interrupt_handler ~action ~interrupt_handler = @Builtin_Method "Thread.with_interrupt_handler"

View File

@ -0,0 +1,4 @@
create_process command arguments input redirect_in redirect_out redirect_err = @Builtin_Method "System.create_process"
@Builtin_Type
type System_Process_Result exit_code stdout stderr