Skip to content

Commit 762ff85

Browse files
authored
add support for JSON.RESP (RedisJSON#39)
* add support for JSON.RESP * Use Bulk String for RESP per ReJSON spec
1 parent d97439a commit 762ff85

File tree

2 files changed

+44
-3
lines changed

2 files changed

+44
-3
lines changed

src/lib.rs

+43-2
Original file line numberDiff line numberDiff line change
@@ -578,8 +578,49 @@ fn json_debug(_ctx: &Context, _args: Vec<String>) -> RedisResult {
578578
///
579579
/// JSON.RESP <key> [path]
580580
///
581-
fn json_resp(_ctx: &Context, _args: Vec<String>) -> RedisResult {
582-
Err("Command was not implemented".into())
581+
fn json_resp(ctx: &Context, args: Vec<String>) -> RedisResult {
582+
let mut args = args.into_iter().skip(1);
583+
584+
let key = args.next_string()?;
585+
let path = backwards_compat_path(args.next_string()?);
586+
587+
let key = ctx.open_key(&key);
588+
match key.get_value::<RedisJSON>(&REDIS_JSON_TYPE)? {
589+
Some(doc) => Ok(resp_serialize(doc.get_doc(&path)?)),
590+
None => Ok(().into()),
591+
}
592+
}
593+
594+
fn resp_serialize(doc: &Value) -> RedisValue {
595+
match doc {
596+
Value::Null => RedisValue::None,
597+
598+
Value::Bool(b) => RedisValue::SimpleString(b.to_string()),
599+
600+
Value::Number(n) => n
601+
.as_i64()
602+
.map(|i| RedisValue::Integer(i))
603+
.unwrap_or_else(|| RedisValue::Float(n.as_f64().unwrap())),
604+
605+
Value::String(s) => RedisValue::BulkString(s.clone()),
606+
607+
Value::Array(arr) => {
608+
let mut res: Vec<RedisValue> = Vec::with_capacity(arr.len() + 1);
609+
res.push(RedisValue::SimpleStringStatic("["));
610+
arr.iter().for_each(|v| res.push(resp_serialize(v)));
611+
RedisValue::Array(res)
612+
}
613+
614+
Value::Object(obj) => {
615+
let mut res: Vec<RedisValue> = Vec::with_capacity(obj.len() + 1);
616+
res.push(RedisValue::SimpleStringStatic("{"));
617+
for (key, value) in obj.iter() {
618+
res.push(RedisValue::SimpleString(key.to_string()));
619+
res.push(resp_serialize(value));
620+
}
621+
RedisValue::Array(res)
622+
}
623+
}
583624
}
584625

585626
fn json_len<F: Fn(&RedisJSON, &String) -> Result<usize, Error>>(

src/redisjson.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -216,7 +216,7 @@ impl RedisJSON {
216216
}
217217
}
218218

219-
fn get_doc<'a>(&'a self, path: &'a str) -> Result<&'a Value, Error> {
219+
pub fn get_doc<'a>(&'a self, path: &'a str) -> Result<&'a Value, Error> {
220220
let results = jsonpath_lib::select(&self.data, path)?;
221221
match results.first() {
222222
Some(s) => Ok(s),

0 commit comments

Comments
 (0)