Python

Lekko Python SDK

⚠️

This page is under construction. A new major version of the Python SDK with code transformations and full GitHub integration is on our roadmap, so stay tuned!

This page explains how to use the Python SDK to read configurations from the Lekko backend.

Install

In your terminal, run the following to install the Lekko Python SDK:

pip install lekko_client

Initialize a cached Lekko client

Create a client that fetches and caches configurations from the Lekko backend. The configurations are kept updated through polling.

import lekko_client
 
lekko_client.initialize(lekko_client.CachedServerConfig(
    owner_name="REPOSITORY_OWNER",
    repo_name="REPOSITORY_NAME",
    api_key="LEKKO_API_KEY",    # Optional - defaults to "LEKKO_API_KEY" ENV var
    lekko_uri="URI",            # Optional - defaults to "prod.api.lekko.dev:443"
    context={},                 # Optional - additional context for each request
))
 
str_config = lekko_client.get_string("my_namespace", "my_config", {"context_key": "context_val"})

Replace the following:

  • LEKKO_API_KEY is your Lekko API key.
  • REPOSITORY_OWNER is the owner of the Lekko config repository.
  • REPOSITORY_NAME is the name of the Lekko config repository.

Use cached client with Git mode

Create a client that reads and caches configurations from a local Git repository. Configurations are updated via a file watcher.

import lekko_client
 
lekko_client.initialize(lekko_client.CachedGitConfig(
    owner_name="REPOSITORY_OWNER",
    repo_name="REPOSITORY_NAME",
    git_repo_path="GIT_REPO_PATH",
    api_key="LEKKO_API_KEY",    # Optional - defaults to "LEKKO_API_KEY" ENV var
    lekko_uri="URI",            # Optional - defaults to "prod.api.lekko.dev:443"
    context={},                 # Optional - additional context for each request
))
 
str_config = lekko_client.get_string("my_namespace", "my_config", {"context_key": "context_val"})

Replace the following:

  • LEKKO_API_KEY is your Lekko API key.
  • REPOSITORY_OWNER is the owner of the Lekko config repository.
  • REPOSITORY_NAME is the name of the Lekko config repository.

Use client for remote evaluation

Create a client that communicates with the Lekko API or a Lekko sidecar for remote evaluation.

import lekko_client
 
lekko_client.initialize(lekko_client.APIConfig(  # Or use lekko_client.SidecarConfig
    owner_name="REPOSITORY_OWNER",
    repo_name="REPOSITORY_NAME",
    api_key="LEKKO_API_KEY",    # Optional - defaults to "LEKKO_API_KEY" ENV var
    context={},                 # Optional - additional context for each request
))
 
str_config = lekko_client.get_string("my_namespace", "my_config", {"context_key": "context_val"})

Replace the following:

  • LEKKO_API_KEY is your Lekko API key.
  • REPOSITORY_OWNER is the owner of the Lekko config repository.
  • REPOSITORY_NAME is the name of the Lekko config repository.

Manage client lifecycle

To initialize the client, call lekko_client.initialize() at the start of your app, such as during the setup of a Flask app or within FastAPI’s lifecycle context manager.

To close the app, call lekko_client.close() during app shutdown to ensure all events are tracked and the client is properly deregistered.

Alternatively, to manage the client lifecycle manually, instantiate clients directly from lekko_client.clients and use them as needed.

from lekko_client.clients import APIClient
 
client = APIClient(
    owner_name="REPOSITORY_OWNER",
    repo_name="REPOSITORY_NAME",
    api_key="LEKKO_API_KEY",
)
 
def use_client(client):
    str_config = client.get_string("my_namespace", "my_config", {"context_key": "context_val"})
    return str_config
 
use_client(client)

Work with Protobuf configs

You can retrieve Protobuf configs in the following ways:

  • get_proto_by_type(key, context, proto_message_type) converts the config to the specified proto message type, and raises MismatchedProtoType on failure.

  • get_proto(key, context) tries to find the proto message type in the proto symbol database. If the type is not found, it returns the message as a google.protobuf.any_pb2.Any.

For example, you have a proto configuration named proto_config:

{
  "@type": "type.googleapis.com/google.protobuf.BoolValue",
  "value": false
}

You see the following behavior without and with the appropriate proto type:

# Without importing the proto type
>>> config_value = client.get_proto("proto", {})
>>> type(config_value)
<class 'google.protobuf.any_pb2.Any'>
>>> config_value.value
b''
 
# After importing the appropriate proto type
>>> from google.protobuf import wrappers_pb2
>>> config_value = client.get_proto("proto", {})
>>> type(config_value)
<class 'google.protobuf.wrappers_pb2.BoolValue'>
>>> config_value.value
False

Example Code

For a full example, see the Lekko Python SDK example (opens in a new tab).