Refactor LanguageModuleInterpreter and its dependencies
This commit is contained in:
@@ -3,18 +3,21 @@ package io.smnp.environment
|
||||
import io.smnp.callable.function.Function
|
||||
import io.smnp.callable.method.Method
|
||||
import io.smnp.type.model.Value
|
||||
import io.smnp.type.module.Module
|
||||
|
||||
interface Environment {
|
||||
fun loadModule(path: String)
|
||||
fun printModules(printContent: Boolean)
|
||||
fun invokeFunction(name: String, arguments: List<Value>): Value
|
||||
fun invokeMethod(obj: Value, name: String, arguments: List<Value>): Value
|
||||
fun printCallStack()
|
||||
fun defineFunction(function: Function)
|
||||
fun defineMethod(method: Method)
|
||||
fun pushScope(scope: MutableMap<String, Value> = mutableMapOf())
|
||||
fun popScope(): Map<String, Value>?
|
||||
fun printScopes()
|
||||
fun setVariable(name: String, value: Value)
|
||||
fun getVariable(name: String): Value
|
||||
fun loadModule(path: String)
|
||||
fun printModules(printContent: Boolean)
|
||||
fun invokeFunction(name: String, arguments: List<Value>): Value
|
||||
fun invokeMethod(obj: Value, name: String, arguments: List<Value>): Value
|
||||
fun printCallStack()
|
||||
fun defineFunction(function: Function)
|
||||
fun defineMethod(method: Method)
|
||||
fun pushScope(scope: MutableMap<String, Value> = mutableMapOf())
|
||||
fun popScope(): Map<String, Value>?
|
||||
fun printScopes()
|
||||
fun setVariable(name: String, value: Value)
|
||||
fun getVariable(name: String): Value
|
||||
|
||||
fun getRootModule(): Module
|
||||
}
|
||||
@@ -7,14 +7,20 @@ abstract class LanguageModuleProvider(path: String) : ModuleProvider(path) {
|
||||
open fun files() = listOf("main.mus")
|
||||
|
||||
override fun provideModule(interpreter: Interpreter): Module {
|
||||
val module = Module.create(path)
|
||||
interpreter.updateRootModule(module)
|
||||
val segments = path.split(".")
|
||||
val parentNodesChainPath = segments.dropLast(1).joinToString(".")
|
||||
val moduleName = segments.last()
|
||||
|
||||
files()
|
||||
val module = files()
|
||||
.asSequence()
|
||||
.map { javaClass.classLoader.getResource(it) }
|
||||
.map { it.readText() }
|
||||
.forEach { interpreter.run(it) }
|
||||
.map { interpreter.run(it) }
|
||||
.map { it.getRootModule() }
|
||||
.reduce { acc, module -> acc.merge(module) }
|
||||
|
||||
return module
|
||||
module.name = moduleName
|
||||
|
||||
return Module.create(parentNodesChainPath, children = listOf(module))
|
||||
}
|
||||
}
|
||||
@@ -1,8 +1,7 @@
|
||||
package io.smnp.interpreter
|
||||
|
||||
import io.smnp.type.module.Module
|
||||
import io.smnp.environment.Environment
|
||||
|
||||
interface Interpreter {
|
||||
fun run(code: String)
|
||||
fun updateRootModule(newRootModule: Module): Unit = throw RuntimeException("Replacing root module is not supported in this Interpreter implementation")
|
||||
fun run(code: String): Environment
|
||||
}
|
||||
@@ -5,7 +5,7 @@ import io.smnp.callable.method.Method
|
||||
import io.smnp.type.model.Value
|
||||
|
||||
class Module(
|
||||
val name: String,
|
||||
var name: String,
|
||||
functions: List<Function> = emptyList(),
|
||||
methods: List<Method> = emptyList(),
|
||||
children: List<Module> = emptyList()
|
||||
|
||||
@@ -10,7 +10,8 @@ import io.smnp.runtime.model.CallStack
|
||||
import io.smnp.type.model.Value
|
||||
import io.smnp.type.module.Module
|
||||
|
||||
class DefaultEnvironment(private val rootModule: Module = Module.create("<root>")) : Environment {
|
||||
class DefaultEnvironment : Environment {
|
||||
private val rootModule = Module.create("<root>")
|
||||
private val loadedModules = mutableListOf<String>()
|
||||
private val callStack = CallStack()
|
||||
|
||||
@@ -105,4 +106,6 @@ class DefaultEnvironment(private val rootModule: Module = Module.create("<root>"
|
||||
override fun setVariable(name: String, value: Value) = callStack.top().setVariable(name, value)
|
||||
|
||||
override fun getVariable(name: String) = callStack.top().getVariable(name)
|
||||
|
||||
override fun getRootModule() = rootModule
|
||||
}
|
||||
@@ -13,12 +13,13 @@ class DefaultInterpreter : Interpreter {
|
||||
private val parser = RootParser()
|
||||
private val evaluator = RootEvaluator()
|
||||
|
||||
fun run(code: String, printTokens: Boolean = false, printAst: Boolean = false, dryRun: Boolean = false) {
|
||||
fun run(code: String, printTokens: Boolean = false, printAst: Boolean = false, dryRun: Boolean = false): Environment {
|
||||
val lines = code.split("\n")
|
||||
run(lines, printTokens, printAst, dryRun)
|
||||
return run(lines, printTokens, printAst, dryRun)
|
||||
}
|
||||
|
||||
private fun run(lines: List<String>, printTokens: Boolean = false, printAst: Boolean = false, dryRun: Boolean = false) {
|
||||
private fun run(lines: List<String>, printTokens: Boolean, printAst: Boolean, dryRun: Boolean): Environment {
|
||||
val environment = createEnvironment()
|
||||
val tokens = tokenizer.tokenize(lines)
|
||||
val ast = parser.parse(tokens)
|
||||
|
||||
@@ -26,13 +27,14 @@ class DefaultInterpreter : Interpreter {
|
||||
if(printAst) ast.node.pretty()
|
||||
|
||||
if(!dryRun) {
|
||||
val environment = createEnvironment()
|
||||
val result = evaluator.evaluate(ast.node, environment)
|
||||
|
||||
if(result.result == EvaluationResult.FAILED) {
|
||||
throw RuntimeException("Evaluation failed")
|
||||
}
|
||||
}
|
||||
|
||||
return environment
|
||||
}
|
||||
|
||||
private fun createEnvironment(): Environment {
|
||||
@@ -42,9 +44,9 @@ class DefaultInterpreter : Interpreter {
|
||||
return environment
|
||||
}
|
||||
|
||||
fun run(file: File, printTokens: Boolean = false, printAst: Boolean = false, dryRun: Boolean = false) {
|
||||
fun run(file: File, printTokens: Boolean = false, printAst: Boolean = false, dryRun: Boolean = false): Environment {
|
||||
val lines = file.readLines()
|
||||
run(lines, printTokens, printAst, dryRun)
|
||||
return run(lines, printTokens, printAst, dryRun)
|
||||
}
|
||||
|
||||
override fun run(code: String) = run(code, printTokens = false, printAst = false, dryRun = false)
|
||||
|
||||
@@ -21,26 +21,17 @@ class LanguageModuleInterpreter : Interpreter {
|
||||
), "function definition or extend statement")
|
||||
)
|
||||
|
||||
override fun updateRootModule(newRootModule: Module) {
|
||||
rootModule = newRootModule
|
||||
}
|
||||
|
||||
override fun run(code: String) {
|
||||
override fun run(code: String): Environment {
|
||||
val lines = code.split("\n")
|
||||
val tokens = tokenizer.tokenize(lines)
|
||||
val ast = parser.parse(tokens)
|
||||
|
||||
val environment = createEnvironment()
|
||||
val environment = DefaultEnvironment()
|
||||
val result = evaluator.evaluate(ast.node, environment)
|
||||
|
||||
if (result.result == EvaluationResult.FAILED) {
|
||||
throw RuntimeException("Evaluation failed")
|
||||
}
|
||||
}
|
||||
|
||||
private fun createEnvironment(): Environment {
|
||||
val environment = DefaultEnvironment(rootModule)
|
||||
environment.loadModule("smnp.lang")
|
||||
|
||||
return environment
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user