BerriAI/litellm · error · ValueError

Both project_id and topic_id must be provided

Error message

Both project_id and topic_id must be provided

What it means

Pubsub.py raises ValueError when, after fallbacks, either project_id or topic_id is unresolved. The constructor accepts explicit project_id/topic_id arguments, falling back to GCS_PUBSUB_PROJECT_ID and GCS_PUBSUB_TOPIC_ID env vars; both must end up non-None. Note a premium-user check runs just before this, so enterprise licensing must already be in order.

Solutions

  1. Set both env vars: GCS_PUBSUB_PROJECT_ID and GCS_PUBSUB_TOPIC_ID.
  2. Or pass project_id= and topic_id= explicitly when constructing the Pubsub callback.
  3. Verify with printenv in the actual runtime environment.
  4. Remember GCS_PATH_SERVICE_ACCOUNT is optional only if default vertex auth works; project/topic are never optional.

Example fix

# before
# only GCS_PUBSUB_TOPIC_ID set

# after
export GCS_PUBSUB_PROJECT_ID=my-gcp-project
export GCS_PUBSUB_TOPIC_ID=litellm-logs
Defensive patterns

Strategy: validation

Validate before calling

import os

project = project_id or os.getenv('GCS_PUBSUB_PROJECT_ID')
topic = topic_id or os.getenv('GCS_PUBSUB_TOPIC_ID')
if not project or not topic:
    raise SystemExit('Both GCS_PUBSUB_PROJECT_ID and GCS_PUBSUB_TOPIC_ID (or constructor args) are required')

Type guard

def pubsub_resolved(project_id: str | None, topic_id: str | None) -> bool:
    return bool(project_id or os.getenv('GCS_PUBSUB_PROJECT_ID')) and bool(topic_id or os.getenv('GCS_PUBSUB_TOPIC_ID'))

Try / catch

try:
    Pubsub(project_id=project, topic_id=topic)
except ValueError as e:
    if 'project_id and topic_id' in str(e):
        raise ConfigError('Set GCS_PUBSUB_PROJECT_ID and GCS_PUBSUB_TOPIC_ID') from e
    raise

Prevention

When it happens

Trigger: Registering the GCS Pub/Sub callback with neither constructor args nor GCS_PUBSUB_PROJECT_ID/GCS_PUBSUB_TOPIC_ID set; setting only one of the two env vars; typo'd variable names in the deployment manifest.

Common situations: Enabling pubsub logging from docs that show only one variable; k8s secret mounted with the wrong key names; splitting project/topic across different config mechanisms and one not loading.

Understand the failure class

Background: "X is required", "must be set", "cannot be empty": the missing-required-config error family, from Vertex AI project/location to WeChat keys — this error's family across 18 libraries.

Related errors


AI-assisted analysis of BerriAI/litellm@77b7c6c40c (2026-08-18). Data as JSON: /api/errors/153040a7b26fe47f. Report an issue: GitHub.

Appendix: source

Thrown at litellm/integrations/gcs_pubsub/pub_sub.py:58

        Initialize Google Cloud Pub/Sub publisher

        Args:
            project_id (str): Google Cloud project ID
            topic_id (str): Pub/Sub topic ID
            credentials_path (str, optional): Path to Google Cloud credentials JSON file
        """
        from litellm.proxy.utils import _premium_user_check

        _premium_user_check()

        self.async_httpx_client = get_async_httpx_client(llm_provider=httpxSpecialProvider.LoggingCallback)

        self.project_id = project_id or os.getenv("GCS_PUBSUB_PROJECT_ID")
        self.topic_id = topic_id or os.getenv("GCS_PUBSUB_TOPIC_ID")
        self.path_service_account_json = credentials_path or os.getenv("GCS_PATH_SERVICE_ACCOUNT")

        if not self.project_id or not self.topic_id:
            raise ValueError("Both project_id and topic_id must be provided")

        self.flush_lock = asyncio.Lock()
        super().__init__(**kwargs, flush_lock=self.flush_lock)
        asyncio.create_task(self.periodic_flush())
        self.log_queue: list[SpendLogsPayload | StandardLoggingPayload] = []

    async def construct_request_headers(self) -> dict[str, str]:
        """Construct authorization headers using Vertex AI auth"""
        from litellm import vertex_chat_completion

        (
            _auth_header,
            vertex_project,
        ) = await vertex_chat_completion._ensure_access_token_async(
            credentials=self.path_service_account_json,
            project_id=self.project_id,
            custom_llm_provider="vertex_ai",
        )

View on GitHub (pinned to 77b7c6c40c)