Skip to content

Commit f90538b

Browse files
Python: switch to uv (microsoft#8320)
### Motivation and Context <!-- Thank you for your contribution to the semantic-kernel repo! Please help reviewers and future users, providing the following information: 1. Why is this change required? 2. What problem does it solve? 3. What scenario does it contribute to? 4. If it fixes an open issue, please link to the issue here. --> Switches from poetry to uv much faster and easier lock management easier maintenance of pyproject.toml fixes: microsoft#6584 fixes: microsoft#8326 ### Description <!-- Describe your changes, the overall approach, the underlying design. These notes will help understanding how your code works. Thanks! --> ### Contribution Checklist <!-- Before submitting this PR, please make sure: --> - [x] The code builds clean without any errors or warnings - [x] The PR follows the [SK Contribution Guidelines](https://github.com/microsoft/semantic-kernel/blob/main/CONTRIBUTING.md) and the [pre-submission formatting script](https://github.com/microsoft/semantic-kernel/blob/main/CONTRIBUTING.md#development-scripts) raises no violations - [x] All unit tests pass, and I have added new tests where possible - [ ] I didn't break anyone 😄
1 parent 163d512 commit f90538b

24 files changed

Lines changed: 5819 additions & 8362 deletions

File tree

‎.github/workflows/python-build-wheel.yml‎

Lines changed: 0 additions & 45 deletions
This file was deleted.

‎.github/workflows/python-integration-tests.yml‎

Lines changed: 64 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -49,27 +49,37 @@ jobs:
4949
matrix:
5050
python-version: ["3.11"]
5151
os: [ubuntu-latest]
52+
env:
53+
# Configure a constant location for the uv cache
54+
UV_CACHE_DIR: /tmp/.uv-cache
5255
steps:
5356
- uses: actions/checkout@v4
54-
- name: Install poetry
55-
run: pipx install poetry
57+
- name: Set up uv
58+
if: ${{ matrix.os == 'ubuntu-latest' || matrix.os == 'macos-latest' }}
59+
run: curl -LsSf https://astral.sh/uv/install.sh | sh
60+
- name: Set up uv
61+
if: ${{ matrix.os == 'windows-latest' }}
62+
run: irm https://astral.sh/uv/install.ps1 | iex
63+
shell: powershell
5664
- name: Set up Python ${{ matrix.python-version }}
5765
uses: actions/setup-python@v5
5866
with:
5967
python-version: ${{ matrix.python-version }}
60-
cache: "poetry"
68+
- name: Restore uv cache
69+
id: cache
70+
uses: actions/cache@v4
71+
with:
72+
path: ${{ env.UV_CACHE_DIR }}
73+
key: uv-${{ runner.os }}-${{ matrix.python-version }}-${{ hashFiles('**/uv.lock') }}
6174
- name: Install dependencies with hnswlib native disabled
6275
if: matrix.os == 'macos-latest' && matrix.python-version == '3.11'
6376
run: |
6477
export HNSWLIB_NO_NATIVE=1
65-
python -m pip install --upgrade pip setuptools wheel
66-
cd python && poetry install --with tests
78+
uv sync --all-extras --dev
6779
- name: Install dependencies with hnswlib native enabled
6880
if: matrix.os != 'macos-latest' || matrix.python-version != '3.11'
6981
run: |
70-
python -m pip install --upgrade pip setuptools wheel
71-
cd python
72-
poetry install --with tests
82+
uv sync --all-extras --dev
7383
- name: Install Ollama
7484
if: matrix.os == 'ubuntu-latest'
7585
run: |
@@ -98,7 +108,7 @@ jobs:
98108
- name: Run Integration Tests
99109
id: run_tests
100110
shell: bash
101-
env: # Set Azure credentials secret as an input
111+
env:
102112
HNSWLIB_NO_NATIVE: 1
103113
Python_Integration_Tests: Python_Integration_Tests
104114
AZURE_OPENAI_EMBEDDING_DEPLOYMENT_NAME: ${{ vars.AZURE_OPENAI_EMBEDDING_DEPLOYMENT_NAME }} # azure-text-embedding-ada-002
@@ -137,7 +147,7 @@ jobs:
137147
REDIS_CONNECTION_STRING: ${{ vars.REDIS_CONNECTION_STRING }}
138148
run: |
139149
cd python
140-
poetry run pytest -n logical --dist loadfile --dist worksteal ./tests/integration ./tests/samples -v --junitxml=pytest.xml
150+
uv run pytest -n logical --dist loadfile --dist worksteal ./tests/integration ./tests/samples -v --junitxml=pytest.xml
141151
- name: Surface failing tests
142152
if: always()
143153
uses: pmeier/pytest-results-action@main
@@ -155,6 +165,8 @@ jobs:
155165
fail-on-empty: true
156166
# (Optional) Title of the test results section in the workflow summary
157167
title: Test results
168+
- name: Minimize uv cache
169+
run: uv cache prune --ci
158170

159171
python-integration-tests:
160172
needs: paths-filter
@@ -168,26 +180,32 @@ jobs:
168180
os: [ubuntu-latest, windows-latest, macos-latest]
169181
steps:
170182
- uses: actions/checkout@v4
171-
- name: Install poetry
172-
run: pipx install poetry
183+
- name: Set up uv
184+
if: ${{ matrix.os == 'ubuntu-latest' || matrix.os == 'macos-latest' }}
185+
run: curl -LsSf https://astral.sh/uv/install.sh | sh
186+
- name: Set up uv
187+
if: ${{ matrix.os == 'windows-latest' }}
188+
run: irm https://astral.sh/uv/install.ps1 | iex
189+
shell: powershell
173190
- name: Set up Python ${{ matrix.python-version }}
174191
uses: actions/setup-python@v5
175192
with:
176193
python-version: ${{ matrix.python-version }}
177-
cache: "poetry"
194+
- name: Restore uv cache
195+
id: cache
196+
uses: actions/cache@v4
197+
with:
198+
path: ${{ env.UV_CACHE_DIR }}
199+
key: uv-${{ runner.os }}-${{ matrix.python-version }}-${{ hashFiles('**/uv.lock') }}
178200
- name: Install dependencies with hnswlib native disabled
179201
if: matrix.os == 'macos-latest' && matrix.python-version == '3.11'
180202
run: |
181203
export HNSWLIB_NO_NATIVE=1
182-
python -m pip install --upgrade pip setuptools wheel
183-
cd python && poetry install --with tests
184-
204+
uv sync --all-extras --dev
185205
- name: Install dependencies with hnswlib native enabled
186206
if: matrix.os != 'macos-latest' || matrix.python-version != '3.11'
187207
run: |
188-
python -m pip install --upgrade pip setuptools wheel
189-
cd python && poetry install --with tests
190-
208+
uv sync --all-extras --dev
191209
- name: Install Ollama
192210
if: matrix.os == 'ubuntu-latest'
193211
run: |
@@ -209,11 +227,15 @@ jobs:
209227

210228
- name: Set up gcloud
211229
uses: google-github-actions/setup-gcloud@v2
230+
231+
- name: Setup Redis Stack Server
232+
if: matrix.os == 'ubuntu-latest'
233+
run: docker run -d --name redis-stack-server -p 6379:6379 redis/redis-stack-server:latest
212234

213235
- name: Run Integration Tests
214236
id: run_tests
215237
shell: bash
216-
env: # Set Azure credentials secret as an input
238+
env:
217239
HNSWLIB_NO_NATIVE: 1
218240
Python_Integration_Tests: Python_Integration_Tests
219241
AZURE_OPENAI_EMBEDDING_DEPLOYMENT_NAME: ${{ vars.AZURE_OPENAI_EMBEDDING_DEPLOYMENT_NAME }} # azure-text-embedding-ada-002
@@ -240,6 +262,8 @@ jobs:
240262
MISTRALAI_API_KEY: ${{secrets.MISTRALAI_API_KEY}}
241263
MISTRALAI_CHAT_MODEL_ID: ${{ vars.MISTRALAI_CHAT_MODEL_ID }}
242264
MISTRALAI_EMBEDDING_MODEL_ID: ${{ vars.MISTRALAI_EMBEDDING_MODEL_ID }}
265+
ANTHROPIC_API_KEY: ${{secrets.ANTHROPIC_API_KEY}}
266+
ANTHROPIC_CHAT_MODEL_ID: ${{ vars.ANTHROPIC_CHAT_MODEL_ID }}
243267
OLLAMA_MODEL: "${{ matrix.os == 'ubuntu-latest' && vars.OLLAMA_MODEL || '' }}" # phi3
244268
GOOGLE_AI_GEMINI_MODEL_ID: ${{ vars.GOOGLE_AI_GEMINI_MODEL_ID }}
245269
GOOGLE_AI_EMBEDDING_MODEL_ID: ${{ vars.GOOGLE_AI_EMBEDDING_MODEL_ID }}
@@ -248,16 +272,28 @@ jobs:
248272
VERTEX_AI_GEMINI_MODEL_ID: ${{ vars.VERTEX_AI_GEMINI_MODEL_ID }}
249273
VERTEX_AI_EMBEDDING_MODEL_ID: ${{ vars.VERTEX_AI_EMBEDDING_MODEL_ID }}
250274
REDIS_CONNECTION_STRING: ${{ vars.REDIS_CONNECTION_STRING }}
251-
ANTHROPIC_API_KEY: ${{secrets.ANTHROPIC_API_KEY}}
252-
ANTHROPIC_CHAT_MODEL_ID: ${{ vars.ANTHROPIC_CHAT_MODEL_ID }}
253275
run: |
254-
if ${{ matrix.os == 'ubuntu-latest' }}; then
255-
docker run -d --name redis-stack-server -p 6379:6379 redis/redis-stack-server:latest
256-
fi
257-
258276
cd python
259-
poetry run pytest -n logical --dist loadfile --dist worksteal ./tests/integration -v
260-
poetry run pytest -n logical --dist loadfile --dist worksteal ./tests/samples -v
277+
uv run pytest -n logical --dist loadfile --dist worksteal ./tests/integration ./tests/samples -v --junitxml=pytest.xml
278+
- name: Surface failing tests
279+
if: always()
280+
uses: pmeier/pytest-results-action@main
281+
with:
282+
# A list of JUnit XML files, directories containing the former, and wildcard
283+
# patterns to process.
284+
# See @actions/glob for supported patterns.
285+
path: python/pytest.xml
286+
# (Optional) Add a summary of the results at the top of the report
287+
summary: true
288+
# (Optional) Select which results should be included in the report.
289+
# Follows the same syntax as `pytest -r`
290+
display-options: fEX
291+
# (Optional) Fail the workflow if no JUnit XML was found.
292+
fail-on-empty: true
293+
# (Optional) Title of the test results section in the workflow summary
294+
title: Test results
295+
- name: Minimize uv cache
296+
run: uv cache prune --ci
261297

262298
# This final job is required to satisfy the merge queue. It must only run (or succeed) if no tests failed
263299
python-integration-tests-check:

‎.github/workflows/python-lint.yml‎

Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,14 +15,29 @@ jobs:
1515
python-version: ["3.10"]
1616
runs-on: ubuntu-latest
1717
continue-on-error: true
18+
defaults:
19+
run:
20+
working-directory: python
21+
env:
22+
# Configure a constant location for the uv cache
23+
UV_CACHE_DIR: /tmp/.uv-cache
1824
steps:
1925
- uses: actions/checkout@v4
20-
- name: Install poetry
21-
run: pipx install poetry
22-
- uses: actions/setup-python@v5
26+
- name: Set up uv
27+
run: curl -LsSf https://astral.sh/uv/install.sh | sh
28+
- name: Set up Python ${{ matrix.python-version }}
29+
uses: actions/setup-python@v5
2330
with:
2431
python-version: ${{ matrix.python-version }}
25-
cache: "poetry"
26-
- name: Install dependencies
27-
run: cd python && poetry install
32+
- name: Restore uv cache
33+
uses: actions/cache@v4
34+
with:
35+
path: ${{ env.UV_CACHE_DIR }}
36+
key: uv-${{ runner.os }}-${{ matrix.python-version }}-${{ hashFiles('**/uv.lock') }}
37+
- name: Install the project
38+
run: uv sync --all-extras --dev
2839
- uses: pre-commit/action@v3.0.1
40+
with:
41+
extra_args: --config python/.pre-commit-config.yaml
42+
- name: Minimize uv cache
43+
run: uv cache prune --ci

‎.github/workflows/python-unit-tests.yml‎

Lines changed: 37 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,9 @@ on:
55
branches: ["main", "feature*"]
66
paths:
77
- "python/**"
8+
env:
9+
# Configure a constant location for the uv cache
10+
UV_CACHE_DIR: /tmp/.uv-cache
811

912
jobs:
1013
python-unit-tests:
@@ -28,17 +31,27 @@ jobs:
2831
working-directory: python
2932
steps:
3033
- uses: actions/checkout@v4
31-
- name: Install poetry
32-
run: pipx install poetry
34+
- name: Set up uv
35+
if: ${{ matrix.os == 'ubuntu-latest' || matrix.os == 'macos-latest' }}
36+
run: curl -LsSf https://astral.sh/uv/install.sh | sh
37+
- name: Set up uv
38+
if: ${{ matrix.os == 'windows-latest' }}
39+
run: irm https://astral.sh/uv/install.ps1 | iex
40+
shell: powershell
3341
- name: Set up Python ${{ matrix.python-version }}
3442
uses: actions/setup-python@v5
3543
with:
3644
python-version: ${{ matrix.python-version }}
37-
cache: "poetry"
38-
- name: Install dependencies
39-
run: poetry install --with unit-tests
45+
- name: Restore uv cache
46+
id: cache
47+
uses: actions/cache@v4
48+
with:
49+
path: ${{ env.UV_CACHE_DIR }}
50+
key: uv-${{ runner.os }}-${{ matrix.python-version }}-${{ hashFiles('**/uv.lock') }}
51+
- name: Install the project
52+
run: uv sync --all-extras --dev
4053
- name: Test with pytest
41-
run: poetry run pytest --junitxml=pytest.xml ./tests/unit
54+
run: uv run pytest --junitxml=pytest.xml ./tests/unit
4255
- name: Surface failing tests
4356
if: always()
4457
uses: pmeier/pytest-results-action@main
@@ -56,6 +69,8 @@ jobs:
5669
fail-on-empty: true
5770
# (Optional) Title of the test results section in the workflow summary
5871
title: Test results
72+
- name: Minimize uv cache
73+
run: uv cache prune --ci
5974
python-test-coverage:
6075
name: Python Test Coverage
6176
runs-on: [ubuntu-latest]
@@ -65,21 +80,27 @@ jobs:
6580
defaults:
6681
run:
6782
working-directory: python
83+
env:
84+
PYTHON_VERSION: "3.10"
6885
steps:
6986
- uses: actions/checkout@v4
7087
- name: Setup filename variables
7188
run: echo "FILE_ID=${{ github.event.number }}" >> $GITHUB_ENV
72-
- name: Install poetry
73-
run: pipx install poetry
74-
- name: Set up Python 3.10
89+
- name: Set up uv
90+
run: curl -LsSf https://astral.sh/uv/install.sh | sh
91+
- name: Set up Python ${{ env.PYTHON_VERSION }}
7592
uses: actions/setup-python@v5
7693
with:
77-
python-version: "3.10"
78-
cache: "poetry"
79-
- name: Install dependencies
80-
run: poetry install --with unit-tests
94+
python-version: ${{ env.PYTHON_VERSION }}
95+
- name: Restore uv cache
96+
uses: actions/cache@v4
97+
with:
98+
path: ${{ env.UV_CACHE_DIR }}
99+
key: uv-${{ runner.os }}-${{ env.PYTHON_VERSION }}-${{ hashFiles('**/uv.lock') }}
100+
- name: Install the project
101+
run: uv sync --all-extras --dev
81102
- name: Test with pytest
82-
run: poetry run pytest -q --junitxml=pytest.xml --cov=semantic_kernel --cov-report=term-missing:skip-covered ./tests/unit | tee python-coverage.txt
103+
run: uv run pytest -q --junitxml=pytest.xml --cov=semantic_kernel --cov-report=term-missing:skip-covered ./tests/unit | tee python-coverage.txt
83104
- name: Upload coverage
84105
if: always()
85106
uses: actions/upload-artifact@v4
@@ -96,3 +117,5 @@ jobs:
96117
path: python/pytest.xml
97118
overwrite: true
98119
retention-days: 1
120+
- name: Minimize uv cache
121+
run: uv cache prune --ci

‎.gitignore‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -461,6 +461,7 @@ env/
461461
venv/
462462
myvenv/
463463
ENV/
464+
.venv*/
464465

465466
# Python dist
466467
dist/

0 commit comments

Comments
 (0)