Skip to content

Commit

Permalink
Get command keys for subcommands (#2170)
Browse files Browse the repository at this point in the history
* parse subcommands

* fix tests
  • Loading branch information
dvora-h authored May 8, 2022
1 parent faf55b6 commit 883fca7
Show file tree
Hide file tree
Showing 5 changed files with 32 additions and 3 deletions.
4 changes: 4 additions & 0 deletions redis/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -553,6 +553,10 @@ def parse_command(response, **options):
cmd_dict["first_key_pos"] = command[3]
cmd_dict["last_key_pos"] = command[4]
cmd_dict["step_count"] = command[5]
if len(command) > 7:
cmd_dict["tips"] = command[7]
cmd_dict["key_specifications"] = command[8]
cmd_dict["subcommands"] = command[9]
commands[cmd_name] = cmd_dict
return commands

Expand Down
1 change: 1 addition & 0 deletions redis/cluster.py
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,7 @@ class AbstractRedisCluster:
[
"ACL CAT",
"ACL DELUSER",
"ACL DRYRUN",
"ACL GENPASS",
"ACL GETUSER",
"ACL HELP",
Expand Down
26 changes: 25 additions & 1 deletion redis/commands/parser.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,21 @@ def initialize(self, r):
commands[cmd.lower()] = commands.pop(cmd)
self.commands = commands

def parse_subcommand(self, command, **options):
cmd_dict = {}
cmd_name = str_if_bytes(command[0])
cmd_dict["name"] = cmd_name
cmd_dict["arity"] = int(command[1])
cmd_dict["flags"] = [str_if_bytes(flag) for flag in command[2]]
cmd_dict["first_key_pos"] = command[3]
cmd_dict["last_key_pos"] = command[4]
cmd_dict["step_count"] = command[5]
if len(command) > 7:
cmd_dict["tips"] = command[7]
cmd_dict["key_specifications"] = command[8]
cmd_dict["subcommands"] = command[9]
return cmd_dict

# As soon as this PR is merged into Redis, we should reimplement
# our logic to use COMMAND INFO changes to determine the key positions
# https://github.com/redis/redis/pull/8324
Expand Down Expand Up @@ -72,8 +87,17 @@ def get_keys(self, redis_conn, *args):
and command["first_key_pos"] == 0
and command["last_key_pos"] == 0
):
is_subcmd = False
if "subcommands" in command:
subcmd_name = f"{cmd_name}|{args[1].lower()}"
for subcmd in command["subcommands"]:
if str_if_bytes(subcmd[0]) == subcmd_name:
command = self.parse_subcommand(subcmd)
is_subcmd = True

# The command doesn't have keys in it
return None
if not is_subcmd:
return None
last_key_pos = command["last_key_pos"]
if last_key_pos < 0:
last_key_pos = len(args) - abs(last_key_pos)
Expand Down
1 change: 0 additions & 1 deletion tests/test_cluster.py
Original file line number Diff line number Diff line change
Expand Up @@ -1121,7 +1121,6 @@ def test_cluster_links(self, r):
links_to = sum(x.count("to") for x in res)
links_for = sum(x.count("from") for x in res)
assert links_to == links_for
print(res)
for i in range(0, len(res) - 1, 2):
assert res[i][3] == res[i + 1][3]

Expand Down
3 changes: 2 additions & 1 deletion tests/test_commands.py
Original file line number Diff line number Diff line change
Expand Up @@ -1164,7 +1164,7 @@ def test_expire_option_xx(self, r):
r.set("key", "val")
assert r.expire("key", 100, xx=True) == 0
assert r.expire("key", 100)
assert r.expire("key", 500, nx=True) == 1
assert r.expire("key", 500, xx=True) == 1

@skip_if_server_version_lt("7.0.0")
def test_expire_option_gt(self, r):
Expand Down Expand Up @@ -3012,6 +3012,7 @@ def test_sort_all_options(self, r):
assert r.lrange("sorted", 0, 10) == [b"vodka", b"milk", b"gin", b"apple juice"]

@skip_if_server_version_lt("7.0.0")
@pytest.mark.onlynoncluster
def test_sort_ro(self, r):
r["score:1"] = 8
r["score:2"] = 3
Expand Down

0 comments on commit 883fca7

Please sign in to comment.