deepset-ai/haystack · error · PipelineConnectError

'${sender_component_name}' does not have any output connecti

Error message

'${sender_component_name}' does not have any output connections. Please check that the output types of '${sender_component_name}.run' are set, for example by using the '@component.output_types' decorator.

What it means

Pipeline.connect() raises PipelineConnectError when the sender component exists but declares no output sockets, i.e. its run() method has no @component.output_types decorator (or it declares none). The pipeline cannot know what the component produces, so no connection can be established.

Source

Thrown at haystack/core/pipeline/base.py:633

        # Edges may be named explicitly by passing 'node_name.edge_name' to connect().
        sender_component_name, sender_socket_name = parse_connect_string(sender)
        receiver_component_name, receiver_socket_name = parse_connect_string(receiver)

        if sender_component_name == receiver_component_name:
            raise PipelineConnectError("Connecting a Component to itself is not supported.")

        # Get the nodes data.
        try:
            sender_sockets = self.graph.nodes[sender_component_name]["output_sockets"]
        except KeyError as exc:
            raise ValueError(f"Component named {sender_component_name} not found in the pipeline.") from exc
        try:
            receiver_sockets = self.graph.nodes[receiver_component_name]["input_sockets"]
        except KeyError as exc:
            raise ValueError(f"Component named {receiver_component_name} not found in the pipeline.") from exc

        if not sender_sockets:
            raise PipelineConnectError(
                f"'{sender_component_name}' does not have any output connections. "
                f"Please check that the output types of '{sender_component_name}.run' are set, "
                f"for example by using the '@component.output_types' decorator."
            )

        # If the name of either socket is given, get the socket
        sender_socket: OutputSocket | None = None
        if sender_socket_name:
            sender_socket = sender_sockets.get(sender_socket_name)
            if not sender_socket:
                raise PipelineConnectError(
                    f"'{sender}' does not exist. "
                    f"Output connections of {sender_component_name} are: "
                    + ", ".join([f"{name} (type {_type_name(socket.type)})" for name, socket in sender_sockets.items()])
                )

        receiver_socket: InputSocket | None = None
        if receiver_socket_name:

View on GitHub (pinned to e318778c9b)

Solutions

  1. Add @component.output_types(...) to the sender's run() method declaring its return types
  2. Ensure run() returns a dict whose keys match the declared output socket names
  3. If wrapping the component, decorate the actual run method being called
  4. Check that the decorated run() is the one registered (not overridden in a subclass without the decorator)

Example fix

// before
class MyComponent:
    def run(self, text: str):
        return {'out': text}
// after
class MyComponent:
    @component.output_types(out=str)
    def run(self, text: str):
        return {'out': text}
Defensive patterns

Strategy: validation

Validate before calling

comp = pipeline.get_component('sender')
assert getattr(comp, '__haystack_output__', None) and comp.__haystack_output__._sockets_dict, f"'sender' has no output sockets; decorate run() with @component.output_types"

Type guard

def has_output_sockets(component) -> bool:
    return bool(getattr(getattr(component, '__haystack_output__', None), '_sockets_dict', {}))

Try / catch

try:
    pipeline.connect(sender, receiver)
except PipelineConnectError as e:
    if 'does not have any output connections' in str(e):
        raise TypeError(f'{sender}.run must be decorated with @component.output_types') from e

Prevention

When it happens

Trigger: Calling pipeline.connect('sender', 'receiver') where the sender's run() method lacks the @component.output_types decorator, or a custom component class defines run() without decorated output types.

Common situations: Writing a custom Component and forgetting @component.output_types on run(); a subclass overriding run() and dropping the decorator; wrapping a legacy component that never set output types.

Related errors


AI-assisted analysis of deepset-ai/haystack@e318778c9b (2026-08-30). Data as JSON: /api/errors/813ac2a9cb1c07df. Report an issue: GitHub.