Image-Text-to-Text
PEFT
Safetensors
English
vision-language-model
llava
astronomy
multimodal
visual-instruction-tuning
lora
connector
Instructions to use grKnight/astrollava-stage2 with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- PEFT
How to use grKnight/astrollava-stage2 with PEFT:
Task type is invalid.
- Notebooks
- Google Colab
- Kaggle
| license: cc-by-sa-4.0 | |
| base_model: | |
| - Qwen/Qwen2.5-1.5B-Instruct | |
| - openai/clip-vit-large-patch14 | |
| datasets: | |
| - UniverseTBD/AstroLLaVA_convos | |
| language: | |
| - en | |
| pipeline_tag: image-text-to-text | |
| tags: | |
| - vision-language-model | |
| - llava | |
| - astronomy | |
| - multimodal | |
| - visual-instruction-tuning | |
| - lora | |
| - peft | |
| - connector | |
| # AstroLLaVA Stage-2 (connector + LoRA instruction tuning) | |
| A LLaVA-style visionβlanguage model that lets **Qwen2.5-1.5B-Instruct** answer questions about | |
| astronomy images encoded by **CLIP ViT-L/14**. This is the **Stage-2** model: it warm-starts the | |
| [Stage-1 connector](https://huggingface.co/grKnight/astrollava-stage1) and **continues training it | |
| jointly with LoRA adapters on the Qwen LLM**, on the caption + GPT-4 QA records of | |
| [`UniverseTBD/AstroLLaVA_convos`](https://huggingface.co/datasets/UniverseTBD/AstroLLaVA_convos). | |
| The CLIP vision tower stays frozen. Trained on a **disjoint held-out test split** so it can be | |
| evaluated on unseen images. | |
| Stage 1 aligned the connector with the LLM frozen β it grounds *coarse* visual structure but | |
| hallucinates fine specifics. Stage 2 opens up the LLM (via LoRA) so the model learns to *use* the | |
| visual evidence when committing to answers β the recipe's instruction-tuning step. | |
| > β οΈ This bundle ships the **connector + LoRA adapter only** (not full LLM weights). It is **not** a | |
| > standalone `transformers` model β it needs the custom VLM code from the | |
| > [astronomy-vlm](https://github.com/crimsonKn1ght/astronomy-vlm) repo, the two base models | |
| > (auto-downloaded from the Hub), and [`peft`](https://github.com/huggingface/peft) to run. | |
| ## Download | |
| A single bundle holds the final checkpoint and everything needed to run / reproduce it: | |
| | Bundle | Contents | | |
| |--------|----------| | |
| | [`astrollava-stage2.zip`](https://huggingface.co/grKnight/astrollava-stage2/blob/main/astrollava-stage2.zip) | `checkpoint-2526/` (`connector.safetensors` + `lora/`), `predictions_test_stage2.jsonl`, `finetune_astrollava_stage2.yaml`, `test.json`, `REPRODUCE.md` | | |
| `checkpoint-2526/` contains the continued-trained connector (`connector.safetensors`), the trained | |
| LoRA adapter (`lora/adapter_model.safetensors` + `adapter_config.json`), optimizer/scheduler state | |
| (`training_state.pt`), and `meta.json` (step + final loss). **Both** the connector and the LoRA are | |
| required at inference. | |
| ## Architecture | |
| ``` | |
| image ββΊ CLIP ViT-L/14 (FROZEN) ββΊ MLP connector (TRAINED, init from Stage-1) ββΊ Qwen2.5-1.5B + LoRA (base FROZEN, LoRA TRAINED) ββΊ text | |
| 1024 β 1536 β 1536 | |
| ``` | |
| - **Vision:** `openai/clip-vit-large-patch14`, penultimate-layer patch features (frozen) | |
| - **Connector:** 2-layer MLP with GELU, 1024β1536β1536; **warm-started from Stage-1 `checkpoint-3789`** and kept trainable | |
| - **LLM:** `Qwen/Qwen2.5-1.5B-Instruct`, base frozen + **LoRA adapters** (`r=16`, `Ξ±=32`, dropout 0.05) on `q/k/v/o/gate/up/down_proj` across all 28 layers | |
| - **Trainable / total:** 22,400,000 / 1,868,879,360 (1.20%) β connector 3,935,232 + LoRA 18,464,768 | |
| ## Training | |
| | | | | |
| |---|---| | |
| | Data | `UniverseTBD/AstroLLaVA_convos`, same per-image held-out split as Stage-1: train 161,653 recs / 29,151 imgs, test 591 imgs / 3,271 recs | | |
| | Initialization | connector β Stage-1 `checkpoint-3789` (epoch 3); LoRA β fresh (no-op init) | | |
| | Objective | next-token cross-entropy on answer tokens only (connector + LoRA trainable) | | |
| | Epochs / steps | 1 epoch, 2,526 update steps | | |
| | Effective batch | 64 (per-device 4 Γ grad-accum 16) | | |
| | LR / schedule | 2e-4, cosine with 3% warmup (75 steps) | | |
| | Max length | 512 (+256 image tokens) | | |
| | Precision | bf16 (autocast) + gradient checkpointing | | |
| | Hardware | 1Γ RTX 6000 Ada (48 GB), ~15 samples/s (~3 h) | | |
| | Held-out loss | 1.60 (step 200) β **1.452** (step 2526), decreasing monotonically β see Training curve below | | |
| The full-LLM backward pass (absent in Stage-1) is the memory driver, hence per-device batch 4 + | |
| gradient checkpointing to fit ~48 GB. One epoch is the LLaVA instruction-tuning convention β the | |
| model only needs to learn to *use* the already-aligned visual features, not to align them from | |
| scratch. | |
| ## Training curve | |
| Held-out validation loss, recomputed per checkpoint on a fixed 512-sample subset of the unseen | |
| `test.json` and averaged over its answer tokens. (The per-step training log wasn't retained, so this | |
| was reconstructed from the saved checkpoints with `scripts/eval_loss_curve.py` β which makes it a | |
| true held-out curve rather than a noisy train-loss trace.) It falls monotonically and flattens by the | |
| end of the single epoch, consistent with the 1-epoch choice: | |
| | step | 200 | 400 | 600 | 800 | 1000 | 1200 | 1400 | 1600 | 1800 | 2000 | 2200 | 2400 | 2526 | | |
| |------|----:|----:|----:|----:|-----:|-----:|-----:|-----:|-----:|-----:|-----:|-----:|-----:| | |
| | held-out loss | 1.605 | 1.571 | 1.548 | 1.526 | 1.508 | 1.494 | 1.479 | 1.471 | 1.462 | 1.456 | 1.454 | 1.452 | **1.452** | | |
|  | |
| Regenerate with `python scripts/eval_loss_curve.py --config configs/finetune_astrollava_stage2.yaml | |
| --checkpoint-dir checkpoints/astrollava-stage2 --records-json datasets/astrollava_llava/test.json | |
| --image-dir datasets/astrollava_llava/images --num-samples 512 --plot` (full series in | |
| `eval_loss_curve.csv`). | |
| ## Usage | |
| ```bash | |
| # 1. get the code | |
| git clone https://github.com/crimsonKn1ght/astronomy-vlm && cd astronomy-vlm | |
| pip install -r requirements.txt # includes peft | |
| # 2. download + unzip the bundle | |
| hf download grKnight/astrollava-stage2 astrollava-stage2.zip --local-dir . | |
| unzip astrollava-stage2.zip -d ckpt2 | |
| # 3. answer a question about an image (CLIP + Qwen auto-download; peft loads the LoRA) | |
| python inference.py \ | |
| --config ckpt2/finetune_astrollava_stage2.yaml \ | |
| --checkpoint ckpt2/checkpoint-2526 \ | |
| --image your_astro_image.jpg \ | |
| --prompt "What type of object is this and what is notable about it?" \ | |
| --temperature 0 | |
| ``` | |
| Pass the Stage-2 **config** so the LoRA modules are built before the adapter weights load; the loader | |
| then restores both the connector and the LoRA automatically. The bundled | |
| `predictions_test_stage2.jsonl` holds the held-out outputs with their reference captions. | |
| ## Capabilities & limitations | |
| Stage 2 fine-tunes the LLM (LoRA) jointly with the connector, so β unlike Stage-1 β the language | |
| model itself learns from the QA pairs rather than improvising specifics from its frozen prior. The | |
| intended effect is **fewer hallucinated fine details** (catalog numbers, instruments, dates) on | |
| question-answering prompts, on top of Stage-1's coarse visual grounding. Compare the bundled | |
| `predictions_test_stage2.jsonl` with Stage-1's `predictions_test_ep3.jsonl` (held out, same images) | |
| to see the difference. | |
| Limitations carried over from the design: CLIP's 224Γ224 input discards fine astronomical detail; | |
| the base LLM is small (1.5B); and LoRA is a low-rank adaptation, not a full fine-tune. Evaluation is | |
| a held-out generation set, not a full quantitative benchmark β read results qualitatively. | |
| ## Reproduction | |
| The bundle's `REPRODUCE.md` pins the exact code commit, base models, the seeded dataset-build | |
| command, the training command, and package versions (`torch`, `transformers`, `peft`). The split is | |
| seeded, so the build reproduces the exact train/test partition. | |
| ``` | |
| prereq: Stage-1 connector checkpoint-3789 (grKnight/astrollava-stage1 ep3 bundle) | |
| build: python scripts/build_astrollava_trainset.py --include-qa --max-image-size 384 --test-fraction 0.02 --seed 42 | |
| train: python train.py --config configs/finetune_astrollava_stage2.yaml | |
| eval: python scripts/batch_inference.py --config configs/finetune_astrollava_stage2.yaml --records-json datasets/astrollava_llava/test.json --num-samples 0 ... | |
| ``` | |
| ## License & attribution | |
| - **Weights:** `cc-by-sa-4.0`, inherited from the training data. | |
| - **Training data:** [`UniverseTBD/AstroLLaVA_convos`](https://huggingface.co/datasets/UniverseTBD/AstroLLaVA_convos) | |
| (CC-BY-SA-4.0); imagery from NASA APOD, ESO, and NASA/ESA Hubble. | |
| - **Base models:** Qwen2.5-1.5B-Instruct (Apache-2.0), CLIP ViT-L/14 (OpenAI, MIT). | |
| - **Builds on:** [AstroLLaVA Stage-1](https://huggingface.co/grKnight/astrollava-stage1) and the | |
| AstroLLaVA work ([arXiv:2504.08583](https://arxiv.org/abs/2504.08583)). | |
| ``` | |