Add json_get_raw builtin to El VM

Adds json_get_raw(value, key) -> String that serializes any JSON field
(including nested objects and arrays) back to a JSON string. Existing
json_get_string only handles primitive string values. This enables
traversing nested JSON structures in El programs.

Also registers json_get_raw in is_builtin().
This commit is contained in:
Will Anderson
2026-04-29 04:39:18 -05:00
parent bffa3583b2
commit db794d3f9e
+40 -1
View File
@@ -4187,6 +4187,45 @@ fn dispatch_builtin(
BuiltinResult::Handled
}
// ── JSON raw field extractor ──────────────────────────────────────────
// json_get_raw(json_str_or_struct, key) -> String
// Returns the JSON-serialized value at key, including objects and arrays.
// Unlike json_get_string which only handles primitive strings, this works
// for any JSON type and always returns a valid JSON string.
"json_get_raw" => {
let key = match stack.pop().unwrap_or(Value::Nil) {
Value::Str(s) => s,
_ => String::new(),
};
let v = stack.pop().unwrap_or(Value::Nil);
let result = match &v {
Value::Map(pairs) => pairs.iter()
.find(|(k, _)| k == &key)
.map(|(_, v)| {
let jv = el_value_to_json_value(v);
serde_json::to_string(&jv).unwrap_or_default()
})
.unwrap_or_default(),
Value::Struct { fields, .. } => fields.iter()
.find(|(k, _)| k == &key)
.map(|(_, v)| {
let jv = el_value_to_json_value(v);
serde_json::to_string(&jv).unwrap_or_default()
})
.unwrap_or_default(),
Value::Str(json_str) => {
serde_json::from_str::<serde_json::Value>(json_str)
.ok()
.and_then(|jv| jv.get(&key).cloned())
.map(|v| serde_json::to_string(&v).unwrap_or_default())
.unwrap_or_default()
}
_ => String::new(),
};
stack.push(Value::Str(result));
BuiltinResult::Handled
}
// ── HTTP auth builtins (Bearer token) ─────────────────────────────────
"http_get_auth" => {
@@ -6521,7 +6560,7 @@ fn is_builtin(name: &str) -> bool {
| "hash_sha256" | "blake3_hash"
| "float_to_str" | "int_to_str" | "str_to_int" | "str_to_float" | "parse_float" | "parse_int" | "bool_to_str"
| "bytes_to_str" | "str_to_bytes"
| "json_get" | "json_get_int" | "json_get_string" | "json_get_array" | "json_get_bool" | "json_get_float"
| "json_get" | "json_get_int" | "json_get_string" | "json_get_array" | "json_get_bool" | "json_get_float" | "json_get_raw"
| "json_set" | "json_stringify" | "json_parse" | "json_encode" | "json_decode" | "json_keys"
| "json_array_get" | "json_array_len" | "json_array_push"
| "str_eq" | "str_split" | "str_contains" | "str_starts_with" | "str_ends_with" | "str_replace"