AURORA-1677: Dockerfile fix
This commit is contained in:
parent
f29800e645
commit
cac2054e8a
@ -1,6 +1,6 @@
|
||||
# syntax=docker/dockerfile:1
|
||||
# Образ для dev и `make check-full`. Контекст сборки — корень репозитория tabular-parser.
|
||||
# Библиотека передаётся именованным контекстом arm_statements (см. make docker-build).
|
||||
# Библиотека передаётся именованным контекстом statements (см. make docker-build).
|
||||
# Платформенные пакеты raisa_* (Nexus) в образ не ставятся.
|
||||
FROM python:3.11-slim
|
||||
|
||||
@ -10,9 +10,9 @@ ENV PYTHONUNBUFFERED=1 \
|
||||
WORKDIR /app/api
|
||||
|
||||
COPY api/requirements.txt ./requirements.txt
|
||||
RUN --mount=type=bind,from=arm_statements,target=/tmp/arm_statements,rw \
|
||||
grep -Ev '^(raisa_|pylib_ai)' requirements.txt > /tmp/req.txt \
|
||||
&& pip install --no-cache-dir -r /tmp/req.txt /tmp/arm_statements \
|
||||
RUN --mount=type=bind,from=statements,target=/tmp/statements,rw \
|
||||
grep -v '^raisa_' requirements.txt > /tmp/req.txt \
|
||||
&& pip install --no-cache-dir -r /tmp/req.txt /tmp/statements \
|
||||
&& rm /tmp/req.txt
|
||||
|
||||
COPY api/ ./
|
||||
|
||||
8
Makefile
8
Makefile
@ -2,6 +2,7 @@
|
||||
VENV := api/.venv
|
||||
BIN := $(CURDIR)/$(VENV)/bin
|
||||
STATEMENTS_DIR ?= ../pylib_ai_arm_statements
|
||||
STATEMENTS_TAG ?= v0.1.1
|
||||
COMPOSE_FILE ?= ../docs/dev/docker-compose.yml
|
||||
|
||||
.PHONY: venv install lint test test-integration test-fixtures golden-update golden-check check docker-build check-full up
|
||||
@ -46,7 +47,12 @@ check: lint test
|
||||
|
||||
# Сборка образа из корня репозитория
|
||||
docker-build:
|
||||
docker build --build-context arm_statements="$(STATEMENTS_DIR)" -t tabular-parser .
|
||||
@release=$$(git -C "$(STATEMENTS_DIR)" rev-parse --verify "refs/tags/$(STATEMENTS_TAG)^{commit}") || \
|
||||
{ echo "Ошибка: в библиотеке отсутствует тег $(STATEMENTS_TAG); выполните git fetch --tags в $(STATEMENTS_DIR)" >&2; exit 1; }; \
|
||||
head=$$(git -C "$(STATEMENTS_DIR)" rev-parse HEAD) || exit 1; \
|
||||
[ "$$head" = "$$release" ] || \
|
||||
{ echo "Ошибка: HEAD библиотеки не совпадает с $(STATEMENTS_TAG)" >&2; exit 1; }
|
||||
docker build --build-context "statements=$(STATEMENTS_DIR)" -t tabular-parser .
|
||||
|
||||
# Полная проверка перед PR: быстрые проверки, затем NATS/MinIO из compose (make up), затем образ
|
||||
check-full: check test-integration docker-build
|
||||
|
||||
13
README.md
13
README.md
@ -97,7 +97,7 @@ openspec/ требования и дельта текущего ср
|
||||
| `make golden-check` | то же без записи; код возврата 1, если снимки расходятся с разбором |
|
||||
| `make check` | `make lint` + `make test` (включая идентичность копии контракта с `../docs/contracts`); с каталогом fixtures ≈ 95 с — из-за тестов на 82 файлах |
|
||||
| `make check-full` | `make check` + `make test-integration` + `docker build`; запускать перед PR (нужен поднятый compose, `make up`) |
|
||||
| `make docker-build` | собирает образ, передавая локальную библиотеку через `--build-context arm_statements="$(STATEMENTS_DIR)"` (нужен BuildKit) |
|
||||
| `make docker-build` | собирает образ, передавая локальную библиотеку через `--build-context "statements=$(STATEMENTS_DIR)"` (нужен BuildKit) |
|
||||
| `make up` | `docker compose -f ../docs/dev/docker-compose.yml up -d --wait postgres nats minio` |
|
||||
|
||||
Интеграционные тесты (`make test-integration`, `make check-full`) поднимают сервис в процессе теста и вступают в queue group `tabular-parser` на реальной шине: на шине compose не должно работать другого экземпляра tabular-parser (и наоборот: на время теста in-process воркер ответит ошибкой разбора (`UNSUPPORTED_FORMAT` / `UNREADABLE`) на реальные запросы других производителей).
|
||||
@ -544,3 +544,14 @@ ENV_FILE=.env.test .venv/bin/python -m src.parser.cli <файл> [--file-type XL
|
||||
`SERVICE_NAME` — имя сервиса в конвертах контракта (`service.name`); допустимо только `tabular-parser`, иное значение —
|
||||
ошибка конфигурации при старте. Queue group подписки NATS — константа `tabular-parser` в `src/core/nats.py`, настройкой
|
||||
не меняется.
|
||||
|
||||
Сборка Docker использует BuildKit-контекст `statements` из `STATEMENTS_DIR`
|
||||
(по умолчанию `../pylib_ai_arm_statements`). Другой путь:
|
||||
`make docker-build STATEMENTS_DIR=/путь/к/библиотеке`. Библиотека устанавливается
|
||||
из исходников вместе с requirements; её версия должна соответствовать закреплённой
|
||||
в requirements. Остальные зависимости загружаются из пакетного индекса.
|
||||
|
||||
Перед локальной сборкой `make docker-build` проверяет совпадение HEAD библиотеки
|
||||
с тегом `STATEMENTS_TAG` (по умолчанию `v0.1.1`). Получить тег:
|
||||
`git -C ../pylib_ai_arm_statements fetch origin --tags`.
|
||||
Незакоммиченные изменения разрешены и попадают в сборку из `STATEMENTS_DIR`.
|
||||
|
||||
@ -20,14 +20,14 @@
|
||||
|
||||
3. **Версия через API библиотеки.** `require_statements_version` продолжает вызывать `statements_version(path)` и запрещает старт при отсутствии версии. Меняются документация и RuntimeError: `библиотека arm_statements без VERSION и версии пакета: выполните make install`. VERSION сохраняет приоритет, метаданные дают fallback для установленного дистрибутива; прямое чтение метаданных в сервисе дублировало бы логику библиотеки. Тип поля контракта остаётся непустой строкой, JSON-схемы не редактируются.
|
||||
|
||||
4. **Именованный контекст BuildKit.** `make docker-build` передаёт `--build-context arm_statements="$(STATEMENTS_DIR)"`. Dockerfile подключает его через временный bind mount на шаге RUN и устанавливает `/tmp/arm_statements` вместе с отфильтрованными requirements. `rw` нужен сборочным инструментам для временных файлов; изменения mount не записываются обратно на хост и не становятся содержимым образа. Установленный пакет и его package data остаются в образе. Альтернатива расширения основного контекста на весь workspace меняет правила COPY и состав контекста; копирование checkout в слой добавляет ненужные исходники. Прямым вызовам Docker, внешним CI и Compose потребуется тот же именованный контекст; их конфигурация в этой задаче не менялась.
|
||||
4. **Именованный контекст BuildKit.** `make docker-build` передаёт `--build-context statements="$(STATEMENTS_DIR)"`. Dockerfile подключает его через временный bind mount на шаге RUN и устанавливает `/tmp/statements` вместе с отфильтрованными requirements. `rw` нужен сборочным инструментам для временных файлов; изменения mount не записываются обратно на хост и не становятся содержимым образа. Установленный пакет и его package data остаются в образе. Альтернатива расширения основного контекста на весь workspace меняет правила COPY и состав контекста; копирование checkout в слой добавляет ненужные исходники. Прямым вызовам Docker, внешним CI и Compose потребуется тот же именованный контекст; их конфигурация в этой задаче не менялась.
|
||||
|
||||
5. **Документация отражает библиотечную поставку.** README, CLAUDE.md, `api/rules/README.md`, комментарии в requirements-dev, проверке версии, тесте worker и модели `Service` обновлены. Архивные OpenSpec change и копии JSON-схем не переписываются. Внешнее описание поля как коммита требует согласования отдельным change в docs.
|
||||
|
||||
## Risks / Trade-offs
|
||||
|
||||
- [Нет локального checkout или неверный STATEMENTS_DIR] → установка завершается ошибкой; путь и команда переустановки описаны в README.
|
||||
- [Отличие локальной версии от pin] → перед сборкой проверять метаданные дистрибутива и `statements_version()`; автоматическая сверка не добавлялась.
|
||||
- [Отличие локальной версии от pin] → перед сборкой проверять метаданные дистрибутива и `statements_version()`; при Docker-сборке pip автоматически проверяет соответствие локальной версии pin из requirements.
|
||||
- [Версия 0.1.1 не идентифицирует локальные изменения исходников] → переустановка принудительная, воспроизводимый релиз требует дисциплины версий библиотеки; Git SHA больше не является обязательным форматом поля.
|
||||
- [Нет BuildKit или не передан именованный контекст] → использовать `make docker-build`; в других системах сборки явно передавать контекст.
|
||||
- [Нет маркера типов у библиотеки] → mypy проверяет код сервиса, поведение интеграции подтверждают тесты адаптеров.
|
||||
|
||||
@ -93,7 +93,7 @@ NATS и S3; воркер MUST NOT зависеть от конкретной р
|
||||
- **THEN** библиотека переустановлена из указанного пути в `api/.venv` и изменения доступны сервису
|
||||
|
||||
### Requirement: Библиотека форм в контейнерном образе
|
||||
`make docker-build` SHALL передавать `STATEMENTS_DIR` именованным контекстом BuildKit `arm_statements`. Сборка SHALL устанавливать библиотеку из этого контекста вместе с публичными зависимостями, без загрузки `pylib_ai*` из PyPI. Образ SHALL содержать установленный пакет и его словари, доступные при запуске без исходной папки хоста.
|
||||
`make docker-build` SHALL передавать `STATEMENTS_DIR` именованным контекстом BuildKit `statements`. Сборка SHALL устанавливать библиотеку из этого контекста вместе с публичными зависимостями, без загрузки `pylib_ai*` из PyPI. Образ SHALL содержать установленный пакет и его словари, доступные при запуске без исходной папки хоста.
|
||||
|
||||
#### Scenario: Сборка и запуск с локальной библиотекой
|
||||
- **WHEN** образ собран через `make docker-build` при доступном BuildKit и локальной библиотеке
|
||||
@ -101,5 +101,5 @@ NATS и S3; воркер MUST NOT зависеть от конкретной р
|
||||
|
||||
#### Scenario: Прямая сборка
|
||||
- **WHEN** сборка запускается напрямую командой `docker build`
|
||||
- **THEN** вызывающая сторона SHALL передать `--build-context arm_statements=<путь-к-библиотеке>`; отсутствие контекста не заменяется загрузкой библиотеки из PyPI
|
||||
- **THEN** вызывающая сторона SHALL передать `--build-context statements=<путь-к-библиотеке>`; отсутствие контекста не заменяется загрузкой библиотеки из PyPI
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user