PrefectHQ/fastmcp · error · ValueError

Required function arguments {required_params} must be a subs

Error message

Required function arguments {required_params} must be a subset of the URI path parameters {path_params}

What it means

Required function parameters (no default) must be satisfiable from the URI path, because path parameters are always present when the template matches. If a required parameter isn't in the path, there is no guaranteed source for it (query params are optional), so registration fails.

Source

Thrown at fastmcp_slim/fastmcp/resources/template.py:522

        optional_params = {
            p
            for p in func_params
            if user_sig.parameters[p].default is not inspect.Parameter.empty
            and user_sig.parameters[p].kind != inspect.Parameter.VAR_KEYWORD
        }

        # Validate RFC 6570 query parameters
        # Query params must be optional (have defaults)
        if query_params:
            invalid_query_params = query_params - optional_params
            if invalid_query_params:
                raise ValueError(
                    f"Query parameters {invalid_query_params} must be optional function parameters with default values"
                )

        # Check if required parameters are a subset of the path parameters
        if not required_params.issubset(path_params):
            raise ValueError(
                f"Required function arguments {required_params} must be a subset of the URI path parameters {path_params}"
            )

        # Check if all URI parameters are valid function parameters (skip if **kwargs present)
        if not any(
            param.kind == inspect.Parameter.VAR_KEYWORD
            for param in sig.parameters.values()
        ):
            if not all_uri_params.issubset(func_params):
                raise ValueError(
                    f"URI parameters {all_uri_params} must be a subset of the function arguments: {func_params}"
                )

        description = description if description is not None else inspect.getdoc(fn)

        # if the fn is a callable class, we need to get the __call__ method from here out
        if not inspect.isroutine(fn) and not isinstance(fn, functools.partial):
            fn = fn.__call__

View on GitHub (pinned to 1f02114297)

Solutions

  1. Add the parameter to the URI path: uri_template="data://{key}/{locale}"
  2. Give the parameter a default value and (optionally) expose it as a query parameter
  3. Remove the parameter from the function signature if it's unused

Example fix

// before
def get(key: str, locale: str): ...
ResourceTemplate.from_function(get, uri_template="data://{key}")
// after
def get(key: str, locale: str = "en"): ...
ResourceTemplate.from_function(get, uri_template="data://{key}?locale={locale}")
Defensive patterns

Strategy: validation

Validate before calling

import inspect, re
def check_required_in_path(fn, uri_template):
    path = uri_template.split("?", 1)[0]
    path_params = {p.replace("-", "_") for p in re.findall(r"\{(\w[-\w]*)\}", path)}
    required = {n for n, p in inspect.signature(fn).parameters.items()
                if p.default is inspect.Parameter.empty
                and p.kind in (inspect.Parameter.POSITIONAL_OR_KEYWORD, inspect.Parameter.KEYWORD_ONLY)}
    if not required <= path_params:
        raise TypeError(f"required {required - path_params} missing from path")

Type guard

def required_in_path(fn, uri_template) -> bool:
    import inspect, re
    path = uri_template.split("?", 1)[0]
    pp = {p.replace("-", "_") for p in re.findall(r"\{(\w[-\w]*)\}", path)}
    req = {n for n, p in inspect.signature(fn).parameters.items()
           if p.default is inspect.Parameter.empty}
    return req <= pp

Try / catch

try:
    tpl = FunctionResourceTemplate.from_function(fn, uri_template=uri)
except ValueError as e:
    if "must be a subset of the URI path" in str(e):
        raise TypeError(f"Add missing path placeholders to {uri!r} or give the params defaults") from e
    raise

Prevention

When it happens

Trigger: Registering a template where a required function parameter appears neither in the path placeholders nor with a default - e.g. def fn(key: str, locale: str) with uri_template="data://{key}".

Common situations: Forgetting to include a parameter in the URI template after adding it to the function; copy-pasting a function from another template; server-injected params misread as user-facing (those are excluded automatically).

Related errors


AI-assisted analysis of PrefectHQ/fastmcp@1f02114297 (2026-08-29). Data as JSON: /api/errors/abfa680fcc514ece. Report an issue: GitHub.