offline-docker-cli 2.2.2__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (64) hide show
  1. offline_docker_cli-2.2.2/LICENSE +21 -0
  2. offline_docker_cli-2.2.2/PKG-INFO +417 -0
  3. offline_docker_cli-2.2.2/README.md +385 -0
  4. offline_docker_cli-2.2.2/pyproject.toml +46 -0
  5. offline_docker_cli-2.2.2/setup.cfg +4 -0
  6. offline_docker_cli-2.2.2/src/offline_docker/__init__.py +3 -0
  7. offline_docker_cli-2.2.2/src/offline_docker/__main__.py +4 -0
  8. offline_docker_cli-2.2.2/src/offline_docker/actions.py +173 -0
  9. offline_docker_cli-2.2.2/src/offline_docker/build.py +245 -0
  10. offline_docker_cli-2.2.2/src/offline_docker/cli.py +486 -0
  11. offline_docker_cli-2.2.2/src/offline_docker/config.py +692 -0
  12. offline_docker_cli-2.2.2/src/offline_docker/configure.py +282 -0
  13. offline_docker_cli-2.2.2/src/offline_docker/context.py +111 -0
  14. offline_docker_cli-2.2.2/src/offline_docker/defaults.py +48 -0
  15. offline_docker_cli-2.2.2/src/offline_docker/discover.py +139 -0
  16. offline_docker_cli-2.2.2/src/offline_docker/docker_cmd.py +136 -0
  17. offline_docker_cli-2.2.2/src/offline_docker/download_debs.py +142 -0
  18. offline_docker_cli-2.2.2/src/offline_docker/download_images.py +26 -0
  19. offline_docker_cli-2.2.2/src/offline_docker/download_npm.py +106 -0
  20. offline_docker_cli-2.2.2/src/offline_docker/download_trivy.py +90 -0
  21. offline_docker_cli-2.2.2/src/offline_docker/download_wheels.py +363 -0
  22. offline_docker_cli-2.2.2/src/offline_docker/download_yarn.py +208 -0
  23. offline_docker_cli-2.2.2/src/offline_docker/ensure_base.py +61 -0
  24. offline_docker_cli-2.2.2/src/offline_docker/hooks.py +84 -0
  25. offline_docker_cli-2.2.2/src/offline_docker/init_cmd.py +54 -0
  26. offline_docker_cli-2.2.2/src/offline_docker/load_images.py +34 -0
  27. offline_docker_cli-2.2.2/src/offline_docker/oc_discovery.py +206 -0
  28. offline_docker_cli-2.2.2/src/offline_docker/resolve.py +306 -0
  29. offline_docker_cli-2.2.2/src/offline_docker/scan.py +496 -0
  30. offline_docker_cli-2.2.2/src/offline_docker/sources/__init__.py +18 -0
  31. offline_docker_cli-2.2.2/src/offline_docker/sources/base.py +18 -0
  32. offline_docker_cli-2.2.2/src/offline_docker/sources/filesystem.py +17 -0
  33. offline_docker_cli-2.2.2/src/offline_docker/sources/nexus.py +61 -0
  34. offline_docker_cli-2.2.2/src/offline_docker/sources/nexus_client.py +67 -0
  35. offline_docker_cli-2.2.2/src/offline_docker/sources/proget.py +49 -0
  36. offline_docker_cli-2.2.2/src/offline_docker/sources/proget_client.py +48 -0
  37. offline_docker_cli-2.2.2/src/offline_docker/sources/upstream.py +36 -0
  38. offline_docker_cli-2.2.2/src/offline_docker/status.py +247 -0
  39. offline_docker_cli-2.2.2/src/offline_docker/sync_cache.py +125 -0
  40. offline_docker_cli-2.2.2/src/offline_docker/trivy_scan.py +86 -0
  41. offline_docker_cli-2.2.2/src/offline_docker/tui/__init__.py +19 -0
  42. offline_docker_cli-2.2.2/src/offline_docker/tui/app.py +56 -0
  43. offline_docker_cli-2.2.2/src/offline_docker/tui/runner.py +87 -0
  44. offline_docker_cli-2.2.2/src/offline_docker/tui/screens.py +333 -0
  45. offline_docker_cli-2.2.2/src/offline_docker/user_config.py +89 -0
  46. offline_docker_cli-2.2.2/src/offline_docker/utils.py +73 -0
  47. offline_docker_cli-2.2.2/src/offline_docker/validate.py +53 -0
  48. offline_docker_cli-2.2.2/src/offline_docker/wheel_prune.py +141 -0
  49. offline_docker_cli-2.2.2/src/offline_docker_cli.egg-info/PKG-INFO +417 -0
  50. offline_docker_cli-2.2.2/src/offline_docker_cli.egg-info/SOURCES.txt +62 -0
  51. offline_docker_cli-2.2.2/src/offline_docker_cli.egg-info/dependency_links.txt +1 -0
  52. offline_docker_cli-2.2.2/src/offline_docker_cli.egg-info/entry_points.txt +2 -0
  53. offline_docker_cli-2.2.2/src/offline_docker_cli.egg-info/requires.txt +11 -0
  54. offline_docker_cli-2.2.2/src/offline_docker_cli.egg-info/top_level.txt +1 -0
  55. offline_docker_cli-2.2.2/tests/test_actions.py +64 -0
  56. offline_docker_cli-2.2.2/tests/test_cli.py +132 -0
  57. offline_docker_cli-2.2.2/tests/test_config.py +187 -0
  58. offline_docker_cli-2.2.2/tests/test_download_npm.py +19 -0
  59. offline_docker_cli-2.2.2/tests/test_hooks.py +147 -0
  60. offline_docker_cli-2.2.2/tests/test_init_scan.py +116 -0
  61. offline_docker_cli-2.2.2/tests/test_oc_discovery.py +72 -0
  62. offline_docker_cli-2.2.2/tests/test_resolve.py +300 -0
  63. offline_docker_cli-2.2.2/tests/test_status.py +68 -0
  64. offline_docker_cli-2.2.2/tests/test_wheel_prune.py +78 -0
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 D.Shapovalov
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,417 @@
1
+ Metadata-Version: 2.4
2
+ Name: offline-docker-cli
3
+ Version: 2.2.2
4
+ Summary: Universal Docker offline cache, build and Trivy scan CLI
5
+ Author-email: "D.Shapovalov" <d.shapovalov@vitebsk.energo.net>
6
+ License-Expression: MIT
7
+ Project-URL: Homepage, https://github.com/DzmitrySha/offline-docker-cli
8
+ Project-URL: Repository, https://github.com/DzmitrySha/offline-docker-cli
9
+ Project-URL: Issues, https://github.com/DzmitrySha/offline-docker-cli/issues
10
+ Project-URL: Changelog, https://github.com/DzmitrySha/offline-docker-cli/blob/main/CHANGELOG.md
11
+ Keywords: docker,offline,trivy,cli
12
+ Classifier: Programming Language :: Python :: 3
13
+ Classifier: Programming Language :: Python :: 3.11
14
+ Classifier: Programming Language :: Python :: 3.12
15
+ Classifier: Environment :: Console
16
+ Classifier: Intended Audience :: Developers
17
+ Classifier: Operating System :: OS Independent
18
+ Classifier: Topic :: System :: Software Distribution
19
+ Classifier: Topic :: Utilities
20
+ Requires-Python: >=3.11
21
+ Description-Content-Type: text/markdown
22
+ License-File: LICENSE
23
+ Provides-Extra: yaml
24
+ Requires-Dist: pyyaml>=6.0; extra == "yaml"
25
+ Provides-Extra: tui
26
+ Requires-Dist: textual>=0.80; extra == "tui"
27
+ Provides-Extra: dev
28
+ Requires-Dist: pyyaml>=6.0; extra == "dev"
29
+ Requires-Dist: textual>=0.80; extra == "dev"
30
+ Requires-Dist: pytest>=8; extra == "dev"
31
+ Dynamic: license-file
32
+
33
+ <div align="center">
34
+
35
+ <h1>offdock</h1>
36
+
37
+ Универсальная Python CLI для portable offline-cache, офлайн-сборки Docker-образов и Trivy-сканирования Docker-проектов.<br>
38
+ Весь конфиг живёт в целевом репозитории (`.offline-docker.json`); CLI не содержит настроек конкретных проектов.
39
+
40
+ <a href="LICENSE"><img src="https://img.shields.io/badge/license-MIT-2dd4bf?style=flat-square" alt="License: MIT"></a>
41
+ <img src="https://img.shields.io/badge/python-3.11%2B-3776AB?style=flat-square&logo=python&logoColor=white" alt="Python 3.11+">
42
+ <img src="https://img.shields.io/badge/Docker-ready-2496ED?style=flat-square&logo=docker&logoColor=white" alt="Docker">
43
+ <img src="https://img.shields.io/badge/Trivy-scan-1904DA?style=flat-square" alt="Trivy">
44
+ <img src="https://img.shields.io/badge/uv-locked-DE5FE1?style=flat-square" alt="uv">
45
+ <img src="https://img.shields.io/badge/i18n-RU%20%2F%20EN-22c55e?style=flat-square" alt="RU / EN">
46
+
47
+ <sub><a href=".github/README.md">English</a> · Русская версия · <a href="docs/ru/CONTRIBUTING.md">Участие</a> · <a href="docs/ru/SECURITY.md">Безопасность</a> · <a href="docs/ru/CHANGELOG.md">Changelog</a></sub>
48
+
49
+ </div>
50
+
51
+ ---
52
+
53
+ ## Содержание
54
+
55
+ - [Как это работает](#как-это-работает)
56
+ - [Возможности](#возможности)
57
+ - [Установка](#установка)
58
+ - [Быстрый старт](#быстрый-старт)
59
+ - [Команды](#команды)
60
+ - [Общие флаги](#общие-флаги)
61
+ - [Примеры команд](#примеры-команд)
62
+ - [Конфигурация целевого проекта](#конфигурация-целевого-проекта)
63
+ - [Источники пакетов (local / ProGet / Nexus)](#источники-пакетов-local--proget--nexus)
64
+ - [Env-переменные](#env-переменные)
65
+ - [Требования](#требования)
66
+ - [Разработка и тесты](#разработка-и-тесты)
67
+ - [Структура репозитория](#структура-репозитория)
68
+ - [Ограничения](#ограничения)
69
+ - [Участие](#участие)
70
+ - [Лицензия](#лицензия)
71
+ - [Changelog](#changelog)
72
+
73
+ ## Как это работает
74
+
75
+ ```mermaid
76
+ flowchart LR
77
+ proj[целевой репозиторий<br/>.offline-docker.json] -->|discover| plan[cache plan]
78
+ net[(PyPI / npm / apt / registry)] -->|cache| bundle[(offline-cache/)]
79
+ plan --> bundle
80
+ bundle -->|перенос вручную| offline[офлайн-машина]
81
+ offline -->|cache load| images[docker images]
82
+ offline -->|build| images
83
+ images -->|up / down| stack[Docker Compose]
84
+ bundle -->|scan| trivy[Trivy offline DB]
85
+ ```
86
+
87
+ Бандл-папка `offline-cache/` переносится на офлайн-машину вручную — постоянного зеркала/registry-сервиса нет. Compose-файлы склеиваются из `compose_build` / `compose_up_offline` конфига проекта.
88
+
89
+ ## Возможности
90
+
91
+ | Возможность | Что даёт |
92
+ |-------------|----------|
93
+ | Project-scoped конфиг | Всё в целевом репозитории: `.offline-docker.json` (или `.yaml`); CLI не хранит проектные настройки |
94
+ | Portable offline-cache | debs, wheels, npm, yarn, docker images, Trivy DB в одной переносимой папке |
95
+ | Источники local → ProGet → Nexus | `resolve.order`, user-level `sources.json`, project override |
96
+ | `cache wheels` | Python берётся из базового образа + ABI-проверка версии |
97
+ | `cache debs` | Кэш привязан к дистрибутиву гостевого образа (`debs/.base-os`) |
98
+ | `hooks.after_cache` + `validation.critical_vendor` | Проектные хуки после кэша и проверка критичных vendor-артефактов |
99
+ | `build` | Офлайн-сборка с merge-файлами и списком сервисов |
100
+ | `up` / `down` | Offline / lab / online режимы Compose |
101
+ | Trivy-скан | Офлайн-БД и лог в `{log_dir}` |
102
+ | Опциональный Textual TUI | Статус кэша, меню команд и live-лог поверх тех же действий CLI |
103
+
104
+ ## Установка
105
+
106
+ ### Вариант A — без pip (рекомендуется в corp-сети)
107
+
108
+ ```powershell
109
+ # из корня репозитория offline-docker-cli
110
+ .\offdock.cmd discover -p ..\my-project
111
+ ```
112
+
113
+ ### Вариант B — pip (если PyPI доступен)
114
+
115
+ ```powershell
116
+ cd offline-docker-cli
117
+ pip install -e .
118
+ pip install -e ".[yaml]" # опционально: .offline-docker.yaml
119
+ pip install -e ".[tui]" # опционально: Textual TUI
120
+ offdock configure # ProGet/Nexus URL (Enter = только offline-cache)
121
+ ```
122
+
123
+ ### Опциональный TUI
124
+
125
+ Терминальный UI поверх тех же команд (статус кэша, меню, live-лог). CLI остаётся основным интерфейсом.
126
+
127
+ ```powershell
128
+ # Установка (для использования — без -e, чтобы пакет жил в site-packages)
129
+ pip install .\[tui]
130
+
131
+ # Запуск
132
+ offdock tui -p .
133
+ ```
134
+
135
+ **Важно:** `pip install -e ".[tui]"` (editable) привязывает пакет к папке исходников — если папку переместить/удалить, CLI сломается. Для использования рекомендуется **обычная установка** (без `-e`).
136
+ Для разработки самого CLI — тогда `-e`.
137
+
138
+ ## Быстрый старт
139
+
140
+ Сгенерировать черновик конфига (рекурсивный scan) или скопировать шаблон из `examples/`:
141
+
142
+ ```powershell
143
+ cd ..\my-project
144
+ offdock init -p . # → .offline-docker.json (или .generated.json)
145
+ offdock discover -p .
146
+ offdock cache -p .
147
+ offdock cache check -p . # проверка полноты offline-cache
148
+ offdock build -p .
149
+ offdock up -p .
150
+ ```
151
+
152
+ ### `init` — черновик конфига
153
+
154
+ Рекурсивно ищет compose, Dockerfile, python/frontend lock-файлы и пишет JSON по схеме example.
155
+
156
+ | Ситуация | Файл |
157
+ |----------|------|
158
+ | Нет `.offline-docker.json` / `.yaml` | создаётся `.offline-docker.json` |
159
+ | Канон уже есть | пишется `.offline-docker.generated.json` (канон **не** затирается) |
160
+
161
+ В JSON есть секция `_init.gaps` и в stdout — блок `Missing / to fix:` (нет `Dockerfile.*.offline`, offline-compose и т.д.).
162
+ **Не** генерируются сами offline-Dockerfile / compose — только пути и список доработок.
163
+
164
+ ```powershell
165
+ offdock init -p . --dry-run # только отчёт
166
+ ```
167
+
168
+ ## Команды
169
+
170
+ | Команда | Описание |
171
+ |---------|----------|
172
+ | `configure` | User-level ProGet/Nexus (или local-only) |
173
+ | `tui` | Интерактивный Textual TUI (нужен `pip install …[tui]`) |
174
+ | `init` | Рекурсивный scan → черновик `.offline-docker.json` (+ gaps) |
175
+ | `discover` | Compose, Python/npm lock, Dockerfile, APT-пакеты, sources, Missing |
176
+ | `cache` | Полный download offline-cache |
177
+ | `cache wheels\|debs\|npm\|yarn\|images\|trivy` | Частичный download |
178
+ | `cache check` | Проверка полноты кэша |
179
+ | `cache load` | `docker load` из `offline-cache/docker/` |
180
+ | `build [base backend frontend]` | Офлайн-сборка |
181
+ | `up [--lab\|--online] […]` | Compose up (offline / lab / online) |
182
+ | `down [--lab\|--online] [services]` | Compose down того же стека |
183
+ | `scan [trivy] <backend\|frontend> [image]` | Скан образа (default: trivy) |
184
+
185
+ ## Общие флаги
186
+
187
+ - `--project PATH` / `-p` — корень целевого проекта (default: текущий каталог)
188
+ - `--config PATH` — явный путь к конфигу (default: `.offline-docker.json` в корне проекта)
189
+
190
+ Справка и примеры — в `--help` (общий и по команде):
191
+
192
+ ```powershell
193
+ offdock --help
194
+ offdock scan --help
195
+ offdock up --help
196
+ ```
197
+
198
+ ## Примеры команд
199
+
200
+ Пути относительны: команды запускаются из корня `offline-docker-cli`, целевой проект — соседний каталог `my-project`.
201
+
202
+ ### Подготовка и сборка
203
+
204
+ ```powershell
205
+ # Полный цикл подготовки кэша (на машине с интернетом)
206
+ offdock cache -p ..\my-project
207
+
208
+ # На офлайн-машине: загрузить образы и собрать
209
+ offdock cache load -p .
210
+ offdock build -p .
211
+ offdock cache check -p .
212
+
213
+ # Собрать только backend (без base/frontend)
214
+ offdock build -p . backend
215
+ ```
216
+
217
+ ### `up` / `down` и режимы `--lab` / `--online`
218
+
219
+ Обычный offline-стек (merge-файлы из `compose_up_offline` в конфиге):
220
+
221
+ ```powershell
222
+ offdock up -p .
223
+ offdock down -p .
224
+ ```
225
+
226
+ Home lab — дополнительно подключается `docker-compose.lab.yml`:
227
+
228
+ ```powershell
229
+ offdock up -p . --lab
230
+ offdock down -p . --lab
231
+ ```
232
+
233
+ Online — только `compose_online`:
234
+
235
+ ```powershell
236
+ offdock up -p . --online
237
+ offdock down -p . --online
238
+ ```
239
+
240
+ Что нужно в **целевом проекте** для `--lab`:
241
+
242
+ 1. Файл `docker-compose.lab.yml` в корне репозитория (override для домашней среды).
243
+ 2. В `.offline-docker.json` — секция `compose_up_offline_lab` со списком compose-файлов (см. `examples/offline-docker.json.example`). Если секция не задана, CLI сам добавит `docker-compose.lab.yml` к списку из `compose_up_offline`.
244
+
245
+ Подробнее о полях конфига: [`examples/README.md`](examples/README.md).
246
+
247
+ Дополнительные флаги:
248
+
249
+ ```powershell
250
+ # Не пересобирать образы (уже собраны)
251
+ offdock up -p . --no-build
252
+
253
+ # Поднять только backend, без пересоздания зависимостей
254
+ offdock up -p . --no-deps backend
255
+
256
+ # Lab + только frontend
257
+ offdock up -p . --lab frontend
258
+
259
+ # Остановить отдельные сервисы
260
+ offdock down -p . backend frontend
261
+ ```
262
+
263
+ ### `scan`
264
+
265
+ **Обязательный** target: `backend` или `frontend`.
266
+ Опционально — сканер (`trivy`, default) и тег образа.
267
+
268
+ ```powershell
269
+ # Скан backend-образа из конфига (images.backend)
270
+ offdock scan backend
271
+
272
+ # Явно указать сканер
273
+ offdock scan trivy frontend
274
+
275
+ # Явный тег образа
276
+ offdock scan trivy backend myapp-backend:cuda12
277
+ ```
278
+
279
+ Перед сканом:
280
+
281
+ 1. Образ должен существовать локально (`docker images`) — обычно после `build`.
282
+ 2. БД Trivy в `offline-cache/trivy/` — `cache trivy` или `cache` (на машине с интернетом); на офлайн-машине CLI попытается использовать кэш и предупредит, если БД устарела.
283
+ 3. Образ сканера `aquasec/trivy:latest` — в `docker_images` конфига, загружается через `cache load`.
284
+
285
+ Параметры сканирования (`severity`, `scanners`, `db_max_age_days`) — в секции `trivy` конфига:
286
+
287
+ ```json
288
+ "trivy": {
289
+ "scanner_image": "aquasec/trivy:latest",
290
+ "db_max_age_days": 7,
291
+ "severity": "HIGH,CRITICAL",
292
+ "scanners": "vuln"
293
+ }
294
+ ```
295
+
296
+ Лог пишется в `{log_dir}/trivy-scan-{backend|frontend}.log` (default: `storage/logs/`).
297
+
298
+ ## Конфигурация целевого проекта
299
+
300
+ 1. **`.offline-docker.json`** (или `.offline-docker.yaml`) в корне репозитория — **канон**
301
+ 2. **Auto-discovery** — fallback, если конфига нет (для `discover`; для build рекомендуется конфиг)
302
+
303
+ Пример: `examples/offline-docker.json.example` — скопируйте в корень проекта как `.offline-docker.json`.
304
+
305
+ ## Источники пакетов (local / ProGet / Nexus)
306
+
307
+ По умолчанию CLI использует **только локальный** `offline-cache/`.
308
+
309
+ После установки настройте корпоративные реестры (один раз на машину):
310
+
311
+ ```powershell
312
+ offdock configure
313
+ # заполнение кэша с интернета (local + PyPI/npmjs):
314
+ offdock configure --with-upstream
315
+ # только offline-cache (корп/офлайн VM):
316
+ offdock configure --local-only
317
+ offdock configure --proget-url https://proget.example.com --nexus-url http://nexus.example.com:8081
318
+ ```
319
+
320
+ Конфиг пишется в user-level файл (не в example проекта):
321
+
322
+ - Linux/macOS: `~/.config/offline-docker/sources.json`
323
+ - Windows: `%APPDATA%\offline-docker\sources.json`
324
+ - override каталога: `OFFLINE_DOCKER_CONFIG_DIR`
325
+
326
+ Приоритет: **project `.offline-docker.json` → секция `cache`** перекрывает user-config; иначе user; иначе local-only.
327
+
328
+ | Режим | Когда |
329
+ |-------|--------|
330
+ | `--with-upstream` | Машина с сетью: `cache` / `cache wheels` тянет с PyPI/npmjs в `offline-cache/` |
331
+ | `--local-only` | Офлайн/корп VM: сборка только из уже скачанного кэша |
332
+ | ProGet/Nexus | Корп. зеркала; порядок в `resolve.order` |
333
+
334
+ Порядок поиска задаётся `resolve.order` (например `local,upstream` или `local,proget,nexus`). `cache wheels` / `cache npm` ходят по цепочке index URL и дописывают артефакты в локальную папку (`fill_local`).
335
+
336
+ Если в `sources.json` стоит **local-only**, `cache wheels` всё равно временно добавляет PyPI/PyTorch (с WARN) и перед скачиванием удаляет **устаревшие** wheels, чья версия не совпадает с pin в lock/requirements (типичный случай `protobuf==7.x` при старом `6.x` в кэше).
337
+
338
+ Auth (опционально, через env, не в JSON): `PROGET_API_KEY`, `NEXUS_AUTH` (`user:pass` или Bearer).
339
+
340
+ Для Nexus по HTTP pip автоматически получает `--trusted-host`; npm — `strict-ssl false`.
341
+
342
+ Env: `OFFLINE_RESOLVE_ORDER=local,proget,nexus` — временный override порядка.
343
+
344
+ Шаблон проекта (`examples/offline-docker.json.example`) **нейтральный** — без корпоративных URL.
345
+
346
+ ## Env-переменные
347
+
348
+ | Переменная | Назначение |
349
+ |------------|------------|
350
+ | `OFFLINE_CACHE` | Путь к offline-cache (override) |
351
+ | `{APP_NAME}_OFFLINE_CACHE` | Alias из `app_name` в конфиге |
352
+ | `OFFLINE_DOCKER_CONFIG_DIR` | Каталог user-config (`sources.json`) |
353
+ | `OFFLINE_RESOLVE_ORDER` | Порядок sources через запятую |
354
+ | `PROGET_API_KEY` / `NEXUS_AUTH` | Auth для remote |
355
+ | `PYTORCH_INDEX` | Index URL для torch wheels |
356
+ | `PYPI_INDEX` | Force primary PyPI index |
357
+ | `DOCKER_BUILDKIT` | `1` для build |
358
+
359
+ ## Требования
360
+
361
+ - Python 3.11+
362
+ - Docker (CLI на PATH)
363
+
364
+ ## Разработка и тесты
365
+
366
+ ```bash
367
+ uv sync --extra dev # .venv с pyyaml, textual, pytest
368
+ uv run pytest -q # весь набор tests/
369
+ uv run offdock --version
370
+ uv run offdock --help
371
+ ```
372
+
373
+ - После правок зависимостей — `uv lock` и коммит `uv.lock`.
374
+ - Версия синхронизируется в `pyproject.toml` и `src/offline_docker/__init__.py`.
375
+ - Проверка на реальном проекте: `offdock discover -p ..\my-project`.
376
+ - Запуск без установки — `offdock.cmd` (`PYTHONPATH=src`, `python -m offline_docker`).
377
+
378
+ ## Структура репозитория
379
+
380
+ ```
381
+ offline-docker-cli/
382
+ ├── .github/ # EN README, шаблоны issue/PR, GitHub Actions
383
+ ├── docs/ru/ # RU-версии CONTRIBUTING / SECURITY / CHANGELOG
384
+ ├── examples/ # шаблоны .offline-docker.json
385
+ ├── src/offline_docker/ # CLI, cache, build, scan, TUI
386
+ ├── tests/ # pytest
387
+ ├── .gitattributes
388
+ ├── .gitlab-ci.yml # GitLab CI
389
+ ├── AGENTS.md # правила для агентов
390
+ ├── CONTRIBUTING.md # EN
391
+ ├── SECURITY.md # EN
392
+ ├── CHANGELOG.md # EN
393
+ ├── LICENSE
394
+ ├── offdock.cmd # запуск без установки (Windows)
395
+ ├── pyproject.toml
396
+ └── README.md # RU (этот файл)
397
+ ```
398
+
399
+ ## Ограничения
400
+
401
+ - Не LAN-зеркало: portable бандл, без постоянного registry-сервиса.
402
+ - Для `build` / `up` нужен Docker.
403
+ - Trivy DB стареет; `db_max_age_days` только предупреждает, не блокирует.
404
+ - Образы тянутся по тегу (digest не пиннится).
405
+ - Конфиги конкретных проектов в CLI не хранятся.
406
+
407
+ ## Участие
408
+
409
+ Правила разработки и проверки — [docs/ru/CONTRIBUTING.md](docs/ru/CONTRIBUTING.md). Политика безопасности — [docs/ru/SECURITY.md](docs/ru/SECURITY.md); уязвимости не публикуйте в публичном issue.
410
+
411
+ ## Лицензия
412
+
413
+ [MIT](LICENSE) © 2026 D.Shapovalov.
414
+
415
+ ## Changelog
416
+
417
+ Полная история изменений — [docs/ru/CHANGELOG.md](docs/ru/CHANGELOG.md).