Skip to content

Commit ebc0664

Browse files
Merge pull request #38 from developmentseed/feature/switch-to-uv
update python/dockerimage and switch to uv
2 parents 2f78420 + 5785157 commit ebc0664

File tree

16 files changed

+3059
-109
lines changed

16 files changed

+3059
-109
lines changed

.github/workflows/ci.yml

Lines changed: 23 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -19,36 +19,37 @@ on:
1919
# Run tests on pull requests.
2020
pull_request:
2121
env:
22-
LATEST_PY_VERSION: '3.12'
22+
LATEST_PY_VERSION: '3.13'
2323

2424

2525
jobs:
2626
tests:
2727
runs-on: ubuntu-latest
2828
strategy:
2929
matrix:
30-
python-version: ['3.8', '3.9', '3.10', '3.11', '3.12']
30+
python-version: ['3.11', '3.12', '3.13']
3131

3232
steps:
33-
- uses: actions/checkout@v4
34-
- name: Set up Python ${{ matrix.python-version }}
35-
uses: actions/setup-python@v5
33+
- uses: actions/checkout@v5
34+
35+
- name: Install uv
36+
uses: astral-sh/setup-uv@v7
3637
with:
38+
version: "0.9.*"
39+
enable-cache: true
3740
python-version: ${{ matrix.python-version }}
3841

3942
- name: Install dependencies
4043
run: |
41-
python -m pip install --upgrade pip
42-
python -m pip install -e .["test"]
44+
uv sync
4345
4446
- name: run pre-commit
4547
if: ${{ matrix.python-version == env.LATEST_PY_VERSION }}
4648
run: |
47-
python -m pip install pre-commit
48-
pre-commit run --all-files
49+
uv run pre-commit run --all-files
4950
5051
- name: Run tests
51-
run: python -m pytest --cov titiler.stacapi --cov-report term-missing -s -vv
52+
run: uv run pytest --cov titiler.stacapi --cov-report term-missing -s -vv
5253

5354
- name: Upload Results
5455
if: ${{ matrix.python-version == env.LATEST_PY_VERSION }}
@@ -64,17 +65,17 @@ jobs:
6465
runs-on: ubuntu-latest
6566
if: startsWith(github.event.ref, 'refs/tags') || github.event_name == 'release'
6667
steps:
67-
- uses: actions/checkout@v4
68-
- name: Set up Python
69-
uses: actions/setup-python@v5
68+
- uses: actions/checkout@v5
69+
- name: Install uv
70+
uses: astral-sh/setup-uv@v7
7071
with:
71-
python-version: ${{ env.LATEST_PY_VERSION }}
72+
version: "0.9.*"
73+
enable-cache: true
74+
python-version: ${{ matrix.python-version }}
7275

7376
- name: Install dependencies
7477
run: |
75-
python -m pip install --upgrade pip
76-
python -m pip install wheel twine build
77-
python -m pip install .
78+
uv sync
7879
7980
- name: Set tag version
8081
id: tag
@@ -90,12 +91,12 @@ jobs:
9091
- name: Build and publish
9192
if: ${{ steps.tag.outputs.version }} == ${{ steps.module.outputs.version}}
9293
env:
93-
TWINE_USERNAME: ${{ secrets.PYPI_USERNAME }}
94-
TWINE_PASSWORD: ${{ secrets.PYPI_PASSWORD }}
94+
UV_PUBLISH_USERNAME: ${{ secrets.PYPI_USERNAME }}
95+
UV_PUBLISH_PASSWORD: ${{ secrets.PYPI_PASSWORD }}
9596
run: |
9697
rm -rf dist
97-
python -m build
98-
twine upload dist/*
98+
uv build
99+
uv publish dist/*
99100
100101
publish-docker:
101102
needs: [tests]
@@ -105,7 +106,7 @@ jobs:
105106

106107
steps:
107108
- name: Checkout
108-
uses: actions/checkout@v4
109+
uses: actions/checkout@v5
109110

110111
- name: Set up QEMU
111112
uses: docker/setup-qemu-action@v3

.github/workflows/deploy_mkdocs.yml

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -19,17 +19,13 @@ jobs:
1919
runs-on: ubuntu-latest
2020
steps:
2121
- name: Checkout main
22-
uses: actions/checkout@v4
22+
uses: actions/checkout@v5
2323

24-
- name: Set up Python 3.11
25-
uses: actions/setup-python@v5
24+
- name: Install uv
25+
uses: astral-sh/setup-uv@v7
2626
with:
27-
python-version: 3.11
28-
29-
- name: Install dependencies
30-
run: |
31-
python -m pip install --upgrade pip
32-
python -m pip install mkdocs mkdocs-material pygments
27+
version: "0.9.*"
28+
enable-cache: true
3329

3430
- name: Deploy docs
35-
run: mkdocs gh-deploy --force -f docs/mkdocs.yml
31+
run: uv run --group docs mkdocs gh-deploy --force -f docs/mkdocs.yml

.pre-commit-config.yaml

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,29 +1,24 @@
11
repos:
22
- repo: https://github.com/abravalheri/validate-pyproject
3-
rev: v0.12.1
3+
rev: v0.24
44
hooks:
55
- id: validate-pyproject
66

7-
- repo: https://github.com/psf/black
8-
rev: 22.12.0
9-
hooks:
10-
- id: black
11-
language_version: python
12-
137
- repo: https://github.com/PyCQA/isort
148
rev: 5.12.0
159
hooks:
1610
- id: isort
1711
language_version: python
1812

19-
- repo: https://github.com/charliermarsh/ruff-pre-commit
20-
rev: v0.0.290
13+
- repo: https://github.com/astral-sh/ruff-pre-commit
14+
rev: v0.8.4
2115
hooks:
2216
- id: ruff
2317
args: ["--fix"]
18+
- id: ruff-format
2419

2520
- repo: https://github.com/pre-commit/mirrors-mypy
26-
rev: v1.5.1
21+
rev: v1.11.2
2722
hooks:
2823
- id: mypy
2924
language_version: python

CHANGELOG.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,13 @@
22

33
## [Unreleased]
44

5+
* switch to `uv` for development
6+
* switch to `hatch` for python package build-system
7+
* remove `titiler` metapackage **breaking change**
8+
* add support for python version 3.13
9+
* bump minimum python version to 3.11
10+
* update docker image to python:3.13
11+
512
## [0.3.3] - 2025-11-06
613

714
* fix single date query to only select one day (author @wschoors, https://github.com/developmentseed/titiler-stacapi/pull/34)

CONTRIBUTING.md

Lines changed: 33 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,23 +2,53 @@
22

33
Issues and pull requests are more than welcome: https://github.com/developmentseed/titiler-stacapi/issues
44

5+
We recommand using [`uv`](https://docs.astral.sh/uv) as project manager for development.
6+
7+
See https://docs.astral.sh/uv/getting-started/installation/ for installation
8+
59
**dev install**
610

711
```bash
812
git clone https://github.com/developmentseed/titiler-stacapi.git
913
cd titiler-stacapi
1014

11-
python -m pip install pre-commit -e .["dev,test"]
15+
uv sync
1216
```
1317

1418
You can then run the tests with the following command:
1519

1620
```sh
17-
python -m pytest --cov titiler.stacapi --cov-report term-missing
21+
uv run pytest --cov titiler.stacapi --cov-report term-missing
1822
```
1923

2024
This repo is set to use `pre-commit` to run *isort*, *flake8*, *pydocstring*, *black* ("uncompromising Python code formatter") and mypy when committing new code.
2125

2226
```bash
23-
$ pre-commit install
27+
uv run pre-commit install
28+
29+
# If needed, you can run pre-commit script manually
30+
uv run pre-commit run --all-files
2431
```
32+
33+
### Docs
34+
35+
```bash
36+
git clone https://github.com/developmentseed/titiler-stacapi.git
37+
cd titiler-stacapi
38+
39+
# Build docs
40+
uv run --group docs mkdocs build -f docs/mkdocs.yml
41+
```
42+
43+
Hot-reloading docs:
44+
45+
```bash
46+
uv run --group docs mkdocs serve -f docs/mkdocs.yml --livereload
47+
```
48+
49+
To manually deploy docs (note you should never need to do this because Github
50+
Actions deploys automatically for new commits.):
51+
52+
```bash
53+
uv run --group docs mkdocs gh-deploy -f docs/mkdocs.yml
54+
```

Dockerfile

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
ARG PYTHON_VERSION=3.13
2+
3+
FROM python:${PYTHON_VERSION}
4+
RUN apt update && apt upgrade -y \
5+
&& apt install curl -y \
6+
&& rm -rf /var/lib/apt/lists/*
7+
8+
# Ensure root certificates are always updated at evey container build
9+
# and curl is using the latest version of them
10+
RUN mkdir /usr/local/share/ca-certificates/cacert.org
11+
RUN cd /usr/local/share/ca-certificates/cacert.org && curl -k -O https://www.cacert.org/certs/root.crt
12+
RUN cd /usr/local/share/ca-certificates/cacert.org && curl -k -O https://www.cacert.org/certs/class3.crt
13+
RUN update-ca-certificates
14+
ENV CURL_CA_BUNDLE=/etc/ssl/certs/ca-certificates.crt
15+
16+
RUN python -m pip install -U pip
17+
RUN python -m pip install uvicorn uvicorn-worker gunicorn
18+
19+
COPY titiler/ titiler/
20+
COPY pyproject.toml pyproject.toml
21+
COPY README.md README.md
22+
COPY LICENSE LICENSE
23+
24+
RUN python -m pip install --no-cache-dir --upgrade .
25+
RUN rm -rf titiler/ pyproject.toml README.md LICENSE
26+
27+
###################################################
28+
# For compatibility (might be removed at one point)
29+
ENV MODULE_NAME=titiler.stacapi.main
30+
ENV VARIABLE_NAME=app
31+
ENV HOST=0.0.0.0
32+
ENV PORT=80
33+
ENV WEB_CONCURRENCY=1
34+
CMD gunicorn -k uvicorn.workers.UvicornWorker ${MODULE_NAME}:${VARIABLE_NAME} --bind ${HOST}:${PORT} --workers ${WEB_CONCURRENCY}

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ $ export TITILER_STACAPI_STAC_API_URL=https://api.stac
6969
$ docker-compose up --build api
7070
```
7171

72-
It runs `titiler.stacapi` using Gunicorn web server.
72+
It runs `titiler.stacapi` using Uvicorn web server.
7373

7474
### How it works
7575

docker-compose.yml

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,10 @@
1-
version: '3'
2-
31
services:
42
api:
53
# At the time of writing, rasterio wheels are not available for arm64 arch
64
# so we force the image to be built with linux/amd64
75
platform: linux/amd64
86
build:
97
context: .
10-
dockerfile: dockerfiles/Dockerfile
118
ports:
129
- "8081:8081"
1310
environment:
@@ -45,6 +42,4 @@ services:
4542
# TiTiler STAC API Config
4643
- TITILER_STACAPI_API_DEBUG=TRUE
4744
- TITILER_STACAPI_STAC_API_URL=${TITILER_STACAPI_STAC_API_URL}
48-
command:
49-
# You can also overwrite the CMD option and use simple `uvicorn` ASGI server
50-
bash -c "uvicorn titiler.stacapi.main:app --port 8081 --host 0.0.0.0"
45+
command: ["uvicorn", "titiler.stacapi.main:app", "--host", "0.0.0.0", "--port", "8081", "--workers", "1"]

dockerfiles/Dockerfile

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

notebooks/demo_wmts_eoapi.ipynb

Lines changed: 6 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -141,7 +141,6 @@
141141
}
142142
],
143143
"source": [
144-
"\n",
145144
"from owslib.wmts import WebMapTileService\n",
146145
"\n",
147146
"wmts = WebMapTileService(\n",
@@ -164,7 +163,7 @@
164163
"print(layer.tilematrixsetlinks[\"WebMercatorQuad\"].tilematrixlimits)\n",
165164
"print()\n",
166165
"print(\"Layer dimensions\")\n",
167-
"print(layer.dimensions)\n"
166+
"print(layer.dimensions)"
168167
]
169168
},
170169
{
@@ -174,10 +173,10 @@
174173
"outputs": [],
175174
"source": [
176175
"tile = wmts.gettile(\n",
177-
" layer='MAXAR_Emilia_Romagna_Italy_flooding_may23_visual',\n",
176+
" layer=\"MAXAR_Emilia_Romagna_Italy_flooding_may23_visual\",\n",
178177
" style=\"default\",\n",
179-
" tilematrixset='WebMercatorQuad',\n",
180-
" tilematrix='13',\n",
178+
" tilematrixset=\"WebMercatorQuad\",\n",
179+
" tilematrix=\"13\",\n",
181180
" column=4373,\n",
182181
" row=2963,\n",
183182
" format=\"image/png\",\n",
@@ -298,22 +297,15 @@
298297
"source": [
299298
"from folium import Map, TileLayer\n",
300299
"\n",
301-
"m = Map(\n",
302-
" location=(44.52, 12.22),\n",
303-
" zoom_start=14\n",
304-
")\n",
300+
"m = Map(location=(44.52, 12.22), zoom_start=14)\n",
305301
"\n",
306302
"collection = \"MAXAR_Emilia_Romagna_Italy_flooding_may23\"\n",
307303
"TIME = \"2023-05-23\"\n",
308304
"TileMatrixSet = \"WebMercatorQuad\"\n",
309305
"\n",
310306
"tiles_url = f\"http://127.0.0.1:8000/{collection}/default/{TIME}/{TileMatrixSet}/{{z}}/{{x}}/{{y}}.png?assets=visual&asset_bidx=visual%7C1%2C2%2C3\"\n",
311307
"\n",
312-
"TileLayer(\n",
313-
" tiles=tiles_url,\n",
314-
" opacity=1,\n",
315-
" attr=\"DigitalGlobe OpenData\"\n",
316-
").add_to(m)\n",
308+
"TileLayer(tiles=tiles_url, opacity=1, attr=\"DigitalGlobe OpenData\").add_to(m)\n",
317309
"\n",
318310
"m"
319311
]

0 commit comments

Comments
 (0)