Skip to content

Latest commit

 

History

3 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

loracraft

CLI tool for automated character LoRA training using cloud providers.

Training images are generated with Runware (Flux.1 Kontext). LoRA training runs on RunPod (Flux.2 Klein 4B — primary, ~1.5 it/s on RTX PRO 4500), Replicate, or Fal.ai (both Flux.1-dev only). Weights are uploaded to Runware for inference.

Character LoRA can be stacked with a style LoRA at inference:

character LoRA (~0.70) + watercolor style LoRA (~0.85) → consistent illustrated character

Requirements

  • Python 3.11+
  • uv
  • API keys for inference (Runware), training (RunPod recommended, or Replicate/Fal.ai for Flux.1-dev), and S3-compatible storage (required for RunPod; recommended for Replicate)

Setup

# 1. Install
uv sync

# 2. Configure
cp .env.example .env
# Fill in your API keys (see Environment Variables below)

# 3. Verify
uv run loracraft --help

Environment Variables

Variable Required Description
TRAINING_PROVIDER No runpod (default) or replicate / fal (Flux.1-dev only)
CHARACTER_LORA_WEIGHT No Inference weight for character LoRA. Default: 0.70
STYLE_LORA_WEIGHT No Inference weight for style LoRA. Default: 0.85
RUNWARE_API_KEY Yes Image generation + inference. runware.ai
RUNWARE_FLUX_MODEL_ID Yes AIR for base model on Runware. Default: runware:101@1
RUNWARE_KONTEXT_MODEL_ID Yes AIR for Flux.1 Kontext on Runware. Default: runware:106@1
RUNWARE_MODEL_SOURCE Yes Source identifier for model uploads. Create at app.runware.ai → Models → Sources.
RUNPOD_API_KEY If using RunPod runpod.io/console/user/settings — needs Pod Read + Write permissions
RUNPOD_HF_TOKEN If using RunPod HuggingFace token with read access — required, Klein base model is gated
RUNPOD_GPU_TYPE_ID No RunPod GPU type. Default: NVIDIA RTX PRO 4500 Blackwell
RUNPOD_BASE_MODEL No HF repo for base model. Default: black-forest-labs/FLUX.2-klein-base-4B
RUNPOD_CLOUD_TYPE No SECURE or COMMUNITY. Default: SECURE
RUNPOD_CONTAINER_DISK_GB No Container disk size in GB. Default: 50
REPLICATE_API_KEY If using Replicate replicate.com/account/api-tokens
REPLICATE_MODEL_OWNER If using Replicate Your Replicate username
FAL_API_KEY If using Fal.ai fal.ai/dashboard/keys
S3_ENDPOINT_URL Required for RunPod S3-compatible storage endpoint (Cloudflare R2 recommended — no egress fees)
S3_ACCESS_KEY_ID Required for RunPod S3 access key
S3_SECRET_ACCESS_KEY Required for RunPod S3 secret key
S3_BUCKET_NAME Required for RunPod S3 bucket name
S3_REGION No Bucket region. Default: auto

Commands

loracraft create-character — full pipeline

Runs all steps end-to-end with manual review gates at each stage.

# Interactive prompts
uv run loracraft create-character

# From a config file
uv run loracraft create-character --config characters/luna.yaml

# Options
uv run loracraft create-character \
  --config characters/luna.yaml \
  --provider replicate \
  --steps 1000 \
  --rank 16 \
  --test-scenes 3 \
  --no-runware-upload

Pipeline steps:

1. Generate reference image (1024×1536 portrait, vanilla FLUX.1-dev)
   ↓
[REVIEW] Approve character design / retry / quit
   ↓
2. Generate 20 training images via Flux.1 Kontext (reference-anchored)
   ↓
[REVIEW] Approve training set / retry / [s]elect slots to regenerate / edit manually / quit
   ↓
3. Submit LoRA training job (RunPod ~20–25 min · Replicate ~20–30 min · Fal ~5–15 min · ~$1–2/run)
   ↓
4. Download weights → characters/<name>/lora/<name>.safetensors
5. Upload to Runware (unless --no-runware-upload)
   ↓
[REVIEW] Review test scenes / retry / approve
   ↓
6. Register in characters/registry.json

loracraft generate-reference — step 1 only

Generate a reference image only — without running training.

uv run loracraft generate-reference --config characters/luna.yaml

loracraft train — training only

Submit a training job against a pre-curated images directory.

uv run loracraft train luna \
  --images-dir characters/luna/training \
  --provider replicate \
  --steps 1000 \
  --rank 16

loracraft training-status — check job status

# Single poll
uv run loracraft training-status luna

# Watch until complete
uv run loracraft training-status luna --watch --interval 30

loracraft upload-lora — upload weights to Runware

Re-upload existing local weights without re-training.

uv run loracraft upload-lora luna

loracraft list-characters — registry

uv run loracraft list-characters

loracraft test-character — inference test

Generate scenes with a trained character LoRA. Optionally stack a style LoRA.

uv run loracraft test-character luna --scenes 4

# With a style LoRA (Runware AIR)
uv run loracraft test-character luna \
  --scenes 4 \
  --style-lora civitai:512147@1271855

Character Config File

Copy characters/luna.yaml.example as a starting point:

name: Leo
trigger_word: LFPZ # short nonsense token — avoid real words
gender: boy
age_description: "toddler boy, about 3 years old"
ethnicity: "mixed Latino and East Asian descent, warm medium tan skin"
hair: "soft tight dark brown curls, kept short"
face: "very round chubby toddler face, big bright dark brown eyes, wide cheerful smile"
outfit: "sky blue zip-up romper with small patch pockets, white socks, white sneakers with Velcro straps"

# Style LoRA applied during test inference only (not during training image generation)
# style_lora_id: "civitai:512147@1271855"

Key rules:

  • trigger_word must be a short nonsense string (e.g. ZNKL, BFPT). It's embedded in every training caption and used at inference time.
  • outfit describes the canonical look. Keep it identical across all training images — outfit variation is handled at prompt time during inference, not in training.
  • Training images are generated against vanilla FLUX.1-dev with no style LoRA. Style is applied only at inference time, keeping the character LoRA style-agnostic and compatible with all your style LoRAs.

Output Structure

characters/
├── registry.json
└── <name>/
    ├── character.yaml           canonical character config
    ├── reference.png            reference image
    ├── training/                images + .txt captions submitted for training
    ├── lora/
    │   └── <name>.safetensors   downloaded weights
    └── test/                    test scene outputs

Training Providers

RunPod Replicate Fal.ai
Model Flux.2 Klein 4B Flux.1-dev Flux.1-dev
Trainer ostris/aitoolkit:latest (AI Toolkit) ostris/flux-dev-lora-trainer flux-lora-fast-training
Cost ~$1.00–$1.50 / run ~$1.85–$2.75 / run ~$2.00 / run
Rank control Yes Yes (4–64) No (fixed internally)
Turnaround ~20–25 min ~20–30 min ~5–15 min
Recommended rank 16 for characters 16–32 for characters

RunPod is the recommended provider — trains on Flux.2 Klein 4B which is 5x+ faster at inference. Replicate and Fal.ai produce good results on Flux.1-dev if RunPod is unavailable.


S3 Storage (Recommended)

Runware downloads weights from a public URL — it does not accept direct file uploads. S3-compatible storage is used to stage the extracted .safetensors file and provide a presigned URL.

Cloudflare R2 setup:

  • Endpoint format: https://<account_id>.r2.cloudflarestorage.com
  • No egress fees, 10 GB free tier
  • Set S3_REGION=auto

Without S3, fal_client is used as a fallback staging layer (requires FAL_API_KEY).

About

CLI tool for automated character LoRA training

Resources

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages