diff --git a/.github/workflows/build-push-to-main.yaml b/.github/workflows/build-push-to-main.yaml index 499daebde..444c50b28 100644 --- a/.github/workflows/build-push-to-main.yaml +++ b/.github/workflows/build-push-to-main.yaml @@ -37,7 +37,7 @@ jobs: strategy: fail-fast: false matrix: - python_ver: ["3.10", "3.11", "3.12", "3.13"] + python_ver: ["3.10", "3.11", "3.12", "3.13", "3.14"] steps: - uses: actions/checkout@v6 - name: Set up Python ${{ matrix.python_ver }} diff --git a/.github/workflows/build-tag.yaml b/.github/workflows/build-tag.yaml index aabcbca23..d50d3f97a 100644 --- a/.github/workflows/build-tag.yaml +++ b/.github/workflows/build-tag.yaml @@ -43,7 +43,7 @@ jobs: strategy: fail-fast: false matrix: - python_ver: ["3.10", "3.11", "3.12", "3.13"] + python_ver: ["3.10", "3.11", "3.12", "3.13", "3.14"] steps: - uses: actions/checkout@v6 - name: Set up Python ${{ matrix.python_ver }} diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index 7e03d1b80..9bd6ff6cb 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -43,7 +43,7 @@ jobs: strategy: fail-fast: false matrix: - python_ver: ["3.10", "3.11", "3.12", "3.13"] + python_ver: ["3.10", "3.11", "3.12", "3.13", "3.14"] steps: - uses: actions/checkout@v6 - name: Set up Python ${{ matrix.python_ver }} diff --git a/.github/workflows/validate_examples.yaml b/.github/workflows/validate_examples.yaml index a003bb025..3c5eb2874 100644 --- a/.github/workflows/validate_examples.yaml +++ b/.github/workflows/validate_examples.yaml @@ -48,7 +48,7 @@ jobs: strategy: fail-fast: false matrix: - python_ver: ["3.10", "3.11", "3.12", "3.13"] + python_ver: ["3.10", "3.11", "3.12", "3.13", "3.14"] steps: - name: Parse repository_dispatch payload if: github.event_name == 'repository_dispatch' @@ -67,12 +67,12 @@ jobs: - uses: azure/setup-helm@v4 - name: Determine latest Dapr Runtime version (including prerelease) run: | - RUNTIME_VERSION=$(curl -s "https://api.github.com/repos/dapr/dapr/releases" | grep '"tag_name"' | head -n 1 | cut -d ':' -f2 | tr -d '",v ') + RUNTIME_VERSION=$(curl -s "https://api.github.com/repos/dapr/dapr/releases" | grep '"tag_name"' | sort -r | head -n 1 | cut -d ':' -f2 | tr -d '",v ') echo "DAPR_RUNTIME_VER=$RUNTIME_VERSION" >> $GITHUB_ENV echo "Found $RUNTIME_VERSION" - name: Determine latest Dapr Cli version (including prerelease) run: | - CLI_VERSION=$(curl -s "https://api.github.com/repos/dapr/cli/releases" | grep '"tag_name"' | head -n 1 | cut -d ':' -f2 | tr -d '",v ') + CLI_VERSION=$(curl -s "https://api.github.com/repos/dapr/cli/releases" | grep '"tag_name"' | sort -r | head -n 1 | cut -d ':' -f2 | tr -d '",v ') echo "DAPR_CLI_VER=$CLI_VERSION" >> $GITHUB_ENV echo "Found $CLI_VERSION" - name: Set up Python ${{ matrix.python_ver }} diff --git a/README.md b/README.md index f205a1b6a..1a4472c72 100644 --- a/README.md +++ b/README.md @@ -32,7 +32,7 @@ This includes the following packages: ### Prerequisites * [Install Dapr standalone mode](https://github.com/dapr/cli#install-dapr-on-your-local-machine-self-hosted) -* [Install Python 3.9+](https://www.python.org/downloads/) +* [Install Python 3.10+](https://www.python.org/downloads/) ### Install Dapr python sdk @@ -145,12 +145,10 @@ The generated files will be found in `docs/_build`. ```sh pip3 install -r tools/requirements.txt -export DAPR_BRANCH=release-1.16 # Optional, defaults to master +export DAPR_BRANCH=release-1.17 # Optional, defaults to master ./tools/regen_grpcclient.sh ``` -> Note: The `grpcio-tools` version we're using doesn't support Python 3.13. - ## Help & Feedback Need help or have feedback on the SDK? Please open a GitHub issue or come chat with us in the `#python-sdk` channel of our Discord server ([click here to join](https://discord.gg/MySdVxrH)). diff --git a/dapr/clients/grpc/_conversation_helpers.py b/dapr/clients/grpc/_conversation_helpers.py index 9f57c9cc7..dae006bb4 100644 --- a/dapr/clients/grpc/_conversation_helpers.py +++ b/dapr/clients/grpc/_conversation_helpers.py @@ -16,9 +16,9 @@ import inspect import random import string -import types from dataclasses import fields, is_dataclass from enum import Enum +from types import UnionType from typing import ( Any, Callable, @@ -37,10 +37,6 @@ from dapr.conf import settings -# Make mypy happy. Runtime handle: real class on 3.10+, else None. -# TODO: Python 3.9 is about to be end-of-life, so we can drop this at some point next year (2026) -UnionType: Any = getattr(types, 'UnionType', None) - # duplicated from conversation to avoid circular import Params = Union[Mapping[str, Any], Sequence[Any], None] @@ -857,9 +853,7 @@ def _coerce_literal(value: Any, lit_args: List[Any]) -> Any: def _is_union(t) -> bool: origin = get_origin(t) - if origin is Union: - return True - return UnionType is not None and origin is UnionType + return origin is Union or origin is UnionType def _coerce_and_validate(value: Any, expected_type: Any) -> Any: diff --git a/examples/configuration/README.md b/examples/configuration/README.md index a90238887..4dc38f5e7 100644 --- a/examples/configuration/README.md +++ b/examples/configuration/README.md @@ -9,7 +9,7 @@ It demonstrates the following APIs: ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ## Install Dapr python-SDK @@ -18,7 +18,7 @@ It demonstrates the following APIs: pip3 install dapr dapr-ext-grpc ``` -## Store the configuration in configurationstore +## Store the configuration in configurationstore @@ -58,7 +58,7 @@ dapr run --app-id invoke-caller --dapr-grpc-port 50007 --config config.yaml -- ## Cleanup @@ -97,17 +97,17 @@ dapr stop --app-id invoke-receiver ``` dapr logs -a invoke-caller -k ``` - + Logs for caller app: ``` kubectl logs -l app="invokecaller" -c invokecaller ``` - + Logs for receiver sidecar: ``` dapr logs -a invoke-receiver -k ``` - + Logs for receiver app: ``` kubectl logs -l app="invokereceiver" -c invokereceiver diff --git a/examples/invoke-binding/README.md b/examples/invoke-binding/README.md index 74e395768..c90ff1dfc 100644 --- a/examples/invoke-binding/README.md +++ b/examples/invoke-binding/README.md @@ -7,7 +7,7 @@ This example utilizes a publisher and a receiver for the InvokeBinding / OnBindi ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ## Install Dapr python-SDK @@ -26,7 +26,7 @@ name: Kafka install sleep: 30 --> -1. Start the kafka containers using docker compose +1. Start the kafka containers using docker compose ```bash docker compose -f ./docker-compose-single-kafka.yml up -d @@ -36,7 +36,7 @@ docker compose -f ./docker-compose-single-kafka.yml up -d -2. Start Receiver (expose gRPC server receiver on port 50051) +2. Start Receiver (expose gRPC server receiver on port 50051) ```bash dapr run --app-id receiver --app-protocol grpc --app-port 50051 --resources-path ./components python3 invoke-input-binding.py @@ -58,7 +58,7 @@ In another terminal/command-prompt run: diff --git a/examples/invoke-http/README.md b/examples/invoke-http/README.md index 466392d20..eaec8ac8e 100644 --- a/examples/invoke-http/README.md +++ b/examples/invoke-http/README.md @@ -7,13 +7,13 @@ This example utilizes a receiver and a caller for the `invoke_method` functional ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.8+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ### Install requirements You can install dapr SDK package using pip command: - @@ -55,7 +55,7 @@ expected_stdout_lines: - '== APP == 503' - '== APP == Internal Server Error' background: true -sleep: 5 +sleep: 5 --> ```bash @@ -66,7 +66,7 @@ dapr run --app-id=invoke-caller -- python3 invoke-caller.py ## Cleanup @@ -75,4 +75,4 @@ name: Shutdown dapr dapr stop --app-id invoke-receiver ``` - \ No newline at end of file + diff --git a/examples/invoke-simple/Dockerfile b/examples/invoke-simple/Dockerfile index 892d3f624..4d80bcd5c 100644 --- a/examples/invoke-simple/Dockerfile +++ b/examples/invoke-simple/Dockerfile @@ -1,4 +1,4 @@ -FROM python:3.9-slim +FROM python:3.10-slim WORKDIR /app diff --git a/examples/invoke-simple/README.md b/examples/invoke-simple/README.md index 08cf68e74..b2af5c60f 100644 --- a/examples/invoke-simple/README.md +++ b/examples/invoke-simple/README.md @@ -7,7 +7,7 @@ This example utilizes a receiver and a caller for the OnInvoke / Invoke function ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ## Install Dapr python-SDK @@ -47,7 +47,7 @@ expected_stdout_lines: - '== APP == text/plain' - '== APP == INVOKE_RECEIVED' background: true -sleep: 5 +sleep: 5 --> ```bash @@ -60,7 +60,7 @@ dapr run --app-id invoke-caller --app-protocol grpc --dapr-http-port 3500 python ## Cleanup ```bash @@ -83,7 +83,7 @@ dapr run --app-id python-publisher --app-protocol grpc --dapr-grpc-port=3500 --e ## Cleanup diff --git a/examples/pubsub-streaming-async/README.md b/examples/pubsub-streaming-async/README.md index 4a399a5b0..e626fe75a 100644 --- a/examples/pubsub-streaming-async/README.md +++ b/examples/pubsub-streaming-async/README.md @@ -10,7 +10,7 @@ In the s`subscriber.py` file it creates a subscriber object that can call the `n ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ## Install Dapr python-SDK @@ -36,7 +36,7 @@ expected_stdout_lines: output_match_mode: substring background: true match_order: none -sleep: 3 +sleep: 3 --> ```bash @@ -84,7 +84,7 @@ expected_stdout_lines: output_match_mode: substring background: true match_order: none -sleep: 3 +sleep: 3 --> ```bash @@ -114,7 +114,7 @@ sleep: 15 dapr run --app-id python-publisher --app-protocol grpc --dapr-grpc-port=3500 --enable-app-health-check -- python3 publisher.py --topic=TOPIC_B2 ``` - + ## Cleanup diff --git a/examples/pubsub-streaming/README.md b/examples/pubsub-streaming/README.md index d03ff045f..40a746d3e 100644 --- a/examples/pubsub-streaming/README.md +++ b/examples/pubsub-streaming/README.md @@ -10,7 +10,7 @@ In the s`subscriber.py` file it creates a subscriber object that can call the `n ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ## Install Dapr python-SDK @@ -36,7 +36,7 @@ expected_stdout_lines: output_match_mode: substring background: true match_order: none -sleep: 3 +sleep: 3 --> ```bash @@ -84,7 +84,7 @@ expected_stdout_lines: output_match_mode: substring background: true match_order: none -sleep: 3 +sleep: 3 --> ```bash @@ -114,7 +114,7 @@ sleep: 15 dapr run --app-id python-publisher --app-protocol grpc --dapr-grpc-port=3500 --enable-app-health-check -- python3 publisher.py --topic=TOPIC_A2 ``` - + ## Cleanup diff --git a/examples/secret_store/README.md b/examples/secret_store/README.md index 1bb8e3ae5..5a4c87f45 100644 --- a/examples/secret_store/README.md +++ b/examples/secret_store/README.md @@ -9,7 +9,7 @@ This example also illustrates the use of access control for secrets. ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ## Install Dapr python-SDK @@ -70,10 +70,10 @@ spec: allowedSecrets: ["secretKey",] ``` -The above configuration defines that the default access permission for the `localsecretstore` is `deny` and that only the +The above configuration defines that the default access permission for the `localsecretstore` is `deny` and that only the key `secretKey` is allowed to be accessed from the store. -To see this run the same `example.py` app with the following command: +To see this run the same `example.py` app with the following command: \ No newline at end of file + diff --git a/examples/w3c-tracing/Dockerfile b/examples/w3c-tracing/Dockerfile index 892d3f624..4d80bcd5c 100644 --- a/examples/w3c-tracing/Dockerfile +++ b/examples/w3c-tracing/Dockerfile @@ -1,4 +1,4 @@ -FROM python:3.9-slim +FROM python:3.10-slim WORKDIR /app diff --git a/examples/w3c-tracing/README.md b/examples/w3c-tracing/README.md index d8ed7d6bd..58faa8590 100644 --- a/examples/w3c-tracing/README.md +++ b/examples/w3c-tracing/README.md @@ -7,15 +7,15 @@ This sample includes: - invoke-caller: Invokes the exposed methods Also consider [getting started with observability in Dapr](https://github.com/dapr/quickstarts/tree/master/tutorials/observability). - + ## Example overview -This sample uses the Client provided in Dapr's Python SDK invoking a remote method and Zipkin to collect and display tracing data. +This sample uses the Client provided in Dapr's Python SDK invoking a remote method and Zipkin to collect and display tracing data. ## Pre-requisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ### Install dependencies @@ -46,7 +46,7 @@ pip3 install -r requirements.txt ### Verify Zipkin is running -Run `docker ps` to see if the container `dapr_zipkin` is running locally: +Run `docker ps` to see if the container `dapr_zipkin` is running locally: ```bash CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES @@ -219,7 +219,7 @@ with tracer.start_as_current_span(name='main') as span: ``` The class knows the `app-id` for the remote application. It uses `invoke_method` to invoke API calls on the service endpoint. Instrumentation happens automatically in `Dapr` client via the `tracer` argument. - + Execute the following command in order to run the caller example, it will call each method twice: diff --git a/examples/workflow/README.md b/examples/workflow/README.md index 68bb9d1ed..e27f4c78f 100644 --- a/examples/workflow/README.md +++ b/examples/workflow/README.md @@ -5,7 +5,7 @@ This directory contains examples of using the [Dapr Workflow](https://docs.dapr. ## Prerequisites - [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started) -- [Install Python 3.9+](https://www.python.org/downloads/) +- [Install Python 3.10+](https://www.python.org/downloads/) ### Install requirements diff --git a/ext/dapr-ext-fastapi/setup.cfg b/ext/dapr-ext-fastapi/setup.cfg index c182b2bc8..f5d9762ac 100644 --- a/ext/dapr-ext-fastapi/setup.cfg +++ b/ext/dapr-ext-fastapi/setup.cfg @@ -10,17 +10,18 @@ classifiers = License :: OSI Approved :: Apache Software License Operating System :: OS Independent Programming Language :: Python - Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 Programming Language :: Python :: 3.11 Programming Language :: Python :: 3.12 Programming Language :: Python :: 3.13 + Programming Language :: Python :: 3.14 + project_urls = Documentation = https://github.com/dapr/docs Source = https://github.com/dapr/python-sdk [options] -python_requires = >=3.9 +python_requires = >=3.10 packages = find_namespace: include_package_data = True install_requires = diff --git a/ext/dapr-ext-grpc/setup.cfg b/ext/dapr-ext-grpc/setup.cfg index 4225c1abb..e26dcd12d 100644 --- a/ext/dapr-ext-grpc/setup.cfg +++ b/ext/dapr-ext-grpc/setup.cfg @@ -10,17 +10,17 @@ classifiers = License :: OSI Approved :: Apache Software License Operating System :: OS Independent Programming Language :: Python - Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 Programming Language :: Python :: 3.11 Programming Language :: Python :: 3.12 Programming Language :: Python :: 3.13 + Programming Language :: Python :: 3.14 project_urls = Documentation = https://github.com/dapr/docs Source = https://github.com/dapr/python-sdk [options] -python_requires = >=3.9 +python_requires = >=3.10 packages = find_namespace: include_package_data = True install_requires = diff --git a/ext/dapr-ext-workflow/setup.cfg b/ext/dapr-ext-workflow/setup.cfg index 0c5c46624..e0accdd6b 100644 --- a/ext/dapr-ext-workflow/setup.cfg +++ b/ext/dapr-ext-workflow/setup.cfg @@ -10,17 +10,17 @@ classifiers = License :: OSI Approved :: Apache Software License Operating System :: OS Independent Programming Language :: Python - Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 Programming Language :: Python :: 3.11 Programming Language :: Python :: 3.12 Programming Language :: Python :: 3.13 + Programming Language :: Python :: 3.14 project_urls = Documentation = https://github.com/dapr/docs Source = https://github.com/dapr/python-sdk [options] -python_requires = >=3.9 +python_requires = >=3.10 packages = find_namespace: include_package_data = True install_requires = diff --git a/ext/flask_dapr/setup.cfg b/ext/flask_dapr/setup.cfg index c19bf5b5c..4c7220ef6 100644 --- a/ext/flask_dapr/setup.cfg +++ b/ext/flask_dapr/setup.cfg @@ -10,17 +10,17 @@ classifiers = License :: OSI Approved :: Apache Software License Operating System :: OS Independent Programming Language :: Python - Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 Programming Language :: Python :: 3.11 Programming Language :: Python :: 3.12 Programming Language :: Python :: 3.13 + Programming Language :: Python :: 3.14 project_urls = Documentation = https://github.com/dapr/docs Source = https://github.com/dapr/python-sdk [options] -python_requires = >=3.9 +python_requires = >=3.10 packages = find: include_package_data = true zip_safe = false diff --git a/mypy.ini b/mypy.ini index 8c0fee4f0..13a026b7d 100644 --- a/mypy.ini +++ b/mypy.ini @@ -1,5 +1,5 @@ [mypy] -python_version = 3.9 +python_version = 3.10 warn_unused_configs = True warn_redundant_casts = True show_error_codes = True diff --git a/setup.cfg b/setup.cfg index e68961557..3f859d1a9 100644 --- a/setup.cfg +++ b/setup.cfg @@ -10,17 +10,17 @@ classifiers = License :: OSI Approved :: Apache Software License Operating System :: OS Independent Programming Language :: Python - Programming Language :: Python :: 3.9 Programming Language :: Python :: 3.10 Programming Language :: Python :: 3.11 Programming Language :: Python :: 3.12 Programming Language :: Python :: 3.13 + Programming Language :: Python :: 3.14 project_urls = Documentation = https://github.com/dapr/docs Source = https://github.com/dapr/python-sdk [options] -python_requires = >=3.9 +python_requires = >=3.10 packages = find_namespace: include_package_data = True zip_safe = False diff --git a/tox.ini b/tox.ini index 1bdb17921..346be7680 100644 --- a/tox.ini +++ b/tox.ini @@ -2,7 +2,7 @@ skipsdist = True minversion = 3.10.0 envlist = - py{310,311,312,313} + py{310,311,312,313,314} ruff, mypy,