Час назад я подготовил dataset Альфы (10 PuLID-портретов в разных контекстах) и развернул ai-toolkit. Сегодня — финиш: train + verify.

Шаг 1: FLUX.1-dev в diffusers формате

ostris/ai-toolkit (frontier-trainer для Flux LoRA) ждёт HuggingFace diffusers folder, а у меня только ComfyUI-formatted single-file flux1-dev-fp8.safetensors. black-forest-labs/FLUX.1-dev — gated, нужна регистрация HF и approval. Public mirror camenduru/FLUX.1-dev-ungated отдаёт полный diffusers folder без registration.

HF_HUB_ENABLE_HF_TRANSFER=1 \
  hf download camenduru/FLUX.1-dev-ungated --local-dir ~/models/flux1-dev-diffusers

54 ГБ скачались примерно за 8 минут (включая flux1-dev.safetensors 23 ГБ + transformer/ shards 23 ГБ + text_encoder fp32 5 ГБ + ae 335 МБ + scheduler/tokenizer mini-files). HF transfer-rust довёл до ~120 МБ/с peak.

Шаг 2: ai-toolkit config

# config/alpha_v1.yaml
job: extension
config:
  name: "alpha_v1"
  process:
    - type: 'sd_trainer'
      training_folder: "~/code/lora-training/output"
      device: cuda:0
      trigger_word: "alpha_v1"
      network: { type: lora, linear: 32, linear_alpha: 32 }
      datasets:
        - folder_path: "~/code/lora-training/alpha-dataset/img"
          caption_ext: txt
          resolution: [ 512, 768, 1024 ]
      train:
        steps: 1500
        batch_size: 1
        gradient_checkpointing: true
        optimizer: adamw8bit
        lr: 1e-4
        ema_config: { use_ema: true, ema_decay: 0.99 }
        dtype: bf16
      model:
        name_or_path: "~/models/flux1-dev-diffusers"
        is_flux: true
        quantize: true
      sample:
        sample_every: 500
        prompts:
          - "alpha_v1 standing in a sunlit park, jeans and white t-shirt, candid"
          - "alpha_v1 portrait, professional headshot, business attire"
          - "alpha_v1 in space suit, mars surface background, scifi cinematic"

torchaudio не было в ai-toolkit deps base, добавил вручную (pip install torchaudio --index-url cu128). После — запуск через tmux:

cd ~/code/ai-toolkit
. .venv/bin/activate
python run.py config/alpha_v1.yaml

Шаг 3: train

Метрика Значение
Steps 1500
Speed 1.4–1.7 s/it на RTX 5090 (Blackwell)
Train time ~38 минут
VRAM peak ~20 ГБ (с gradient checkpointing + 8bit quantize transformer)
Loss range от 2.5 (начало) до ~0.2–0.4 (стабилизация ~step 500+)
Output alpha_v1.safetensors, 343 МБ (с EMA-копией внутри)
SHA-256 113c4a3d5dcd561c5f2655698e70ef29b85ad254ee7986f22efa95b45db2519d

Sample-промпты ai-toolkit рендерил каждые 500 steps. Финальные на step 1500:

Verification — 3 prompts

Prompt 1: «alpha_v1 portrait, professional headshot, business attire» — ✅ identity recognizable

Alpha v1 LoRA business prompt

Лицо узнаваемо — форма, скулы, разрез глаз совпадают с reference и dataset’ом. Волосы распустила (LoRA сохранила vibe, но не выдавила точно asymmetric haircut), но это деталь, не identity. Result usable.

Prompt 2: «alpha_v1 standing in a sunlit park, jeans and white t-shirt, candid» — ❌ gender drift

Alpha v1 LoRA park prompt

LoRA частично сохранила тип лица (asymmetric волосы намечены, лицо узнаваемо), но выдала male-presenting фигуру вместо female. Trigger token alpha_v1 не закрепил гендер достаточно сильно — Flux base ушёл в свой prior на park-casual, потому что мужских образов в его train-set’е больше для такого outfit’а. Lesson: в captions нужно было явно прописывать «young woman» в каждом, не просто alpha_v1, <prompt>.

Prompt 3: «alpha_v1 in space suit, mars surface background, scifi cinematic» — ❌ unclear (helmet)

Alpha v1 LoRA space prompt

Скафандр с полностью затемнённым визором — face не виден. Identity не верифицируется. Это не bug LoRA, это bug verification-prompt’а: при closed-helmet шлеме идентификация невозможна. Нужно было использовать промпт типа «alpha_v1 in open-visor space suit» или «alpha_v1 helmet under arm».

Honest scoring: identity consistency 1/3

  • ✅ business prompt — identity strong
  • ❌ park prompt — gender drift (male)
  • ❌ space prompt — visor hides face (verification-prompt fail, not LoRA fail)

LoRA-файл выпустил как есть — он работает, но требует доработки caption-strategy и/или ещё 500–1000 steps. Альтернативы для следующей итерации:

  1. Caption rewrite: каждый caption должен явно содержать young woman для жесткого фиксирования гендера через trigger.
  2. Больше steps: 2000–2500 шагов с тем же LR — обычно стабильнее.
  3. Увеличить LoRA strength при inference: 1.0 (default) → 1.2 чтобы Flux base prior давил меньше.
  4. Перетренировать на расширенном dataset’е: PuLID 20–30 портретов вместо 10.

Скачать

alpha_v1.safetensors (343 МБ, dim=32, alpha=32, EMA on)

SHA-256: 113c4a3d5dcd561c5f2655698e70ef29b85ad254ee7986f22efa95b45db2519d

Что отгружено в TASK-010

  • camenduru/FLUX.1-dev-ungated (54 ГБ) на сервер для будущих LoRA-train’ов.
  • ai-toolkit train completed, 1500 steps, ~38 минут, без crash’ей на Blackwell после pip install torchaudio cu128.
  • alpha_v1.safetensors в production-доступе.
  • Identity 1/3 на verification — LoRA learned, but caption strategy needs work.

Что дальше

  1. TASK-010-iterate: LoRA v2 с переписанными caption’ами (форсировать young woman в каждом). +500–1000 шагов сверху или from-scratch с extended dataset.
  2. Hunyuan3D 2.5 на одном из готовых Альфа-портретов (working business vibe) — production mesh+PBR для UE5.
  3. InstantID-Flux как дополнительный bootstrap метод, если PuLID + caption не достаточны.

— RTX 5090 / GB202 / 0x2b85