Skip to content

Python: Fix flaky deepcopy service tests using unpickleable async state#13456

Open
yash27-lab wants to merge 2 commits into
microsoft:mainfrom
yash27-lab:fix/python-sample-tests-lazy-import
Open

Python: Fix flaky deepcopy service tests using unpickleable async state#13456
yash27-lab wants to merge 2 commits into
microsoft:mainfrom
yash27-lab:fix/python-sample-tests-lazy-import

Conversation

@yash27-lab

Copy link
Copy Markdown

This PR fixes flaky kernel deepcopy tests caused by OpenAI async client
finalizers raising unraisable exceptions during garbage collection.

Instead of relying on external SDK behavior, the tests now use a minimal
unpickleable service (async generator / lambda) to deterministically
validate deepcopy and model_dump failure paths.

This makes the tests stable across Python versions and environments.
No production code changes; test-only fix.

@yash27-lab yash27-lab requested a review from a team as a code owner January 16, 2026 04:04
@moonbox3 moonbox3 added the python Pull requests for the Python Semantic Kernel label Jan 16, 2026
@github-actions github-actions Bot changed the title Fix flaky deepcopy service tests using unpickleable async state Python: Fix flaky deepcopy service tests using unpickleable async state Jan 16, 2026
@yash27-lab

Copy link
Copy Markdown
Author

@microsoft-github-policy-service agree

@moonbox3

Copy link
Copy Markdown
Collaborator

Python Test Coverage

Python Test Coverage Report •
FileStmtsMissCoverMissing
kernel.py2345875%149, 160, 164, 320–321, 323, 405, 411–412, 416–417, 470–474, 476–477, 490–499, 501, 503–504, 506–526, 528–533
TOTAL28063481282% 

Python Unit Test Overview

Tests Skipped Failures Errors Time
3787 23 💤 0 ❌ 0 🔥 1m 46s ⏱️

Copilot AI review requested due to automatic review settings April 8, 2026 02:03

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR updates Python unit tests to make Kernel deepcopy and model dump failure behavior deterministic by using an intentionally unpickleable service, instead of relying on OpenAI client finalization behavior during garbage collection.

Changes:

  • Replaced OpenAIChatCompletion usage in deepcopy and model dump failure tests with a minimal in test unpickleable service storing an async generator.
  • Removed inline comments that tied the failure to OpenAI client serialization behavior.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +1041 to +1051
class _UnserializableService:
service_id = "unserializable"

def __init__(self):
async def _agen():
yield "tick"

# Async generator objects are not deepcopy/pickle friendly.
self._bad = _agen()

kernel.add_service(_UnserializableService())

Copilot AI Apr 8, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Kernel.add_service is typed to accept AIServiceClientBase, but this test inserts a plain object. That can make model_dump(deep=True)/model_copy(deep=True) fail for reasons unrelated to the intended “unpickleable internal state” (for example, serializer/type handling of non-AIServiceClientBase values). Consider making _UnserializableService a minimal AIServiceClientBase subclass (with required ai_model_id and a field holding the async generator) so the failure is specifically attributable to the unpickleable state while staying within the API contract.

Copilot uses AI. Check for mistakes.
Comment on lines +1041 to +1067
class _UnserializableService:
service_id = "unserializable"

def __init__(self):
async def _agen():
yield "tick"

# Async generator objects are not deepcopy/pickle friendly.
self._bad = _agen()

kernel.add_service(_UnserializableService())

with pytest.raises(TypeError):
# This will fail because OpenAIChatCompletion is not serializable, more specifically,
# the client is not serializable
kernel.model_dump(deep=True)


def test_kernel_deep_copy_fail_with_services(kernel: Kernel):
open_ai_chat_completion = OpenAIChatCompletion(ai_model_id="abc", api_key="abc")
kernel.add_service(open_ai_chat_completion)
class _UnserializableService:
service_id = "unserializable"

def __init__(self):
async def _agen():
yield "tick"

# Async generator objects are not deepcopy/pickle friendly.
self._bad = _agen()

kernel.add_service(_UnserializableService())

Copilot AI Apr 8, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_UnserializableService is defined twice with identical logic. To reduce duplication and keep the two failure-path tests aligned over time, consider defining a single reusable helper (module-level class or small factory) and using it in both tests.

Copilot uses AI. Check for mistakes.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

python Pull requests for the Python Semantic Kernel

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants