xtekky/gpt4free · error · ValueError

RotatedProvider requires a non-empty list of providers.

Error message

RotatedProvider requires a non-empty list of providers.

What it means

ValueError from RotatedProvider.__init__: constructed with something that is not a non-empty list (wrong type or empty list). RotatedProvider is the round-robin base used by retry providers; it refuses to start with nothing to rotate through. The check is isinstance(providers, list) and len > 0, so tuples/None/generators are rejected too.

Source

Thrown at g4f/providers/retry_provider.py:63

class RotatedProvider(BaseRetryProvider):
    """
    A provider that rotates through a list of providers, attempting one provider per
    request and advancing to the next one upon failure. This distributes load and
    retries across multiple providers in a round-robin fashion.
    """

    def __init__(
        self, providers: List[Type[BaseProvider]], shuffle: bool = True
    ) -> None:
        """
        Initialize the RotatedProvider.
        Args:
            providers (List[Type[BaseProvider]]): A non-empty list of providers to rotate through.
            shuffle (bool): If True, shuffles the provider list once at initialization
                            to randomize the rotation order.
        """
        if not isinstance(providers, list) or len(providers) == 0:
            raise ValueError("RotatedProvider requires a non-empty list of providers.")

        self.providers = providers
        if shuffle:
            random.shuffle(self.providers)

        self.current_index = 0
        self.last_provider: Type[BaseProvider] = None

    def _get_current_provider(self) -> Type[BaseProvider]:
        """Gets the provider at the current index."""
        p = self.providers[self.current_index]
        if isinstance(p, str):
            from ..Provider import __getattr__

            p = __getattr__(p)
        return p

    def _rotate_provider(self) -> None:

View on GitHub (pinned to 973504e177)

Solutions

  1. Ensure the argument is a non-empty Python list of provider classes before constructing.
  2. If the list is built dynamically, guard: providers = [p for p in candidates if ...]; assert providers before use.
  3. Convert tuples/generators with list(...) before passing.
  4. If zero providers is legitimate in your flow, skip constructing the RotatedProvider rather than passing an empty list.

Example fix

# before
rp = RetryProvider([p for p in providers if p.working])  # may be empty

# after
selected = [p for p in providers if p.working]
if not selected:
    raise ValueError('no working providers configured')
rp = RetryProvider(selected)
Defensive patterns

Strategy: validation

Validate before calling

if not isinstance(providers, list) or not providers:
    raise ValueError('need a non-empty list of provider classes')
rp = RotatedProvider(list(providers))

Type guard

def is_valid_provider_list(providers) -> bool:
    return isinstance(providers, list) and len(providers) > 0

Prevention

When it happens

Trigger: Programmatically building RotatedProvider (or a subclass like RetryProvider) with providers=[], a tuple of providers, or None — typically when the caller filters a provider list and the filter removes everything.

Common situations: Dynamic provider lists filtered by working/needs_auth flags that yield zero results; passing a generator expression (already consumed or not a list); refactor changing a list literal to a tuple.

Related errors


AI-assisted analysis of xtekky/gpt4free@973504e177 (2026-08-14). Data as JSON: /api/errors/a2ecf1a19c04467e. Report an issue: GitHub.