Skip to content

Commit 33837d2

Browse files
authored
fix arr_pop backward to 1.0 (RedisJSON#345)
1 parent 3654e36 commit 33837d2

File tree

2 files changed

+25
-16
lines changed

2 files changed

+25
-16
lines changed

src/lib.rs

+20-13
Original file line numberDiff line numberDiff line change
@@ -606,13 +606,13 @@ fn json_arr_pop(ctx: &Context, args: Vec<String>) -> RedisResult {
606606
.next()
607607
.map(|p| {
608608
let path = backwards_compat_path(p);
609-
let index = args.next_i64().unwrap_or(i64::MAX);
609+
let index = args.next_i64().unwrap_or(-1);
610610
(path, index)
611611
})
612612
.unwrap_or((JSON_ROOT_PATH.to_string(), i64::MAX));
613613

614614
let redis_key = ctx.open_key_writable(&key);
615-
let mut res = Value::Null;
615+
let mut res = None;
616616

617617
redis_key
618618
.get_value::<RedisJSON>(&REDIS_JSON_TYPE)?
@@ -629,25 +629,32 @@ fn json_arr_pop(ctx: &Context, args: Vec<String>) -> RedisResult {
629629
)
630630
.map_err(|e| e.into())
631631
})?;
632-
Ok(RedisJSON::serialize(&res, Format::JSON)?.into())
632+
633+
let result = match res {
634+
None => ().into(),
635+
Some(r) => RedisJSON::serialize(&r, Format::JSON)?.into(),
636+
};
637+
Ok(result)
633638
}
634639

635-
fn do_json_arr_pop(mut index: i64, res: &mut Value, value: &mut Value) -> Result<Value, Error> {
640+
fn do_json_arr_pop(index: i64, res: &mut Option<Value>, value: &mut Value) -> Result<Value, Error> {
636641
if let Some(array) = value.as_array() {
637-
// Verify legel index in bounds
638-
let len = array.len() as i64;
639-
index = index.min(len - 1);
640-
if index < 0 {
641-
index += len;
642+
if array.is_empty() {
643+
*res = None;
644+
return Ok(value.clone());
642645
}
643646

644-
if index >= len || index < 0 {
645-
return Err("ERR index out of bounds".into());
646-
}
647+
// Verify legel index in bounds
648+
let len = array.len() as i64;
649+
let index = if index < 0 {
650+
0.max(len + index)
651+
} else {
652+
index.min(len - 1)
653+
} as usize;
647654

648655
let mut new_value = value.take();
649656
let curr = new_value.as_array_mut().unwrap();
650-
*res = curr.remove(index as usize);
657+
*res = Some(curr.remove(index as usize));
651658
Ok(new_value)
652659
} else {
653660
Err(err_json(value, "array"))

tests/pytest/test.py

+5-3
Original file line numberDiff line numberDiff line change
@@ -600,9 +600,11 @@ def testArrPopCommand(env):
600600
r.assertEqual('1', r.execute_command('JSON.ARRPOP', 'test', '.', 0))
601601
r.assertEqual('4', r.execute_command('JSON.ARRPOP', 'test', '.', 2))
602602
r.assertEqual('6', r.execute_command('JSON.ARRPOP', 'test', '.', 99))
603-
# r.assertEqual('2', r.execute_command('JSON.ARRPOP', 'test', '.', -99))
604-
# r.assertEqual('3', r.execute_command('JSON.ARRPOP', 'test'))
605-
# r.assertIsNone(r.execute_command('JSON.ARRPOP', 'test'))
603+
r.assertEqual('2', r.execute_command('JSON.ARRPOP', 'test', '.', -99))
604+
r.assertEqual('3', r.execute_command('JSON.ARRPOP', 'test'))
605+
r.assertIsNone(r.execute_command('JSON.ARRPOP', 'test'))
606+
r.assertIsNone(r.execute_command('JSON.ARRPOP', 'test', '.'))
607+
r.assertIsNone(r.execute_command('JSON.ARRPOP', 'test', '.', 2))
606608

607609
def testTypeCommand(env):
608610
"""Test JSON.TYPE command"""

0 commit comments

Comments
 (0)