Python: Fix RedisJsonCollection.delete() not prefixing keys and add R…#13905
Python: Fix RedisJsonCollection.delete() not prefixing keys and add R…#13905daric93 wants to merge 4 commits intomicrosoft:mainfrom
Conversation
…edis vector store integration tests Signed-off-by: Daria Korenieva <daric2612@gmail.com>
There was a problem hiding this comment.
Automated Code Review
Reviewers: 4 | Confidence: 92%
✓ Correctness
The one-line fix in
redis.pyis correct and addresses a genuine bug:RedisJsonCollection._inner_deletewas not applying_get_redis_key()to keys before deletion, which would cause deletes to silently target the wrong keys whenprefix_collection_name_to_key_names=True. The siblingRedisHashsetCollection._inner_delete(line 581) already applies this transform, as doesRedisJsonCollection._inner_get(line 699), confirming this was an oversight. The new integration test file is well-structured and exercises the fixed code path (batch delete with prefix) along with other CRUD and search operations. No correctness issues found.
✓ Security Reliability
The one-line production fix in redis.py is correct and addresses a real bug:
RedisJsonCollection._inner_deletewas not applying_get_redis_key()to prefix the collection name to keys before deletion, unlike the hashset counterpart (line 581) and the JSON_inner_get(line 699). This could cause delete operations to silently fail (deleting non-existent unprefixed keys) whenprefix_collection_name_to_key_names=True. The new integration test file is well-structured, uses randomized collection names to avoid collisions, and properly cleans up resources infinallyblocks. No security or reliability issues found.
✓ Test Coverage
The one-line bug fix in
RedisJsonCollection._inner_deletecorrectly adds_get_redis_key()to prefix keys, matching the pattern already used in_inner_get(line 699) andRedisHashsetCollection._inner_delete(line 581). The new integration test file is comprehensive, covering batch CRUD, include_vectors, collection lifecycle, explicit index creation, and search with filters. The fix is functionally covered bytest_batch_upsert_get_deletewhich usesprefix_collection_name_to_key_names=True. However, there is no unit-level regression test that would have caught the original bug or prevent its reintroduction without requiring a running Redis server — the existingtest_deleteintest_redis_store.pyonly tests without prefix and doesn't assert on mock arguments.
✓ Design Approach
The one-line bug fix in
RedisJsonCollection._inner_deleteis correct and necessary._inner_get(line 699) and_serialize_dicts_to_store_models(line 723) already call_get_redis_keybefore issuing Redis commands, andRedisHashsetCollection._inner_delete(line 581) does too. The pre-fix_inner_deletewas the only Redis operation in the JSON collection that passed the raw application key instead of the prefixed Redis key, causing deletes to silently no-op wheneverprefix_collection_name_to_key_names=True. The fix is consistent with the established pattern. The integration test file is reasonable: the_SEARCH_XFAILmarkers are honestly documented with issue links, the fixture correctly tears down the collection insideasync with col:so the Redis connection is still open during cleanup, andtest_batch_upsert_get_deletecorrectly exercises the fixed code path withprefix_collection_name_to_key_names=True. The existing unit testtest_delete(line 273-276) used collections without the prefix option and did not assert which key was passed to the mock, which is why the bug was not caught earlier — but that is a pre-existing gap, not introduced by this PR.
Suggestions
- Add a unit test in
test_redis_store.pythat verifiesRedisJsonCollection._inner_deletecallsjson().deletewith the prefixed key whenprefix_collection_name_to_key_names=True(e.g.,await collection_with_prefix_json._inner_delete(['id1']); mock_delete_json.assert_called_once_with('test:id1', '$')). The existingtest_delete(line 274) only tests without prefix and doesn't assert mock arguments, which is why the original bug went unnoticed. Consider adding a symmetric test forRedisHashsetCollection._inner_deleteas well.
Automated review by daric93's agents
…bled (microsoft#13904) Signed-off-by: Daria Korenieva <daric2612@gmail.com>
…c93/microsoft-semantic-kernel into fix/python-redis-json-delete-prefix
Motivation and Context
Fixes #13904.
Tried to use the Redis connector and ran into issues — deletes with
prefix_collection_name_to_key_names=Truewere silently failing, and vector search didn't work at all. The existing integration tests only cover single-record upsert → get → delete with the default prefix setting (False) and never callcollection.search(), so these paths had zero test coverage. Added integration tests covering the full public surface and that's how these issues were found.This PR fixes the JSON delete bug and adds the test coverage. The vector search issues are tracked separately in #13896 and addressed by #13899.
Description
Bug fix —
RedisJsonCollection._inner_deletedoes not apply the collection-name prefix to keys before callingJSON.DEL. Whenprefix_collection_name_to_key_names=True, upsert stores keys as{collection_name}:{key}but delete sendsJSON.DEL {key}(without the prefix). The command targets a non-existent key, returns 0, and the record is never deleted. The hashset siblingRedisHashsetCollection._inner_deletecorrectly callsself._get_redis_key(key)— the JSON version was missing it.Test coverage — new file
python/tests/integration/memory/test_redis_vector_store.pywith 30 parametrised integration tests covering:ensure_collection_exists,collection_exists,ensure_collection_deleted)list_collection_names(FT._LIST)getwithinclude_vectors=True/Falseprefix_collection_name_to_key_names=Falseround-tripensure_collection_exists(index_definition=..., fields=...)ensure_collection_existswith invalid args,getwithout keys)include_vectors, tag/text filters (==,!=,and,or)14 of the 30 tests exercise vector search and are marked
xfailreferencing #13896 / #13899 — they will pass once that PR merges and thexfailmarkers can be removed.Tests require a running Redis server reachable via
REDIS_CONNECTION_STRING.Contribution Checklist