diff --git a/doc/descriptions/function-lifecycle-full.md b/doc/descriptions/function-lifecycle-full.md
new file mode 100644
index 0000000..e43b39c
--- /dev/null
+++ b/doc/descriptions/function-lifecycle-full.md
@@ -0,0 +1,355 @@
+# Полный жизненный цикл функции в Fission Console
+
+Актуально: **v1.3.56**, май 2026
+
+---
+
+## 1. Два способа создания функции
+
+| Способ | Content-Type | Обработчик |
+|--------|-------------|------------|
+| **Inline-код** (редактор) | `application/json` | `handleCreateFunction` → `handleCreateFunctionFromCode` |
+| **Архив** (zip-файл) | `multipart/form-data` | `handleCreateFunction` → `handleCreateFunctionFromArchive` |
+
+Определяется автоматически по заголовку `Content-Type` в `handleCreateFunction` (handlers.go ~строка 343).
+
+---
+
+## 2. Создание из inline-кода (шаг за шагом)
+
+### 2.1 UI → Backend
+
+**Файл:** `console/ui/js/functions.js` → `submitCreateFunction()`
+
+1. Читает поля: `name`, `language`, `entrypoint`, `route`, `methods`, `timeout`, `code` (из CodeMirror)
+2. Отправляет `POST /console/api/functions` с `Content-Type: application/json`
+
+### 2.2 Backend обработка
+
+**Файл:** `console/internal/api/handlers.go` → `handleCreateFunction` (строка ~343)
+
+```
+POST /console/api/functions (JSON)
+ ↓
+Валидация имени (regex ^[a-z0-9]([a-z0-9-]*[a-z0-9])?$, max 57 символов)
+ ↓
+EnsureUserNS → создаёт K8s namespace если не существует
+ ↓
+EnsureEnvironment → создаёт Fission Environment CRD если не существует
+ ↓
+buildDeployArchive(lang, code) → упаковывает код в байты
+ ↓
+buildDeploySpec(ctx, bytes) → uploadToStoragesvc → S3
+ ↓
+Создаёт Fission Package CRD (type: url → S3)
+ ↓
+Создаёт Fission Function CRD (ссылается на Package)
+ ↓
+Создаёт Fission HTTPTrigger CRD (роут)
+ ↓
+Аннотация fission-console/source-type = "code"
+```
+
+### 2.3 buildDeployArchive — упаковка кода
+
+**Файл:** `console/internal/api/handlers.go` → `buildDeployArchive()`
+
+| Язык | Что происходит |
+|------|---------------|
+| Python | код → сырые байты (*.py файл) |
+| Node.js | код → zip с `package.json` + `main.js` (ESM wrapper) |
+| PHP | код → zip с `main.php` |
+| Ruby | код → zip с `handler.rb` |
+| Go | отдельный путь: `BuildGoSourceZip` → source package → builder job |
+
+### 2.4 Entrypoint по умолчанию
+
+**Файл:** `console/internal/runtime/` → `DefaultEntrypoint(lang)`
+
+| Язык | Entrypoint по умолчанию |
+|------|------------------------|
+| python | `user.main` |
+| nodejs | `main` |
+| go | `Handler` |
+| php | `main` |
+| ruby | `main` |
+
+---
+
+## 3. Создание из архива (шаг за шагом)
+
+### 3.1 UI → Backend
+
+**Файл:** `console/ui/js/fn-archive.js` → `submitCreateArchive()`
+
+1. Читает поля: `name`, `language`, `entrypoint`, `route`, `methods`, `timeout`
+2. Читает файл из ``
+3. **Валидация на UI:** файл должен заканчиваться на `.zip` — иначе ошибка до отправки
+4. Отправляет `POST /console/api/functions` с `Content-Type: multipart/form-data`
+
+### 3.2 Backend обработка
+
+**Файл:** `console/internal/api/handlers.go` → `handleCreateFunctionFromArchive()` (строка ~1302)
+
+```
+POST /console/api/functions (multipart/form-data)
+ ↓
+ParseMultipartForm (лимит 32 MB)
+ ↓
+Валидация имени
+ ↓
+r.FormFile("archive") → читает байты архива
+ ↓
+⛔ ПРОВЕРКА magic bytes: первые 2 байта должны быть 0x50 0x4B (PK = zip)
+ Если нет → HTTP 400 "загруженный файл не является валидным zip-архивом"
+ ↓
+EnsureUserNS
+ ↓
+EnsureEnvironment (по полю "language")
+ ↓
+buildDeploySpec(ctx, archiveBytes) → uploadToStoragesvc → S3
+ ↓
+Создаёт Fission Package CRD (type: url → S3)
+ ↓
+Создаёт Fission Function CRD
+ ↓
+Создаёт Fission HTTPTrigger CRD
+ ↓
+Аннотация fission-console/source-type = "archive"
+ ↓
+Аннотация fission-console/archive-file = <оригинальное имя файла>
+```
+
+---
+
+## 4. Загрузка в S3 через storagesvc
+
+**Файл:** `console/internal/api/handlers.go` → `uploadToStoragesvc()`
+
+```
+Входные данные: []byte (байты zip-архива)
+ ↓
+Строим multipart/form-data вручную:
+ boundary = "fission" + UnixNano
+ поле: name="uploadfile", filename="archive.zip"
+ Content-Type: application/octet-stream
+ тело: байты архива
+ ↓
+POST http://storagesvc.fission.svc.cluster.local/v1/archive
+ заголовок X-File-Size: <размер байт>
+ ↓
+Storagesvc сохраняет в S3 (bucket: sless-functions)
+ ↓
+Ответ: {"id": "fission/UUID"}
+ ↓
+Возвращаем URL: http://storagesvc.../v1/archive?id=fission/UUID
+```
+
+**Если storagesvcURL не задан** → fallback на `type: literal` (base64 в etcd). Нежелательно для больших файлов.
+
+**Переменная окружения:** `STORAGESVC_URL=http://storagesvc.fission.svc.cluster.local`
+
+### 4.1 Удаление из S3
+
+При удалении функции → `deleteFromStoragesvc()`:
+```
+DELETE http://storagesvc.../v1/archive?id=fission/UUID
+```
+Best-effort: ошибка логируется но не прерывает удаление Function/Package CRD.
+
+---
+
+## 5. Environment — КРИТИЧЕСКИ ВАЖНО
+
+**Файл:** `console/internal/fission/environment.go` → `EnsureEnvironment()`
+**Конфиг образов:** `console/internal/model/types.go` → `LangEnvMap`
+
+### 5.1 Lazy creation
+
+Environment создаётся **только когда пользователь создаёт первую функцию** на языке X в своём namespace. Не заранее — экономия ресурсов.
+
+### 5.2 Текущие образы (АКТУАЛЬНО)
+
+```go
+var LangEnvMap = map[string]LangEnvDef{
+ "python": {Image: "naeel/fission-python-env:v1.0"}, // ⛔ НЕ МЕНЯТЬ НА ОФИЦИАЛЬНЫЙ
+ "nodejs": {Image: "ghcr.io/fission/node-env"},
+ "go": {Image: "ghcr.io/fission/go-env", BuilderImage: "naeel/go-builder-fast:v1"},
+ "php": {Image: "ghcr.io/fission/php-env"},
+ "ruby": {Image: "ghcr.io/fission/ruby-env"},
+}
+```
+
+### 5.3 ⛔⛔⛔ PYTHON — ТОЛЬКО НАШ ОБРАЗ
+
+`naeel/fission-python-env:v1.0` содержит патч `inspect.signature`:
+
+```python
+def _count_required_params(func):
+ # inspect.signature → считает обязательные аргументы
+
+def userfunc_call(self, *args, **kwargs):
+ required = _count_required_params(self.userfunc)
+ if required == 0: return self.userfunc() # def main():
+ elif required == 1: return self.userfunc(request) # def main(request):
+ elif required >= 2: return self.userfunc(request, {}) # def main(event, context):
+```
+
+**Официальный `ghcr.io/fission/python-env`** вызывает `userfunc()` без аргументов → `TypeError: missing 2 required positional arguments` → HTTP 500 для любой функции `def main(event, context)`.
+
+### 5.4 Если environment уже создан с неправильным образом
+
+```bash
+kubectl patch environment -n console-python-env --type=json \
+ -p '[{"op":"replace","path":"/spec/runtime/image","value":"naeel/fission-python-env:v1.0"}]'
+```
+
+Имя environment всегда: `console--env` (например `console-python-env`).
+
+---
+
+## 6. Линтер (lint-archive)
+
+**Файл:** `console/internal/api/lint_archive.go` → `handleLintArchive()`
+
+**Эндпоинт:** `POST /console/api/ai/lint-archive`
+
+### 6.1 Когда вызывается
+
+Из UI при выборе файла в форме архива (`fn-archive.js` → `lintArchiveFile(prefix)`).
+Поля: `archive` (zip), `entrypoint` (опционально), `language` (опционально).
+
+### 6.2 Порядок проверок
+
+```
+1. Размер архива ≤ 100 KB (maxArchiveBytes)
+2. Суммарный распакованный размер ≤ 100 KB (защита от zip bomb)
+3. Синтаксический линтер по каждому файлу:
+ .py → python3 -m py_compile
+ .js → node --check
+ .rb → ruby -c
+ .php → php -l
+4. Проверка language vs расширения файлов в архиве:
+ python → нужен хотя бы один .py
+ nodejs → нужен хотя бы один .js
+ ...и т.д.
+5. Проверка entrypoint (формат "module.function"):
+ → файл module.py должен быть в архиве
+ → def (...) должна быть определена в файле
+```
+
+### 6.3 Ответ
+
+```json
+{
+ "results": [
+ {"file": "demo.py", "ok": true},
+ {"file": "utils.py", "ok": false, "output": "SyntaxError: ..."},
+ {"file": "язык", "ok": false, "output": "выбран python, но .py файлов нет"},
+ {"file": "entrypoint", "ok": false, "output": "demo.py найден, но def main не определён"}
+ ],
+ "ok": false
+}
+```
+
+---
+
+## 7. Fission: как функция выполняется (runtime)
+
+```
+Пользователь вызывает HTTP URL роута
+ ↓
+Fission Router (JWT auth если включён)
+ ↓
+Executor (poolmgr) — выбирает под из пула
+ ↓
+Fetcher sidecar — скачивает архив из S3:
+ GET http://storagesvc.../v1/archive?id=fission/UUID
+ Распаковывает zip → /userfunc/
+ (для inline Python: кладёт .py как /userfunc/user.py)
+ ↓
+Python runtime pod специализируется:
+ POST /specialize на порт 8888 пода
+ server.py импортирует module из /userfunc/
+ ↓
+Вызов функции:
+ _count_required_params(userfunc) → 0/1/2 аргументов
+ 0 → userfunc()
+ 1 → userfunc(request)
+ 2 → userfunc(request, {})
+```
+
+---
+
+## 8. Namespace пользователя
+
+Каждый пользователь → отдельный K8s namespace.
+
+| Пользователь | Namespace |
+|-------------|-----------|
+| chiken | `fission-54a1d63ee5e0921b` |
+| livetest@test.local | `fission-199e39e44b809ec1` |
+
+Namespace создаётся при первом обращении через `EnsureUserNS()`.
+
+Имя environment всегда `console-python-env` (не уникально на пользователя) — каждый пользователь имеет СВОЙ environment в своём namespace.
+
+---
+
+## 9. Роут функции
+
+Формат по умолчанию: `/<последние 12 символов namespace>/<имя функции>`
+
+Пример: namespace `fission-54a1d63ee5e0921b` → роут `/d63ee5e0921b/funcname`
+
+---
+
+## 10. Аннотации на Function CRD
+
+| Аннотация | Значение |
+|-----------|---------|
+| `fission-console/source-type` | `code` или `archive` |
+| `fission-console/archive-file` | оригинальное имя загруженного файла (только для архивов) |
+| `fission-console/expires-at` | Unix timestamp протухания (если задан TTL) |
+
+---
+
+## 11. Что НЕ ДОЛЖНО происходить (зафиксированные баги)
+
+| Баг | Причина | Последствие |
+|-----|---------|-------------|
+| `ghcr.io/fission/python-env` в LangEnvMap | Забыли про наш патч | `def main(event, context)` → 500 |
+| Загрузка `.py` файла вместо `.zip` | UI не проверял расширение | Fission не может распаковать → 500 |
+| 0 байт в S3 | Файл не zip (magic bytes ≠ PK) | Fetcher не может распаковать → 500 |
+
+---
+
+## 12. Файловая структура кода (консоль)
+
+```
+console/
+ cmd/server/ — точка входа (main.go)
+ internal/
+ api/
+ handlers.go — HTTP handlers: CRUD функций, invoke, edit
+ lint_archive.go — POST /ai/lint-archive
+ ai_check.go — LLM-анализ кода через OpenAI-совместимый API
+ server.go — Server struct, маршрутизация
+ auth/ — JWT/Basic auth middleware
+ fission/
+ environment.go — EnsureEnvironment, CleanupEnvironmentIfUnused
+ namespace.go — EnsureUserNS
+ gvr.go — GVR константы для K8s dynamic client
+ model/
+ types.go — LangEnvMap ⚠️ ОБРАЗЫ ЯЗЫКОВ ЗДЕСЬ
+ runtime/
+ python.go — DefaultEntrypoint, BuildPythonZip
+ nodejs.go — BuildJSDeployZip
+ go.go — BuildGoSourceZip
+ ui/
+ js/
+ functions.js — создание/редактирование inline-функций
+ fn-archive.js — создание из архива
+ fn-edit-archive.js — редактирование архивной функции
+ app.js — общая логика, auth, API вызовы
+```