-
Notifications
You must be signed in to change notification settings - Fork 3
Expand file tree
/
Copy pathMakefile
More file actions
193 lines (155 loc) · 7.32 KB
/
Copy pathMakefile
File metadata and controls
193 lines (155 loc) · 7.32 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
ifeq ($(DC_ENV),ci)
UV_FLAGS = "--system"
endif
PYTHON ?= python3
# The test targets below need pytest + GDAL + the pinned soil-id-db. They run
# natively only when THIS interpreter ($(PYTHON)) has pytest AND the *pinned*
# GDAL version (so results match CI and the pinned image); otherwise they
# transparently re-run themselves in a GDAL-capable container against the pinned
# soil-id-db image (see scripts/run_in_container.sh), so the same `make test*`
# command works on macOS and on CI alike.
#
# The version gate matters: snapshots are GDAL-version-sensitive, so a native
# Homebrew GDAL of a *different* version must NOT take the native path — it would
# produce snapshots that disagree with CI. It also naturally routes macOS to the
# container, since the interpreter with GDAL (Homebrew) lacks pytest and the
# venv with pytest lacks GDAL. Set NATIVE=1 to force native (also set inside the
# runner container, where the versions do match, to prevent infinite recursion).
GDAL_PIN := $(shell sed -n 's/^gdal==\([0-9.]*\).*/\1/p' requirements.txt)
ifeq ($(NATIVE),1)
NATIVE_OK := 1
else
NATIVE_OK := $(shell $(PYTHON) -c 'import pytest, osgeo.gdal as g; raise SystemExit(g.__version__ != "$(GDAL_PIN)")' >/dev/null 2>&1 && echo 1)
endif
install:
uv pip install -r requirements.txt $(UV_FLAGS)
install_dev:
uv pip install -r requirements-dev.txt $(UV_FLAGS)
setup_git_hooks:
@pre-commit install
lint:
ruff check soil_id
ruff format soil_id --diff
format:
ruff check soil_id --fix
ruff format soil_id
lock:
CUSTOM_COMPILE_COMMAND="make lock" uv pip compile --upgrade --generate-hashes requirements/base.in -o requirements.txt
lock_package:
CUSTOM_COMPILE_COMMAND="make lock" uv pip compile --upgrade-package $(PACKAGE) --generate-hashes --emit-build-options requirements/base.in requirements/deploy.in -o requirements.txt
lock_dev:
CUSTOM_COMPILE_COMMAND="make lock-dev" uv pip compile --upgrade --generate-hashes requirements/dev.in -o requirements-dev.txt
lock_dev_package:
CUSTOM_COMPILE_COMMAND="make lock-dev" uv pip compile --upgrade-package $(PACKAGE) --generate-hashes requirements/dev.in -o requirements-dev.txt
clean:
@find . -name *.pyc -delete
@find . -name __pycache__ -delete
# run the standard test suite (unit + integration, no api_snapshots)
test:
@if [ "$(NATIVE_OK)" != "1" ]; then exec ./scripts/run_in_container.sh test; fi; \
if [ -z "$(PATTERN)" ]; then \
$(PYTHON) -m pytest soil_id -m "not api_snapshot"; \
else \
$(PYTHON) -m pytest soil_id -m "not api_snapshot" -k "$(PATTERN)"; \
fi
# All tests except api_snapshot and integration (no live external APIs)
test_unit:
@if [ "$(NATIVE_OK)" != "1" ]; then exec ./scripts/run_in_container.sh test_unit; fi; \
$(PYTHON) -m pytest soil_id -m "not api_snapshot and not integration"
# update the unit test snapshots (but not the API snapshots)
test_update_unit_snapshots:
@if [ "$(NATIVE_OK)" != "1" ]; then exec ./scripts/run_in_container.sh test_update_unit_snapshots; fi; \
$(PYTHON) -m pytest soil_id -m "not api_snapshot and not integration" --snapshot-update
# Regenerate the unit-test output snapshots reproducibly in a GDAL-capable
# container, against the pinned soil-id-db image CI uses. Wraps
# test_update_unit_snapshots for machines where GDAL won't build natively
# (e.g. macOS). See scripts/regen_snapshots.sh.
regen_snapshots:
./scripts/regen_snapshots.sh
# Integration smoke tests only (full live API run, no output validation)
test_integration:
pytest soil_id -m integration
# API response snapshot tests only (compares live API responses to stored snapshots)
test_api_snapshot:
pytest soil_id -m api_snapshot
# Refresh stored API response snapshots from live APIs
test_update_api_snapshots:
pytest soil_id -m api_snapshot --snapshot-update
test_verbose:
pytest soil_id --capture=no
test_profile:
pytest soil_id --profile
test_graphs: test-profile graphs
graphs:
# gprof2dot -f pstats prof/combined.prof | dot -Tsvg -o prof/combined.svg
# flameprof prof/combined.prof > prof/combined_flame.svg
gprof2dot -f pstats prof/test_soil_location.prof | dot -Tsvg -o prof/test_soil_location.svg
flameprof prof/test_soil_location.prof > prof/test_soil_location_flame.svg
generate_bulk_test_results_us:
python -m soil_id.tests.us.generate_bulk_test_results
process_bulk_test_results_us:
python -m soil_id.tests.us.process_bulk_test_results $(RESULTS_FILE)
generate_bulk_test_results_global:
python -m soil_id.tests.global.generate_bulk_test_results
process_bulk_test_results_global:
python -m soil_id.tests.global.process_bulk_test_results $(RESULTS_FILE)
generate_bulk_test_results_legacy:
python -m soil_id.tests.legacy.generate_bulk_test_results
process_bulk_test_results_legacy:
python -m soil_id.tests.legacy.process_bulk_test_results $(RESULTS_FILE)
# Donwload Munsell CSV, SHX, SHP, SBX, SBN, PRJ, DBF
# 1tN23iVe6X1fcomcfveVp4w3Pwd0HJuTe: LandPKS_munsell_rgb_lab.csv
# 1WUa9e3vTWPi6G8h4OI3CBUZP5y7tf1Li: gsmsoilmu_a_us.shx
# 1l9MxC0xENGmI_NmGlBY74EtlD6SZid_a: gsmsoilmu_a_us.shp
# 1asGnnqe0zI2v8xuOszlsNmZkOSl7cJ2n: gsmsoilmu_a_us.sbx
# 185Qjb9pJJn4AzOissiTz283tINrDqgI0: gsmsoilmu_a_us.sbn
# 1P3xl1YRlfcMjfO_4PM39tkrrlL3hoLzv: gsmsoilmu_a_us.prj
# 1K0GkqxhZiVUND6yfFmaI7tYanLktekyp: gsmsoilmu_a_us.dbf
# 1z7foFFHv_mTsuxMYnfOQRvXT5LKYlYFN: SoilID_US_Areas.shz
download_soil_data:
mkdir -p Data
cd Data; \
gdown 1tN23iVe6X1fcomcfveVp4w3Pwd0HJuTe; \
gdown 1WUa9e3vTWPi6G8h4OI3CBUZP5y7tf1Li; \
gdown 1l9MxC0xENGmI_NmGlBY74EtlD6SZid_a; \
gdown 1asGnnqe0zI2v8xuOszlsNmZkOSl7cJ2n; \
gdown 185Qjb9pJJn4AzOissiTz283tINrDqgI0; \
gdown 1P3xl1YRlfcMjfO_4PM39tkrrlL3hoLzv; \
gdown 1K0GkqxhZiVUND6yfFmaI7tYanLktekyp; \
gdown 1z7foFFHv_mTsuxMYnfOQRvXT5LKYlYFN \
DATABASE_DUMP_FILE ?= Data/soil_id_db.dump
DOCKER_IMAGE_TAG ?= ghcr.io/techmatters/soil-id-db:latest
# Build linux/amd64 explicitly: the postgis:16-3.5 base has no arm64 manifest,
# and CI/prod run the image on amd64 regardless.
build_docker_image:
@echo "Building to tag $(DOCKER_IMAGE_TAG)"
docker build \
--platform linux/amd64 \
--build-arg DATABASE_DUMP_FILE=$(DATABASE_DUMP_FILE) \
-t $(DOCKER_IMAGE_TAG) \
.
push_docker_image:
@echo "Pushing tag $(DOCKER_IMAGE_TAG). Make sure to provide a versioned tag in addition to updating latest!"
docker push $(DOCKER_IMAGE_TAG)
start_db:
docker compose up -d
stop_db:
docker compose down
connect_db:
docker compose exec db psql -U postgres -d soil_id
# Container running the local soil-id-db (PostgreSQL 16). Override if your
# compose project names it differently.
SOIL_ID_DB_CONTAINER ?= terraso-backend-soil-id-db-1
# Dump from *inside* the PG16 container so the archive is always restorable by
# the PG16 image. A host pg_dump newer than 16 (e.g. 17/18) writes an archive
# the image's pg_restore 16 cannot read ("unsupported version in file header"),
# which silently breaks build_docker_image.
dump_soil_id_db:
docker exec $(SOIL_ID_DB_CONTAINER) pg_dump --format=custom -U postgres -d soil_id \
-t hwsd2_segment -t hwsd2_data -t landpks_munsell_rgb_lab -t normdist1 -t normdist2 \
-t wise_soil_data -t wrb2006_to_fao90 -t wrb_fao90_desc -f /tmp/soil_id_db.dump
docker cp $(SOIL_ID_DB_CONTAINER):/tmp/soil_id_db.dump $(DATABASE_DUMP_FILE)
restore_soil_id_db:
pg_restore --dbname=$(DATABASE_URL) --single-transaction --clean --if-exists --no-owner $(DATABASE_DUMP_FILE)
psql $(DATABASE_URL) -c "CLUSTER hwsd2_segment USING hwsd2_segment_shape_idx;"
psql $(DATABASE_URL) -c "ANALYZE;"