From f7b429fbfe47f437174a9f755278caae0d354cc0 Mon Sep 17 00:00:00 2001 From: Chris Wanstrath Date: Sun, 26 Oct 2025 12:12:00 -0700 Subject: [PATCH] better echo --- src/{prelude.ts => prelude/index.ts} | 65 +++++++++++++++------------- 1 file changed, 36 insertions(+), 29 deletions(-) rename src/{prelude.ts => prelude/index.ts} (77%) diff --git a/src/prelude.ts b/src/prelude/index.ts similarity index 77% rename from src/prelude.ts rename to src/prelude/index.ts index 77dc987..fb80502 100644 --- a/src/prelude.ts +++ b/src/prelude/index.ts @@ -1,6 +1,7 @@ // The prelude creates all the builtin Shrimp functions. -import { toValue, type Value, extractParamInfo, isWrapped, getOriginalFunction } from 'reefvm' +import { readFileSync } from 'fs' +import { VM, isValue, toValue, type Value, extractParamInfo, isWrapped, getOriginalFunction } from 'reefvm' export const colors = { reset: '\x1b[0m', @@ -15,40 +16,28 @@ export const colors = { pink: '\x1b[38;2;255;105;180m' } -export const valueFunctions = { - echo: (...args: Value[]) => { - console.log(...args.map(a => formatValue(a))) +export const nativeFunctions = { + // hello + echo: (...args: any[]) => { + console.log(...args.map(a => { + const v = toValue(a) + return ['array', 'dict'].includes(v.type) ? formatValue(v, true) : v.value + })) return toValue(null) }, - length: (value: Value) => { + // info + type: (v: any) => toValue(v).type, + inspect: (v: any) => formatValue(toValue(v)), + length: (v: any) => { + const value = toValue(v) switch (value.type) { - case 'string': case 'array': - return toValue(value.value.length) - case 'dict': - return toValue(Object.keys(value.value).length) - default: - return toValue(0) + case 'string': case 'array': return value.value.length + case 'dict': return value.value.size + default: return 0 } }, - type: (value: Value) => toValue(value.type), - inspect: (value: Value) => toValue(formatValue(value)) -} - -export const nativeFunctions = { - range: (start: number, end: number | null) => { - if (end === null) { - end = start - start = 0 - } - const result: number[] = [] - for (let i = start; i <= end; i++) { - result.push(i) - } - return result - }, - // strings join: (arr: any[], sep: string = ',') => arr.join(sep), split: (str: string, sep: string = ',') => str.split(sep), @@ -61,6 +50,17 @@ export const nativeFunctions = { list: (...args: any[]) => args, dict: (atNamed = {}) => atNamed, slice: (list: any[], start: number, end?: number) => list.slice(start, end), + range: (start: number, end: number | null) => { + if (end === null) { + end = start + start = 0 + } + const result: number[] = [] + for (let i = start; i <= end; i++) { + result.push(i) + } + return result + }, // enumerables map: async (list: any[], cb: Function) => { @@ -71,9 +71,16 @@ export const nativeFunctions = { each: async (list: any[], cb: Function) => { for (const value of list) await cb(value) }, + + // modules + use: function (this: VM, path: string) { + const file = readFileSync(path + '.sh') + } } -export function formatValue(value: Value, inner = false): string { +export function formatValue(value: Value | any, inner = false): string { + if (!isValue(value)) value = toValue(value) + switch (value.type) { case 'string': return `${colors.green}'${value.value.replaceAll("'", "\\'")}${colors.green}'${colors.reset}`