{"record":{"id":"f1eb277b64ef6716","repo":"pandas-dev/pandas","slug":"must-provide-func-or-named-aggregation-kwargs","errorCode":null,"errorMessage":"Must provide 'func' or named aggregation **kwargs.","messagePattern":"Must provide 'func' or named aggregation \\*\\*kwargs\\.","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"pandas/core/apply.py","lineNumber":2317,"sourceCode":"        List of user-provided keys.\n    func : List[Union[str, callable[...,Any]]]\n        List of user-provided aggfuncs\n\n    Examples\n    --------\n    >>> validate_func_kwargs({\"one\": \"min\", \"two\": \"max\"})\n    (['one', 'two'], ['min', 'max'])\n    \"\"\"\n    tuple_given_message = \"func is expected but received {} in **kwargs.\"\n    columns = list(kwargs)\n    func = []\n    for col_func in kwargs.values():\n        if not (isinstance(col_func, str) or callable(col_func)):\n            raise TypeError(tuple_given_message.format(type(col_func).__name__))\n        func.append(col_func)\n    if not columns:\n        no_arg_message = \"Must provide 'func' or named aggregation **kwargs.\"\n        raise TypeError(no_arg_message)\n    return columns, func\n\n\ndef include_axis(op_name: Literal[\"agg\", \"apply\"], colg: Series | DataFrame) -> bool:\n    return isinstance(colg, ABCDataFrame) or (\n        isinstance(colg, ABCSeries) and op_name == \"agg\"\n    )\n","sourceCodeStart":2299,"sourceCodeEnd":2325,"githubUrl":"https://github.com/pandas-dev/pandas/blob/3b7651241d4da534b3559b60ef128e1c34f54116/pandas/core/apply.py#L2299-L2325","documentation":"TypeError raised in validate_func_kwargs when no kwargs at all are passed to a code path that requires named aggregation. With no columns and no funcs the aggregation cannot proceed.","triggerScenarios":"Internal callers reaching validate_func_kwargs with an empty kwargs dict; df.agg(**{}) style invocations; selecting an aggregation spec that resolves to no columns.","commonSituations":"Dynamic code that builds kwargs from a dict comprehension which can yield nothing when the input list is empty.","solutions":["Ensure at least one column->function entry exists in kwargs before calling.","Fall back to a positional func when the kwargs dict is empty.","Guard upstream: if not kwargs: return early or use a default function."],"exampleFix":"# before\ndf.agg(**{})\n# after\ndf.agg('sum')","handlingStrategy":"validation","validationCode":"def safe_named_agg(obj, kwargs):\n    if not kwargs:\n        raise ValueError('named aggregation requires at least one column->func entry')\n    return obj.agg(**kwargs)","typeGuard":null,"tryCatchPattern":"try:\n    df.agg(**kwargs)\nexcept TypeError as e:\n    if 'named aggregation' in str(e):\n        df.agg('sum')  # fallback\n    else:\n        raise","preventionTips":["Short-circuit the call when the kwargs dict is empty.","Build kwargs from a non-empty source list and assert non-empty upstream."],"tags":["agg","validation","named-aggregation"],"backgroundTag":null,"analyzedSha":"3b7651241d4da534b3559b60ef128e1c34f54116","analyzedAt":"2026-08-11T22:10:44.015Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}