Skip to content

Python: fix(sqlserver): handle None and boolean expressions in SqlServerCollection lambda parser - #14687

Open
MOHAMMED WASIM KHAN (wasim-builds) wants to merge 1 commit into
microsoft:mainfrom
wasim-builds:fix/sql-server-null-filter
Open

MOHAMMED WASIM KHAN (wasim-builds) wants to merge 1 commit into
microsoft:mainfrom
wasim-builds:fix/sql-server-null-filter

Conversation

@wasim-builds

Copy link
Copy Markdown
Contributor

Summary

Closes #14683

SqlServerCollection._lambda_parser rendered None comparisons as [field] = ? or [field] <> ? binding the string literal 'None'. Because SQL Server evaluates equality with NULL under ANSI_NULLS ON as UNKNOWN, search filters targeting None could never match NULL rows. In addition:

  • ast.Is and ast.IsNot raised NotImplementedError: Unsupported operator: <class 'ast.Is'> on x.tenant is None and x.tenant is not None.
  • Booleans were bound as string 'True' / 'False' instead of '1' / '0' (which is expected by SQL Server BIT columns and is already used by _cast_value).
  • Omitted search arguments in default_dynamic_filter_function generating lambda x: x.tenant == None bound 'None' as a query parameter.

Changes

  1. SqlServerCollection._lambda_parser:
    • Inspect comparison operators (ast.Eq, ast.NotEq, ast.Is, ast.IsNot).
    • Normalize operands so if left_node is ast.Constant with value is None, it swaps left_node and right_node.
    • When comparing against None:
      • If both sides are scalar constants, evaluate to T-SQL (1 = 1) or (1 = 0).
      • Otherwise, render [column] IS NULL (for ast.Eq, ast.Is) or [column] IS NOT NULL (for ast.NotEq, ast.IsNot) without appending any parameter to command.parameters.
      • Raise NotImplementedError if ast.Is or ast.IsNot is used with a non-None operand.
    • In case ast.Constant():, bind booleans as '1' if True else '0' to match _cast_value and SQL Server BIT semantics.
    • Avoid double-parsing right_node across comparison operator branches.
  2. Unit Tests:
    • Added parameterized test_null_filter_parser in tests/unit/connectors/memory/test_sql_server.py covering 28 cases mirroring Postgres null filter parser tests (== None, != None, is None, is not None, reversed comparisons, constant truth evaluation, compound boolean expressions, boolean bindings '1'/'0', and string 'None').
    • Added test_null_filter_query_parameter_order verifying SELECT query parameter alignment when combining null filters with vector and range filters.
    • Added test_dynamic_null_filter verifying default_dynamic_filter_function(tenant=None) generates [tenant] IS NULL without parameters.
    • Added test_unsupported_is_operator verifying unsupported is comparisons raise NotImplementedError.

Verification

  • uv run pytest tests/unit/connectors/memory/test_sql_server.py (73 passed in 0.16s).
  • uv run ruff check tests/unit/connectors/memory/test_sql_server.py semantic_kernel/connectors/sql_server.py (all checks passed).
  • uv run ruff format --check tests/unit/connectors/memory/test_sql_server.py semantic_kernel/connectors/sql_server.py (all formatted).

… SqlServerCollection

- Map comparisons against None (ast.Eq, ast.NotEq, ast.Is, ast.IsNot) to IS NULL / IS NOT NULL without binding parameter
- Support scalar constant comparisons against None evaluated to T-SQL (1 = 1) or (1 = 0)
- Bind booleans as '1' or '0' matching _cast_value and SQL Server BIT column type
- Add comprehensive unit tests mirroring Postgres test_null_filter_parser

Closes microsoft#14683

Signed-off-by: Wasim <wasim143mr@gmail.com>
Copilot AI balanced review requested due to automatic review settings October 29, 2026 19:46

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.

Copilot was unable to review this pull request because the user who requested the review has insufficient remaining quota.

@semantic-kernel-automation semantic-kernel-automation Bot added the python Pull requests for the Python Semantic Kernel label Oct 29, 2026

This branch was successfully deployed

1 active deployment
github-app-auth — 19a6aad9 Deployed Oct 29, 2026 by wasim-builds via add_label #29494
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.

Python: Bug: SqlServerCollection renders x.tenant == None as [tenant] = ? with the string 'None' instead of IS NULL

2 participants