Chapter 13
源码导读
Axolotl 核心代码 ~3 万行,主轴是"YAML 验证 → 数据 strategy → Trainer 包装"。本章给阅读路线。
13.1仓库结构
axolotl/ https://github.com/axolotl-ai-cloud/axolotl
├── src/axolotl/
│ ├── cli/ ★ CLI 入口
│ │ ├── main.py axolotl 命令分发
│ │ ├── train.py
│ │ ├── inference.py
│ │ ├── merge_lora.py
│ │ ├── preprocess.py
│ │ └── ...
│ ├── core/
│ │ ├── trainer_builder.py ★ 构造 Trainer
│ │ └── ...
│ ├── train.py ★ 主训练函数
│ ├── utils/
│ │ ├── config/ AxolotlInputConfig(pydantic)
│ │ ├── data/ 数据加载
│ │ ├── models.py 模型加载(含 4bit/8bit)
│ │ ├── lora.py PEFT 集成
│ │ ├── fsdp.py / deepspeed.py 分布式
│ │ └── chat_templates.py 内置 chat 模板
│ ├── prompt_strategies/ ★ 20+ 数据格式实现
│ │ ├── alpaca.py
│ │ ├── chat_template.py
│ │ ├── sharegpt.py
│ │ ├── dpo/
│ │ └── ...
│ ├── monkeypatch/ 内核 hack(flash-attn / patching)
│ ├── integrations/ grpo / nemo / spectrum 等
│ └── prompters.py 高层 prompt 封装
├── examples/ 几百个示例 YAML
├── deepspeed_configs/ 4 个 DS preset
├── tests/
└── docs/
13.2调度链
axolotl train my.yml
│
└── src/axolotl/cli/train.py
│
├── load + validate YAML → AxolotlInputConfig (pydantic)
├── src/axolotl/train.py:train()
│ ├── 加载 model + tokenizer(utils/models.py)
│ ├── 加载 dataset,按 type 选 strategy
│ │ └── prompt_strategies/<type>.py:load(...)
│ ├── 套 PEFT(utils/lora.py)
│ ├── 配 deepspeed/fsdp
│ ├── trainer_builder.py 构造 Trainer
│ │ └── 选 Trainer 类型(SFTTrainer/DPOTrainer/...)
│ └── trainer.train()
13.3阅读顺序建议
| # | 文件 | 读什么 |
|---|---|---|
| 1 | src/axolotl/cli/main.py | CLI 分发 |
| 2 | src/axolotl/utils/config/__init__.py | AxolotlInputConfig 全字段 |
| 3 | src/axolotl/train.py | 主流程 |
| 4 | src/axolotl/utils/models.py | 模型加载(4bit/8bit/dtype) |
| 5 | src/axolotl/prompt_strategies/chat_template.py | 最通用数据 strategy |
| 6 | src/axolotl/utils/lora.py | PEFT 怎么集成 |
| 7 | src/axolotl/core/trainer_builder.py | Trainer 工厂 |
| 8 | src/axolotl/monkeypatch/ | flash-attn / liger 等 patch |
13.4关键 commit 时间线
| 时间 | 变更 |
|---|---|
| 2023-05 | v0.1:首版(OpenAccess-AI-Collective) |
| 2023-10 | 多 dataset + sample_packing |
| 2024-01 | FSDP 支持 |
| 2024-04 | chat_template type 重构 |
| 2024-06 | 更名为 axolotl-ai-cloud + Modal 集成 |
| 2024-09 | DPO / ORPO / KTO 全支持 |
| 2024-12 | GRPO 加入(R1 风格) |
| 2025-Q1 | Spectrum / Liger 集成 / pydantic config |
13.5对照其他
| Axolotl | LLaMA-Factory | ms-swift | |
|---|---|---|---|
| 主入口 | YAML | WebUI / CLI | CLI |
| 社区主战场 | 英文 / Discord | 中文 | 中文 + 魔搭 |
| 云原生 | ★★★★(Modal/RunPod) | ★★★ | ★★★★(PAI) |
| 多模态 | ★★(少量) | ★★★ | ★★★★★ |
| 新算法跟进 | ★★★★★ | ★★★★ | ★★★★ |
13.6社区入口
- GitHub:
https://github.com/axolotl-ai-cloud/axolotl(11k+ ⭐) - Discord: README 顶部链接,最活跃
- 官方文档:
https://axolotl.continuumlabs.ai/ - Modal 模板:
examples/modal/ - HuggingFace 上"Axolotl 配方"标签
13.7真实源码树(v2026 commit ab1a0d8)
13.1 是简化版,下面是实际 tree -L 2 src/axolotl/ 输出,便于"读到一半看不到底在哪"时回查:
src/axolotl/
├── cli/ ★ 12 个子命令入口
│ ├── main.py 13 个 Click 子命令注册(41–455)
│ ├── train.py / preprocess.py / inference.py
│ ├── merge_lora.py / merge_sharded_fsdp_weights.py
│ ├── vllm_serve.py / quantize.py / evaluate.py
│ ├── fetch.py / delinearize_llama4.py
│ ├── lm_eval.py / agent_docs.py / config_schema.py
│ └── args.py / utils.py / sweeps.py
│
├── core/ ★ Trainer 工厂
│ ├── builders/
│ │ ├── base.py:56 TrainerBuilderBase(注入 + RNG)
│ │ ├── causal.py:53 HFCausalTrainerBuilder(SFT/pretrain)
│ │ └── rl.py:24 HFRLTrainerBuilder + dispatch
│ ├── trainers/ ★ 8 个 mixin + AxolotlTrainer
│ │ ├── base.py AxolotlTrainer 主类
│ │ ├── mixins/ 8 个:multipack / sequence_parallel /
│ │ │ schedule / optimizer / packing /
│ │ │ checkpoint / rng / ...
│ │ └── dpo.py / kto.py / orpo.py / grpo.py / cpo.py / simpo.py / ipo.py / ebft.py
│ └── tokenizers.py
│
├── train.py ★ 子进程入口(被 cli/train.py 拉起)
│
├── loaders/ ★ 模型加载
│ ├── model.py:72 ModelLoader(pre/post patch)
│ ├── adapter.py:52 find_all_linear_names + 加 PEFT
│ ├── processor.py / tokenizer.py
│ └── patch_manager.py 统一管理 monkeypatch
│
├── utils/
│ ├── config/ AxolotlInputConfig 子模块
│ │ ├── models/ datasets/enums/model/training/peft/...
│ │ ├── input/ AxolotlInputConfig(聚合)
│ │ └── validation/ 跨字段校验
│ ├── data/ wrappers.py:119(dataset.type 路由)
│ ├── chat_templates.py / processing_strategies.py:30
│ └── distributed.py / models.py
│
├── prompt_strategies/ ★ 33+ strategy 注册
│ ├── __init__.py:12–53 type 字符串 → callable
│ ├── alpaca*.py / sharegpt.py / chat_template.py / completion.py
│ ├── dpo/ * 6 / kto/ * 3 / orpo/ * 1
│ ├── bradley_terry/ * 2 reward modeling
│ ├── ebft/ * 5 EBFT 5 变体
│ └── messages/ * 1 原生 messages dict
│
├── monkeypatch/ ★ 30+ 文件
│ ├── attention/ flash-attn / sdpa / ring-attn / xformers
│ ├── trainer/ Trainer.train / .compute_loss patch
│ ├── multipack/ packing patch
│ ├── llama_attn_hijack_*.py Llama 各层 hijack
│ ├── mistral_attn.py / mixtral_attn.py / qwen2_attn.py
│ ├── transformers_fa_utils.py / fastchat_conversation_turns.py
│ └── relora.py / loraplus.py / unsloth.py / liger.py / chunked_loss.py
│
├── integrations/ ★ 17 个 plugin(详见 11.7)
│ ├── liger/ / cut_cross_entropy/ / kernels/ / kd/ / mora/
│ ├── grpo/ / nemo_gym/ / hatchery/ / lm_eval/ / lm_compressor/
│ ├── eaft/ / spectrum/ / grokfast/ / diffusion/ / expert_parallel/
│ ├── densemixer/ / swanlab/
│ └── base.py BasePlugin 接口
│
└── prompters.py 高层接口(少用,多走 strategies)
13.8AxolotlTrainer 的 8 个 mixin
从 core/trainers/base.py 看,AxolotlTrainer 是 HF Trainer 的多重继承组合体,mixin 各管一件事:
| mixin | 负责 |
|---|---|
MultipackMixin | multipack DataLoader / collator 替换 |
SequenceParallelMixin | SP 切分输入 + gather loss |
SchedulerMixin | rex / cosine_w_min_lr / warmup_stable_decay 等扩展 scheduler |
OptimizerMixin | muon / distributed_muon / adam_mini / badam / galore 工厂 |
PackingMixin | sample_packing 流式喂数据 |
CheckpointMixin | FSDP sharded checkpoint / save_only_model / pickle_path |
RNGMixin | data seed + sampler seed 分离 |
RLMixin(RL trainer 才用) | DPO/KTO/ORPO/GRPO/CPO/SimPO/IPO/EBFT 公共逻辑 |
RL 路径:AxolotlDPOTrainer = AxolotlTrainer + DPOTrainer + RL mixin。MRO 顺序在 core/trainers/dpo.py 顶部定义。
13.9monkeypatch 究竟在补什么
Axolotl 的 monkeypatch 不是"hack",是跟着上游版本走的修补层。monkeypatch/ 30+ 文件大致归类:
| 类别 | 代表文件 | 修什么 |
|---|---|---|
| Attention 替换 | attention/sdpa.py、flash_attention.py、ring_attention.py | 给老 transformer 版本注入新 attn 实现 |
| Model-specific hijack | llama_attn_hijack_*.py、mistral_attn.py、qwen2_attn.py | 注入 flash-attn / SP / packing 兼容 |
| Trainer hijack | trainer/train.py、trainer/compute_loss.py | 给 HF Trainer 加 multipack collator / SP gather |
| 损失函数 | chunked_loss.py、cross_entropy_loss.py | cut_cross_entropy / Liger fused loss |
| PEFT 增强 | relora.py、loraplus.py、unsloth.py | ReLoRA reset / LoRA+ 差分 lr / Unsloth kernel |
| Multipack | multipack/data_collator.py 等 6 文件 | FFD 装箱 + position_ids 重建 |
| Liger | liger.py | 把 Liger Kernel 注入到 model.forward |
启用方式:每个 patch 都被 loaders/patch_manager.py 收集,按 cfg.flash_attention / cfg.sample_packing / cfg.unsloth_* 等字段动态打。
13.10从 YAML 字段反查源码的路径表
"我写了 sample_packing: true,到底在哪生效?" 用下表反查:
| YAML 字段 | 读取位置 | 真正发挥作用的代码 |
|---|---|---|
rl: dpo/grpo/... | config/models/training.py | core/builders/rl.py:39–99 dispatch |
adapter: lora / qlora | config/models/peft.py | loaders/adapter.py |
sample_packing: true | config/models/training.py | core/trainers/mixins/packing.py + monkeypatch/multipack/ |
flash_attention: true | config/models/training.py | monkeypatch/attention/flash_attention.py |
plugins: [liger] | config/models/training.py | integrations/liger/ + monkeypatch/liger.py |
fsdp_config: ... | config/models/training.py | utils/fsdp.py + accelerate plugin |
chat_template: tokenizer_default | config/models/training.py | utils/chat_templates.py + prompt_strategies/chat_template.py |
optimizer: muon | config/models/training.py | core/trainers/mixins/optimizer.py → optimizers/muon.py |
quantize.method: gguf | config/models/quantization.py | cli/quantize.py |
13.11跟着测试读 API
tests/ 是读懂 Axolotl 用法的最快路径,比 docs 还实用。重点:
| 测试目录 / 文件 | 示范什么 |
|---|---|
tests/e2e/ | Llama/Mistral/Qwen 各种端到端 train+eval |
tests/prompt_strategies/ | 每个 type 的输入 → 输出 ids 对照 |
tests/integrations/liger/ | 开 Liger 与不开 Liger 的 loss 对比 |
tests/integrations/grpo/ | GRPO + vllm_serve 联动 |
tests/core/trainers/test_*.py | 各 mixin 单测 |
tests/utils/config/ | Pydantic 校验 corner case |
13.123 个推荐阅读路径
读不同目的对应不同路线:
- 路线 A · 加新 dataset type:
prompt_strategies/__init__.py:12–53→ 仿照alpaca.py写 callable → 注册到load()→ 在tests/prompt_strategies/写测; - 路线 B · 加新 RL trainer:
core/builders/rl.py:39–99dispatch →core/trainers/<new>.py继承AxolotlTrainer+ TRL trainer → 把 RLType 加到config/models/enums.py; - 路线 C · 调性能:
monkeypatch/attention/试 ring/sdpa/flash3 →integrations/liger/开 fused →integrations/cut_cross_entropy/省 logits 显存 → 看tests/integrations/里的 benchmark。
13.13axolotl config-schema:自动文档
不想读 pydantic 源码?两条命令:
# 1. 导出 JSON schema(给 IDE / agent 用)
axolotl config-schema > axolotl-schema.json
# 2. 导出文档(给人看)
axolotl agent-docs config-schema
前者可以喂给 VSCode YAML 插件做"鼠标 hover 显示字段说明 + 自动补全"。
13.14这章你需要带走的
- Axolotl 核心调度:YAML → pydantic Config → strategy → Trainer;
- 20+ 数据 strategy 集中在
src/axolotl/prompt_strategies/; - Trainer 选择在
core/trainer_builder.py; - monkeypatch 文件夹放各种性能 hack(flash-attn / liger)。