use module
This commit is contained in:
parent
225906179c
commit
0bd36438c8
|
|
@ -1,7 +1,12 @@
|
||||||
// The prelude creates all the builtin Shrimp functions.
|
// The prelude creates all the builtin Shrimp functions.
|
||||||
|
|
||||||
|
import { resolve, parse } from 'path'
|
||||||
import { readFileSync } from 'fs'
|
import { readFileSync } from 'fs'
|
||||||
import { VM, isValue, toValue, type Value, extractParamInfo, isWrapped, getOriginalFunction } from 'reefvm'
|
import { Compiler } from '#compiler/compiler'
|
||||||
|
import {
|
||||||
|
VM, Scope, toValue, type Value,
|
||||||
|
extractParamInfo, isWrapped, getOriginalFunction,
|
||||||
|
} from 'reefvm'
|
||||||
|
|
||||||
export const colors = {
|
export const colors = {
|
||||||
reset: '\x1b[0m',
|
reset: '\x1b[0m',
|
||||||
|
|
@ -16,7 +21,7 @@ export const colors = {
|
||||||
pink: '\x1b[38;2;255;105;180m'
|
pink: '\x1b[38;2;255;105;180m'
|
||||||
}
|
}
|
||||||
|
|
||||||
export const nativeFunctions = {
|
export const globalFunctions = {
|
||||||
// hello
|
// hello
|
||||||
echo: (...args: any[]) => {
|
echo: (...args: any[]) => {
|
||||||
console.log(...args.map(a => {
|
console.log(...args.map(a => {
|
||||||
|
|
@ -73,14 +78,33 @@ export const nativeFunctions = {
|
||||||
},
|
},
|
||||||
|
|
||||||
// modules
|
// modules
|
||||||
use: function (this: VM, path: string) {
|
use: async function (this: VM, path: string) {
|
||||||
const file = readFileSync(path + '.sh')
|
const scope = this.scope
|
||||||
|
const pc = this.pc
|
||||||
|
|
||||||
|
const fullPath = resolve(path) + '.sh'
|
||||||
|
const code = readFileSync(fullPath, 'utf-8')
|
||||||
|
|
||||||
|
this.pc = this.instructions.length
|
||||||
|
this.scope = new Scope(scope)
|
||||||
|
const compiled = new Compiler(code)
|
||||||
|
this.appendBytecode(compiled.bytecode)
|
||||||
|
|
||||||
|
await this.continue()
|
||||||
|
|
||||||
|
const module: Map<string, Value> = new Map
|
||||||
|
for (const [name, value] of this.scope.locals.entries())
|
||||||
|
module.set(name, value)
|
||||||
|
|
||||||
|
this.scope = scope
|
||||||
|
this.pc = pc
|
||||||
|
this.stopped = false
|
||||||
|
|
||||||
|
this.scope.set(parse(fullPath).name, { type: 'dict', value: module })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function formatValue(value: Value | any, inner = false): string {
|
export function formatValue(value: Value, inner = false): string {
|
||||||
if (!isValue(value)) value = toValue(value)
|
|
||||||
|
|
||||||
switch (value.type) {
|
switch (value.type) {
|
||||||
case 'string':
|
case 'string':
|
||||||
return `${colors.green}'${value.value.replaceAll("'", "\\'")}${colors.green}'${colors.reset}`
|
return `${colors.green}'${value.value.replaceAll("'", "\\'")}${colors.green}'${colors.reset}`
|
||||||
|
|
|
||||||
28
src/prelude/tests/use.test.ts
Normal file
28
src/prelude/tests/use.test.ts
Normal file
|
|
@ -0,0 +1,28 @@
|
||||||
|
import { expect, describe, test } from 'bun:test'
|
||||||
|
import { globalFunctions } from '#prelude'
|
||||||
|
|
||||||
|
describe('use', () => {
|
||||||
|
test(`imports all a file's functions`, async () => {
|
||||||
|
expect(`
|
||||||
|
use ./src/prelude/tests/math
|
||||||
|
dbl = math | at double
|
||||||
|
dbl 4
|
||||||
|
`).toEvaluateTo(8, globalFunctions)
|
||||||
|
|
||||||
|
expect(`
|
||||||
|
use ./src/prelude/tests/math
|
||||||
|
math | at pi
|
||||||
|
`).toEvaluateTo(3.14, globalFunctions)
|
||||||
|
|
||||||
|
expect(`
|
||||||
|
use ./src/prelude/tests/math
|
||||||
|
math | at 🥧
|
||||||
|
`).toEvaluateTo(3.14159265359, globalFunctions)
|
||||||
|
|
||||||
|
expect(`
|
||||||
|
use ./src/prelude/tests/math
|
||||||
|
call = do x y: x y end
|
||||||
|
call (math | at add1) 5
|
||||||
|
`).toEvaluateTo(6, globalFunctions)
|
||||||
|
})
|
||||||
|
})
|
||||||
Loading…
Reference in New Issue
Block a user