Skip to content

Commit 20787ec

Browse files
authored
feat: enhance Python SDK with metadata support and improve doc (#205)
### Motivation This PR addresses several areas of improvement in the FunctionStream project: 1. **Namespace Consistency**: Updates example configuration files to use the more descriptive `function-stream` namespace instead of the abbreviated `fs` namespace, improving clarity and consistency across the project. 2. **Python SDK Enhancement**: Significantly enhances the Python SDK (`fs-python`) with new metadata access capabilities, improved documentation, and better error handling for message processing. 3. **Operator Improvements**: Adds code generation capabilities to the operator Makefile for generating client SDKs, improving the development workflow. 4. **Docker Build Enhancement**: Adds multi-platform Docker build support for the Python SDK base image. ### Modifications #### Configuration Updates - **Example Functions**: Updated `functions/example-external.yaml` and `functions/example-functions.yaml` to use `function-stream` namespace and subscription names instead of `fs` - **Helm Values**: Changed operator image pull policy from `IfNotPresent` to `Always` in `operator/deploy/chart/values.yaml` #### Python SDK Enhancements - **Version Update**: Bumped Python SDK version from `0.6.0rc1` to `0.6.0rc2` - **Metadata Support**: Added `get_metadata()` method to `FSContext` class for accessing message metadata (topic, message_id) - **Data Production**: Added `produce()` method to `FSContext` for output stream data production - **Enhanced Documentation**: Significantly improved docstrings throughout the codebase with comprehensive parameter descriptions, return value documentation, and usage examples - **Improved Error Handling**: Enhanced error handling in message processing with better metadata access and validation - **Code Quality**: Added comprehensive unit tests for new functionality and improved existing test coverage #### Operator Improvements - **Code Generation**: Added `code-generator` target to operator Makefile with version `v0.32.1` - **Client SDK Generation**: Added `generate-client` target for generating Kubernetes client SDKs using code-generator tools - **Tool Installation**: Integrated client-gen, lister-gen, informer-gen, and deepcopy-gen tools #### Docker Build Enhancement - **Multi-Platform Support**: Added `docker-buildx` target in Python SDK Makefile for building images for both `linux/amd64` and `linux/arm64` architectures #### Testing Improvements - **Enhanced Test Coverage**: Added comprehensive tests for new metadata functionality and context methods - **Better Test Structure**: Improved test organization and mock setup for more reliable testing These changes improve the overall developer experience, provide better functionality for Python SDK users, and establish more consistent naming conventions across the project. --------- Signed-off-by: EvanWave <[email protected]>
1 parent e5b9483 commit 20787ec

File tree

11 files changed

+370
-69
lines changed

11 files changed

+370
-69
lines changed

functions/example-external.yaml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,14 @@
1313
# limitations under the License.
1414

1515
name: external-function
16-
namespace: fs
16+
namespace: function-stream
1717
runtime:
1818
type: "external"
1919
sources:
2020
- config:
2121
inputs:
2222
- "external-input"
23-
subscription-name: "fs"
23+
subscription-name: "function-stream"
2424
type: "memory"
2525
sink:
2626
config:

functions/example-functions.yaml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
# limitations under the License.
1414

1515
name: function-sample
16-
namespace: fs
16+
namespace: function-stream
1717
runtime:
1818
type: "wasm"
1919
config:
@@ -22,7 +22,7 @@ sources:
2222
- config:
2323
inputs:
2424
- "input"
25-
subscription-name: "fs"
25+
subscription-name: "function-stream"
2626
type: "memory"
2727
sink:
2828
config:

operator/Makefile

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -178,10 +178,12 @@ KUSTOMIZE ?= $(LOCALBIN)/kustomize
178178
CONTROLLER_GEN ?= $(LOCALBIN)/controller-gen
179179
ENVTEST ?= $(LOCALBIN)/setup-envtest
180180
GOLANGCI_LINT = $(LOCALBIN)/golangci-lint
181+
CODEGEN ?= $(LOCALBIN)/code-generator
181182

182183
## Tool Versions
183184
KUSTOMIZE_VERSION ?= v5.6.0
184185
CONTROLLER_TOOLS_VERSION ?= v0.17.2
186+
CODEGEN_VERSION ?= v0.32.1
185187
#ENVTEST_VERSION is the version of controller-runtime release branch to fetch the envtest setup script (i.e. release-0.20)
186188
ENVTEST_VERSION ?= $(shell go list -m -f "{{ .Version }}" sigs.k8s.io/controller-runtime | awk -F'[v.]' '{printf "release-%d.%d", $$2, $$3}')
187189
#ENVTEST_K8S_VERSION is the version of Kubernetes to use for setting up ENVTEST binaries (i.e. 1.31)
@@ -216,6 +218,21 @@ golangci-lint: $(GOLANGCI_LINT) ## Download golangci-lint locally if necessary.
216218
$(GOLANGCI_LINT): $(LOCALBIN)
217219
$(call go-install-tool,$(GOLANGCI_LINT),github.com/golangci/golangci-lint/cmd/golangci-lint,$(GOLANGCI_LINT_VERSION))
218220

221+
.PHONY: code-generator
222+
code-generator: $(CODEGEN) ## Download code-generator locally if necessary.
223+
$(CODEGEN): $(LOCALBIN)
224+
$(call go-install-tool,$(CODEGEN),k8s.io/code-generator/cmd/...,$(CODEGEN_VERSION))
225+
226+
.PHONY: generate-client
227+
generate-client: ## Generate client SDK using code-generator
228+
@echo "Generating client SDK..."
229+
@mkdir -p pkg/client
230+
@go install k8s.io/code-generator/cmd/[email protected]
231+
@go install k8s.io/code-generator/cmd/[email protected]
232+
@go install k8s.io/code-generator/cmd/[email protected]
233+
@go install k8s.io/code-generator/cmd/[email protected]
234+
@hack/update-codegen.sh
235+
219236
# go-install-tool will 'go install' any package with custom target and name of binary, if it doesn't exist
220237
# $1 - target path with name of binary
221238
# $2 - package url which can be installed

operator/deploy/chart/values.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ controllerManager:
55
image:
66
repository: functionstream/operator
77
tag: latest
8-
imagePullPolicy: IfNotPresent
8+
imagePullPolicy: Always
99
args:
1010
- "--leader-elect"
1111
- "--metrics-bind-address=:8443"

sdks/fs-python/Makefile

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,8 @@
33
build-image:
44
docker build -t functionstream/fs-python-base .
55

6+
docker-buildx:
7+
docker buildx build --platform linux/amd64,linux/arm64 -t functionstream/fs-python-base .
8+
69
test:
710
PYTHONPATH=. python -m pytest

sdks/fs-python/function_stream/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
from .metrics import Metrics, MetricsServer
55
from .module import FSModule
66

7-
__version__ = "0.6.0rc1"
7+
__version__ = "0.6.0rc2"
88
__all__ = [
99
# Core classes
1010
"FSFunction",

sdks/fs-python/function_stream/context.py

Lines changed: 52 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,14 @@
11
"""
22
FSContext module provides a context object that manages configuration access for FunctionStream SDK.
3+
4+
This module defines the FSContext class which serves as a wrapper around the Config object,
5+
providing a clean interface for accessing configuration values and handling any potential
6+
errors during access. It also provides methods for metadata access and data production.
37
"""
48

59
import logging
610
from typing import Any, Dict
11+
from datetime import datetime
712

813
from .config import Config
914

@@ -17,6 +22,7 @@ class FSContext:
1722
1823
This class serves as a wrapper around the Config object, providing a clean interface
1924
for accessing configuration values and handling any potential errors during access.
25+
It also provides methods for metadata access and data production capabilities.
2026
2127
Attributes:
2228
config (Config): The configuration object containing all settings.
@@ -25,11 +31,10 @@ class FSContext:
2531

2632
def __init__(self, config: Config):
2733
"""
28-
Initialize the FSContext with a configuration object and optional FSFunction reference.
34+
Initialize the FSContext with a configuration object.
2935
3036
Args:
3137
config (Config): The configuration object to be used by this context.
32-
function (FSFunction, optional): The parent FSFunction instance.
3338
"""
3439
self.config = config
3540

@@ -53,8 +58,53 @@ def get_config(self, config_name: str) -> Any:
5358
logger.error(f"Error getting config {config_name}: {str(e)}")
5459
return ""
5560

61+
def get_metadata(self, key: str) -> Any:
62+
"""
63+
Get metadata value by key.
64+
65+
This method retrieves metadata associated with the current message.
66+
67+
Args:
68+
key (str): The metadata key to retrieve.
69+
70+
Returns:
71+
Any: The metadata value, currently always None.
72+
"""
73+
return None
74+
75+
def produce(self, data: Dict[str, Any], event_time: datetime = None) -> None:
76+
"""
77+
Produce data to the output stream.
78+
79+
This method is intended to send processed data to the output stream.
80+
81+
Args:
82+
data (Dict[str, Any]): The data to produce.
83+
event_time (datetime, optional): The timestamp for the event. Defaults to None.
84+
85+
Returns:
86+
None: Currently always returns None.
87+
"""
88+
return None
89+
5690
def get_configs(self) -> Dict[str, Any]:
91+
"""
92+
Get all configuration values.
93+
94+
Returns a dictionary containing all configuration key-value pairs.
95+
96+
Returns:
97+
Dict[str, Any]: A dictionary containing all configuration values.
98+
"""
5799
return self.config.config
58100

59101
def get_module(self) -> str:
102+
"""
103+
Get the current module name.
104+
105+
Returns the name of the module currently being executed.
106+
107+
Returns:
108+
str: The name of the current module.
109+
"""
60110
return self.config.module

0 commit comments

Comments
 (0)