{"record":{"id":"7c574880073187b8","repo":"microsoft/semantic-kernel","slug":"use-of-name-node-id-is-not-allowed-in-filter-e-7c5748","errorCode":null,"errorMessage":"Use of name '{node.id}' is not allowed in filter expressions. Only the lambda parameter(s) ({', '.join(lambda_param_names)}) can be used.","messagePattern":"Use of name '(.+?)' is not allowed in filter expressions\\. Only the lambda parameter\\(s\\) \\((.+?)\\) can be used\\.","errorType":"exception","errorClass":"VectorStoreOperationException","httpStatus":null,"severity":"error","filePath":"python/semantic_kernel/connectors/in_memory.py","lineNumber":790,"sourceCode":"\n            node_type = type(node)\n\n            # Check if the node type is allowed\n            if node_type not in self.allowed_filter_ast_nodes:\n                raise VectorStoreOperationException(\n                    f\"AST node type '{node_type.__name__}' is not allowed in filter expressions.\"\n                )\n\n            # For Attribute nodes, validate that dangerous dunder attributes are not accessed\n            if isinstance(node, ast.Attribute) and node.attr in self.blocked_filter_attributes:\n                raise VectorStoreOperationException(\n                    f\"Access to attribute '{node.attr}' is not allowed in filter expressions. \"\n                    \"This attribute could be used to escape the filter sandbox.\"\n                )\n\n            # For Name nodes, only allow the lambda parameter\n            if isinstance(node, ast.Name) and node.id not in lambda_param_names:\n                raise VectorStoreOperationException(\n                    f\"Use of name '{node.id}' is not allowed in filter expressions. \"\n                    f\"Only the lambda parameter(s) ({', '.join(lambda_param_names)}) can be used.\"\n                )\n\n            # For Call nodes, validate that only allowed functions are called\n            if isinstance(node, ast.Call):\n                func_name: str\n                if isinstance(node.func, ast.Name):\n                    func_name = node.func.id\n                elif isinstance(node.func, ast.Attribute):\n                    func_name = node.func.attr\n                else:\n                    raise VectorStoreOperationException(\n                        f\"Call target node type '{type(node.func).__name__}' is not allowed in filter expressions. \"\n                        \"Only direct function and method calls are supported.\"\n                    )\n\n                if func_name not in self.allowed_filter_functions:","sourceCodeStart":772,"sourceCodeEnd":808,"githubUrl":"https://github.com/microsoft/semantic-kernel/blob/c028a0c7dc4f0814cdcbaba9d998f187a41197bf/python/semantic_kernel/connectors/in_memory.py#L772-L808","documentation":"Thrown by InMemoryCollection._parse_and_validate_filter (in_memory.py:790) while walking the AST of a string filter. The sandbox only permits references to the lambda's own parameter names; any other bare name is rejected so untrusted filter strings cannot reach globals or builtins. The offending name and the allowed parameter names are both included in the message.","triggerScenarios":"Passing VectorSearchOptions.filter (or _get_filtered_records) a string lambda that references an external symbol, e.g. \"lambda x: x.age > MIN_AGE\" where MIN_AGE is not a lambda parameter. A single-parameter lambda is the expected shape, so any second identifier fails the ast.Name check at in_memory.py:789.","commonSituations":"Trying to parameterize a string filter with a Python variable instead of a literal; copy-pasting a lambda that worked in a real Python scope; migrating a filter that used a module-level constant; forgetting that the sandbox has no globals namespace.","solutions":["Inline the value as a literal: \"lambda x: x.age > 18\" instead of referencing a bare name.","If you need parameterization, build the string with the literal substituted in (and keep it under max_filter_source_length=2048).","Prefer passing a Python callable (a real lambda object) in options.filter rather than a string; callables bypass AST validation entirely.","If the name must be allowed, subclass InMemoryCollection and extend validation, but never widen this for untrusted input."],"exampleFix":"# before\nMIN_AGE = 18\noptions = VectorSearchOptions(filter=\"lambda x: x.age > MIN_AGE\")\n\n# after\noptions = VectorSearchOptions(filter=\"lambda x: x.age > 18\")\n# or pass a callable (no AST sandbox):\noptions = VectorSearchOptions(filter=lambda x: x.age > MIN_AGE)","handlingStrategy":"validation","validationCode":"import ast\n\ndef validate_filter_names(filter_str: str, allowed_param_names: set[str]) -> list[str]:\n    tree = ast.parse(filter_str, mode=\"eval\")\n    problems = []\n    for node in ast.walk(tree):\n        if isinstance(node, ast.Name) and node.id not in allowed_param_names:\n            problems.append(node.id)\n    return problems\n\n# call before constructing VectorSearchOptions\nbad = validate_filter_names(\"lambda x: x.age > MIN_AGE\", {\"x\"})\nassert not bad, f\"filter references disallowed names: {bad}\"","typeGuard":"def is_safe_string_filter(filter_str: str) -> bool:\n    try:\n        tree = ast.parse(filter_str, mode=\"eval\")\n    except SyntaxError:\n        return False\n    if not (isinstance(tree, ast.Expression) and isinstance(tree.body, ast.Lambda)):\n        return False\n    params = {a.arg for a in tree.body.args.args}\n    return all(\n        not (isinstance(n, ast.Name) and n.id not in params)\n        for n in ast.walk(tree)\n    )","tryCatchPattern":"from semantic_kernel.exceptions.vector_store_exceptions import VectorStoreOperationException\n\ntry:\n    results = await collection.search(options)\nexcept VectorStoreOperationException as ex:\n    if \"not allowed in filter expressions\" in str(ex):\n        # fix the filter string and retry with a sanitized literal\n        ...","preventionTips":["Prefer passing a real Python lambda (callable) in options.filter instead of a string; callables bypass the AST sandbox.","Keep string filters to a single-parameter lambda referencing only that parameter.","Never interpolate external variable names into a string filter; inline their values as literals.","Validate untrusted filter strings with an AST walk before passing them to search."],"tags":["in-memory-collection","filter","sandbox","ast","validation"],"backgroundTag":null,"analyzedSha":"c028a0c7dc4f0814cdcbaba9d998f187a41197bf","analyzedAt":"2026-08-13T13:48:05.040Z","schemaVersion":2},"datasetVersion":"2026-08-13T14:17:21.547Z"}