Skip to content

6. How to use Connection API

Wen Zhou edited this page Oct 24, 2025 · 2 revisions

How to use Connection API

This guide provides detailed examples for using the Connection API across different workload types and connection protocols.

Overview

The Connection API allows you to manage connections to external data sources and services in OpenShift AI. Connections are stored as Kubernetes Secrets with standardized annotations that enable protocol-based validation and routing.

Supported Connection Types (as of 3.0):

  • s3: S3-compatible object storage
  • uri: Public HTTP/HTTPS URIs
  • oci: OCI-compliant container registries

Supported Workloads (as of 3.0):

  • Notebook (Workbenches)
  • InferenceService (Model Serving)
  • LLMInferenceService (LLM Model Serving)

Connection Secret Structure

All connections follow this basic structure:

apiVersion: v1
kind: Secret
metadata:
  name: <connection-name>
  namespace: <your-namespace>
  annotations:
    opendatahub.io/connection-type-protocol: "<protocol>"  # Required: s3, uri, or oci
type: Opaque
data:
  # Protocol-specific fields (base64-encoded)

S3 Connection Examples

Creating an S3 Connection

apiVersion: v1
kind: Secret
metadata:
  name: my-s3-connection
  namespace: my-project
  annotations:
    opendatahub.io/connection-type-protocol: "s3"
type: Opaque
stringData:
  AWS_S3_ENDPOINT: "https://s3.example.com"
  AWS_S3_BUCKET: "my-bucket"
  AWS_ACCESS_KEY_ID: "my-access-key"
  AWS_SECRET_ACCESS_KEY: "my-secret-key"

Required Fields for S3:

Optional Fields:

  • AWS_DEFAULT_REGION: AWS region (e.g., "us-east-1")

Using S3 Connection with Notebook

apiVersion: kubeflow.org/v1
kind: Notebook
metadata:
  name: my-workbench
  namespace: my-project
  annotations:
    # Notebooks support multiple connections via comma-separated list
    opendatahub.io/connections: 'my-project/my-s3-connection'
spec:
  template:
    spec:
      containers:
      - name: notebook
        image: quay.io/opendatahub/workbench-images:jupyter-minimal-ubi9-python-3.11
        # Connection credentials are automatically mounted as environment variables

Using S3 Connection with InferenceService

apiVersion: serving.kserve.io/v1beta1
kind: InferenceService
metadata:
  name: my-model
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-s3-connection'
    opendatahub.io/connection-path: 'my-bucket-path'  # Optional: specify path within S3 bucket
spec:
  predictor:
    model:
      modelFormat:
        name: pytorch
      # .spec.predictor.model.storageUri is automatically injected by the operator based on the connection
      # Example: .spec.predictor.model.storageUri: s3://my-bucket/my-bucket-path

Using S3 Connection with LLMInferenceService

apiVersion: serving.kserve.io/v1alpha1
kind: LLMInferenceService
metadata:
  name: my-llm-model
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-s3-connection'
    opendatahub.io/connection-path: 'my-bucket-path'  # Optional: specify path within S3 bucket
spec:
  model:
    # .spec.model.uri is automatically injected by the operator based on the connection
    # Example: .spec.model.uri: s3://my-bucket/my-bucket-path

URI Connection Examples

Creating a URI Connection

apiVersion: v1
kind: Secret
metadata:
  name: my-uri-connection
  namespace: my-project
  annotations:
    opendatahub.io/connection-type-protocol: "uri"
type: Opaque
stringData:
  URI: "https://example.com/models/my-model.tar.gz"

Required Fields for URI:

  • URI: HTTP/HTTPS URL to the resource

Note: HuggingFace URIs (hf://) are treated as URI protocol connections.

Using URI Connection with Notebook

apiVersion: kubeflow.org/v1
kind: Notebook
metadata:
  name: my-workbench
  namespace: my-project
  annotations:
    # Multiple connections example
    opendatahub.io/connections: 'my-project/my-s3-connection,my-project/my-uri-connection'
spec:
  template:
    spec:
      containers:
      - name: notebook
        image: quay.io/opendatahub/workbench-images:jupyter-minimal-ubi9-python-3.11

Using URI Connection with InferenceService

apiVersion: serving.kserve.io/v1beta1
kind: InferenceService
metadata:
  name: my-model
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-uri-connection'
spec:
  predictor:
    model:
      modelFormat:
        name: sklearn
      # .spec.predictor.model.storageUri is automatically injected by the operator based on the connection
      # Example: .spec.predictor.model.storageUri: https://example.com/models/my-model.tar.gz

Using URI Connection with LLMInferenceService

apiVersion: serving.kserve.io/v1alpha1
kind: LLMInferenceService
metadata:
  name: my-llm-model
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-uri-connection'
spec:
  model:
    # .spec.model.uri is automatically injected by the operator based on the connection
    # Example: .spec.model.uri: https://example.com/models/llm-model

OCI Connection Examples

Creating an OCI Connection

apiVersion: v1
kind: Secret
metadata:
  name: my-oci-connection
  namespace: my-project
  annotations:
    opendatahub.io/connection-type-protocol: "oci"
type: kubernetes.io/dockerconfigjson
data:
  .dockerconfigjson: <base64-encoded-docker-config>
  OCI_HOST: <base64-encoded-registry-url>  # Example: http://quay.io/<org>

Required Fields for OCI:

  • .dockerconfigjson: Docker config JSON with registry authentication (base64-encoded)
  • OCI_HOST: Registry host URL with organization (base64-encoded, e.g., "http://quay.io/my-org")

Example .dockerconfigjson content (before base64 encoding):

{
  "auths": {
    "quay.io": {
      "auth": "<base64-encoded-username:password>"
    }
  }
}

Using OCI Connection with Notebook

apiVersion: kubeflow.org/v1
kind: Notebook
metadata:
  name: my-workbench
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-project/my-oci-connection'
spec:
  template:
    spec:
      containers:
      - name: notebook
        image: quay.io/opendatahub/workbench-images:jupyter-minimal-ubi9-python-3.11

Using OCI Connection with InferenceService

apiVersion: serving.kserve.io/v1beta1
kind: InferenceService
metadata:
  name: my-model
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-oci-connection'
spec:
  predictor:
    model:
      modelFormat:
        name: pytorch
      # .spec.predictor.model.storageUri is automatically injected by the operator based on the connection
      # Example: .spec.predictor.model.storageUri: oci://quay.io/my-org/my-model:latest
    # The operator webhook also creates and injects .spec.predictor.imagePullSecrets for OCI authentication

Using OCI Connection with LLMInferenceService

apiVersion: serving.kserve.io/v1alpha1
kind: LLMInferenceService
metadata:
  name: my-llm-model
  namespace: my-project
  annotations:
    opendatahub.io/connections: 'my-oci-connection'
spec:
  # The operator webhook automatically injects imagePullSecrets for OCI authentication
  # Example: .spec.template.imagePullSecrets[].name set to the connection secret name

Connection Annotation Format by Workload Type

Notebook

  • Format: Comma-separated list with namespace/name format
  • Multiple Connections: ✅ Supported
  • Example:
    opendatahub.io/connections: 'my-project/connection1,my-project/connection2'

InferenceService and LLMInferenceService

  • Format: Connection name as string
  • Multiple Connections: ❌ Single connection only
  • Example:
    opendatahub.io/connections: 'my-connection'
  • Optional Annotation (S3 connections only):
    opendatahub.io/connection-path: 'my-bucket-path'  # Specify path within S3 bucket

Important Notes

Namespace Isolation

  • Connections are scoped to their namespace
  • Resources can only access connections in the same namespace
  • Cross-namespace access is not supported

RBAC Requirements

  • Users need Secret read/write permissions in their namespace to create/manage connections
  • Workload ServiceAccounts need Secret read permissions to consume connections

ServiceAccount Creation and Injection

For S3 connections, the operator automatically creates and injects a ServiceAccount:

  • ServiceAccount Name: Connection Secret name with -sa suffix (e.g., my-s3-connection-sa)
  • Purpose: Used for accessing S3 storage with the connection credentials
  • Automatic Creation: The ServiceAccount is created in the same namespace as the connection Secret
  • Automatic Linking: The ServiceAccount is automatically linked to the S3 connection Secret
  • Automatic Injection: The operator webhook automatically injects this ServiceAccount into:
    • .spec.predictor.serviceAccountName for InferenceService
    • .spec.template.serviceAccountName for LLMInferenceService

Validation Behavior

  • Webhook validation is advisory, not restrictive
  • Invalid connections won't block Secret creation
  • Invalid connections will cause workload failures at runtime
  • Always validate your connection credentials before deploying workloads

Migration from 2.16 to 3.0

If you have existing connections using the 2.16 annotation format:

Old format (2.16, deprecated but still supported):

annotations:
  opendatahub.io/connection-type-ref: "s3"

New format (3.0, recommended):

annotations:
  opendatahub.io/connection-type-protocol: "s3"

Both annotations are supported in 3.0, with connection-type-protocol taking precedence. For new connections, always use connection-type-protocol.

Clone this wiki locally