add runtime/fs.el, exec.el, env.el — filesystem, subprocess, environment in El
Migrates fs_read/write/exists/mkdir/write_bytes/list, exec/exec_bg/exec_command/exec_capture, env/args/exit_program, state_set/get/del/keys, uuid_new/v4, and list helpers get/len from el_runtime.c into El source as thin wrappers over seed primitives.
This commit is contained in:
@@ -0,0 +1,77 @@
|
||||
// runtime/env.el — environment and process
|
||||
// Covers: environment variables, command-line args, process exit, in-process
|
||||
// state store, UUID generation, and list convenience helpers.
|
||||
|
||||
// env — read an environment variable. Returns "" if the variable is not set.
|
||||
fn env(key: String) -> String {
|
||||
return __env_get(key)
|
||||
}
|
||||
|
||||
// args — command-line arguments as a list of strings.
|
||||
// __args_json returns a JSON array (e.g. ["prog","arg1","arg2"]).
|
||||
// The list is built by iterating over the array.
|
||||
fn args() -> [String] {
|
||||
let json: String = __args_json()
|
||||
let n: Int = json_array_len(json)
|
||||
let result: [String] = el_list_empty()
|
||||
let i: Int = 0
|
||||
while i < n {
|
||||
let item: String = json_array_get_string(json, i)
|
||||
let result = el_list_append(result, item)
|
||||
let i = i + 1
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
// exit_program — terminate the process with the given exit code.
|
||||
fn exit_program(code: Int) {
|
||||
__exit_program(code)
|
||||
}
|
||||
|
||||
// ── List convenience helpers ───────────────────────────────────────────────
|
||||
|
||||
// get — index into a list. Thin alias for el_list_get used throughout the
|
||||
// El stdlib so call sites read like `get(lst, i)` rather than the verbose form.
|
||||
fn get(lst: [String], i: Int) -> String {
|
||||
return el_list_get(lst, i)
|
||||
}
|
||||
|
||||
// len — length of a list.
|
||||
fn len(lst: [String]) -> Int {
|
||||
return el_list_len(lst)
|
||||
}
|
||||
|
||||
// ── In-process key-value state store ──────────────────────────────────────
|
||||
|
||||
// state_set — store a string value under key.
|
||||
fn state_set(key: String, val: String) {
|
||||
__state_set(key, val)
|
||||
}
|
||||
|
||||
// state_get — retrieve value for key; returns "" if key not present.
|
||||
fn state_get(key: String) -> String {
|
||||
return __state_get(key)
|
||||
}
|
||||
|
||||
// state_del — remove key from the store.
|
||||
fn state_del(key: String) {
|
||||
__state_del(key)
|
||||
}
|
||||
|
||||
// state_keys — all keys currently in the store as a JSON array string.
|
||||
fn state_keys() -> String {
|
||||
return __state_keys()
|
||||
}
|
||||
|
||||
// ── UUID generation ────────────────────────────────────────────────────────
|
||||
|
||||
// uuid_new — generate a new random UUID v4.
|
||||
fn uuid_new() -> String {
|
||||
return __uuid_v4()
|
||||
}
|
||||
|
||||
// uuid_v4 — alias for uuid_new(); explicit version name for callers that
|
||||
// need to be precise about the UUID variant.
|
||||
fn uuid_v4() -> String {
|
||||
return __uuid_v4()
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
// runtime/exec.el — subprocess execution
|
||||
// All four names resolve to the same seed primitives so callers can use
|
||||
// whichever name matches their mental model of the operation.
|
||||
|
||||
// exec — run a shell command, capture stdout, return as String.
|
||||
// Blocks until the subprocess exits (30-second wall-clock deadline in the
|
||||
// seed layer). Returns "" on any error.
|
||||
fn exec(cmd: String) -> String {
|
||||
return __exec(cmd)
|
||||
}
|
||||
|
||||
// exec_bg — fire-and-forget subprocess. Returns immediately; no stdout.
|
||||
fn exec_bg(cmd: String) {
|
||||
__exec_bg(cmd)
|
||||
}
|
||||
|
||||
// exec_command — alias for exec(); preferred when callers care about side
|
||||
// effects (e.g. invoking a build tool) rather than captured output.
|
||||
fn exec_command(cmd: String) -> String {
|
||||
return __exec(cmd)
|
||||
}
|
||||
|
||||
// exec_capture — alias for exec(); preferred when callers explicitly want
|
||||
// to capture and process stdout.
|
||||
fn exec_capture(cmd: String) -> String {
|
||||
return __exec(cmd)
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
// runtime/fs.el — filesystem operations
|
||||
// Thin El wrappers over seed primitives; no logic beyond what is needed
|
||||
// to present a clean API. The heavy lifting lives in el_runtime.c.
|
||||
|
||||
fn fs_read(path: String) -> String {
|
||||
return __fs_read(path)
|
||||
}
|
||||
|
||||
fn fs_write(path: String, content: String) -> Bool {
|
||||
return __fs_write(path, content)
|
||||
}
|
||||
|
||||
fn fs_exists(path: String) -> Bool {
|
||||
return __fs_exists(path)
|
||||
}
|
||||
|
||||
fn fs_mkdir(path: String) -> Bool {
|
||||
return __fs_mkdir(path)
|
||||
}
|
||||
|
||||
fn fs_write_bytes(path: String, bytes: String, n: Int) -> Bool {
|
||||
return __fs_write_bytes(path, bytes, n)
|
||||
}
|
||||
|
||||
// fs_list — return list of filenames in a directory.
|
||||
// __fs_list_raw returns a newline-separated string (possibly with a trailing
|
||||
// newline); callers that need a clean list should filter empty strings.
|
||||
fn fs_list(path: String) -> [String] {
|
||||
let raw: String = __fs_list_raw(path)
|
||||
return str_split(raw, "\n")
|
||||
}
|
||||
|
||||
// fs_list_json — return a JSON array of filenames in a directory.
|
||||
// Empty strings produced by a trailing newline are stripped before encoding.
|
||||
fn fs_list_json(path: String) -> String {
|
||||
let items: [String] = fs_list(path)
|
||||
let n: Int = el_list_len(items)
|
||||
let clean: [String] = el_list_empty()
|
||||
let i: Int = 0
|
||||
while i < n {
|
||||
let item: String = el_list_get(items, i)
|
||||
let trimmed: String = str_trim(item)
|
||||
if !str_eq(trimmed, "") {
|
||||
let clean = el_list_append(clean, "\"" + trimmed + "\"")
|
||||
}
|
||||
let i = i + 1
|
||||
}
|
||||
return json_build_array(clean)
|
||||
}
|
||||
Reference in New Issue
Block a user