# BAGEL-7B-MoT > BAGEL image generation through the shared online and offline image examples ## Summary - Vendor: ByteDance Seed - Model: `ByteDance-Seed/BAGEL-7B-MoT` - Task: Text-to-image, image-to-image, text-to-text, and image-to-text - Mode: Offline inference and OpenAI-compatible online serving - Maintainer: Community ## When to use this recipe Use this recipe when you want to run BAGEL through the shared image examples instead of model-specific example clients. The generic examples can format BAGEL text-to-image and image-to-image prompts, select the image output modality, attach reference images, and forward BAGEL-specific generation parameters through the pipeline-declared `extra_args` contract. ## References - Upstream model: [`ByteDance-Seed/BAGEL-7B-MoT`](https://huggingface.co/ByteDance-Seed/BAGEL-7B-MoT) - Related offline example: [`examples/offline_inference/text_to_image/text_to_image.py`](../../examples/offline_inference/text_to_image/text_to_image.py) - Related offline image-to-image example: [`examples/offline_inference/image_to_image/image_edit.py`](../../examples/offline_inference/image_to_image/image_edit.py) - Related offline understanding example: [`examples/offline_inference/x_to_text/x_to_text.py`](../../examples/offline_inference/x_to_text/x_to_text.py) - Related online example: [`examples/online_serving/text_to_image/openai_chat_client.py`](../../examples/online_serving/text_to_image/openai_chat_client.py) - Related online image-to-image example: [`examples/online_serving/image_to_image/openai_chat_client.py`](../../examples/online_serving/image_to_image/openai_chat_client.py) - Default deploy configs: [`vllm_omni/deploy/bagel.yaml`](../../vllm_omni/deploy/bagel.yaml), [`vllm_omni/deploy/bagel_single_stage.yaml`](../../vllm_omni/deploy/bagel_single_stage.yaml) ## Hardware Support This recipe documents the CUDA layouts used by the in-repo BAGEL deploy configs. The default two-stage config shares one 80 GB GPU; for more headroom, move the diffusion stage to a second GPU in a custom deploy config. ## GPU ### 1x A100 80GB #### Environment - OS: Linux - Python: Match the repository requirements for your checkout - Driver / runtime: NVIDIA CUDA environment with one A100 80 GB GPU - vLLM version: Match the repository requirements for your checkout - vLLM-Omni version or commit: Use the commit you are deploying from #### Offline Commands Run text-to-image with the shared offline example from the repository root. Pick the topology with `--deploy-config` and forward BAGEL-specific generation parameters as a JSON object through `--extra-body`: ```bash # Two-stage (Thinker + DiT), shares one GPU by default python examples/offline_inference/text_to_image/text_to_image.py \ --model ByteDance-Seed/BAGEL-7B-MoT \ --deploy-config vllm_omni/deploy/bagel.yaml \ --prompt "A beautiful sunset over mountains" \ --height 1024 \ --width 1024 \ --num-inference-steps 50 \ --negative-prompt "blurry, low quality" \ --seed 42 \ --extra-body '{"timestep_shift": 3.0, "cfg_text_scale": 4.0, "cfg_img_scale": 1.5, "cfg_interval": [0.4, 1.0], "cfg_renorm_type": "global", "cfg_renorm_min": 0.0, "think": false}' \ --output /tmp/bagel_text2img.png ``` ```bash # Single-stage (DiT only, with internal LLM/ViT/VAE) python examples/offline_inference/text_to_image/text_to_image.py \ --model ByteDance-Seed/BAGEL-7B-MoT \ --deploy-config vllm_omni/deploy/bagel_single_stage.yaml \ --prompt "A beautiful sunset over mountains" \ --height 1024 \ --width 1024 \ --num-inference-steps 50 \ --seed 42 \ --extra-body '{"timestep_shift": 3.0, "cfg_text_scale": 4.0, "cfg_interval": [0.4, 1.0], "cfg_renorm_type": "global", "cfg_renorm_min": 0.0}' \ --output /tmp/bagel_text2img_single.png ``` The `--extra-body` JSON forwards BAGEL-specific parameters into `OmniDiffusionSamplingParams.extra_args`. Keys are filtered against the model's declared `extra_body_params` (see [`vllm_omni/model_extras/bagel.py`](../../vllm_omni/model_extras/bagel.py)), so unknown keys for BAGEL are silently dropped. This is the preferred way to pass model-specific params — `timestep_shift` (use `3.0` for 1024×1024; the deprecated `--timesteps-shift` flag defaults to `1.0` and is NextStep-oriented), `cfg_text_scale`, `cfg_img_scale`, `cfg_interval`, `cfg_renorm_type`, `cfg_renorm_min`, and `think`. `--seed` makes generation reproducible. > **Note**: the two-stage `bagel.yaml` runs both stages on GPU 0. If you hit > CUDA OOM during warmup, lower stage-0 `gpu_memory_utilization` in the YAML or > split the stages across two GPUs (see the `2x CUDA GPUs` section). Run image-to-image with the shared offline image-to-image example: ```bash python examples/offline_inference/image_to_image/image_edit.py \ --model ByteDance-Seed/BAGEL-7B-MoT \ --prompt "Make the scene look like a watercolor painting" \ --image /tmp/bagel_text2img.png \ --height 512 \ --width 512 \ --extra-args '{"cfg_text_scale": 4.0, "cfg_img_scale": 1.5}' \ --output /tmp/bagel_img2img.png ``` The `--extra-args` JSON forwards BAGEL-specific parameters (e.g. `cfg_text_scale`, `cfg_img_scale`, `cfg_interval`, `cfg_renorm_type`) into `OmniDiffusionSamplingParams.extra_args` via the model-extras registry. Run text-to-text with the shared understanding example. BAGEL's default `bagel.yaml` deploy config is discovered from the checkpoint, so no model-specific example or explicit deploy config is required: ```bash python examples/offline_inference/x_to_text/x_to_text.py \ --model ByteDance-Seed/BAGEL-7B-MoT \ --prompt "Where is the capital of France?" ``` Add `--image` to run image-to-text with the same example: ```bash python examples/offline_inference/x_to_text/x_to_text.py \ --model ByteDance-Seed/BAGEL-7B-MoT \ --image /path/to/input.jpg \ --prompt "Please describe this image in detail." ``` #### Online Commands Start the OpenAI-compatible server: ```bash vllm serve ByteDance-Seed/BAGEL-7B-MoT --omni --port 8091 ``` To use the single-stage topology online: ```bash vllm serve ByteDance-Seed/BAGEL-7B-MoT \ --omni \ --port 8091 \ --deploy-config vllm_omni/deploy/bagel_single_stage.yaml ``` Send a text-to-image request with BAGEL-specific generation parameters: ```bash curl http://localhost:8091/v1/chat/completions \ -H "Content-Type: application/json" \ -d '{ "messages": [ { "role": "user", "content": [ {"type": "text", "text": "<|im_start|>A beautiful sunset over mountains<|im_end|>"} ] } ], "modalities": ["image"], "extra_body": { "height": 512, "width": 512, "num_inference_steps": 50, "cfg_text_scale": 4.0, "cfg_img_scale": 1.5, "negative_prompt": "blurry, low quality", "seed": 42 } }' ``` The important part is that BAGEL-specific keys such as `cfg_text_scale`, `cfg_img_scale`, `cfg_interval`, `cfg_renorm_type`, and `cfg_renorm_min` belong in `extra_body`. The serving layer routes the declared keys into `OmniDiffusionSamplingParams.extra_args` for the BAGEL pipeline. #### Verification Decode the returned data URL into an image: ```bash curl http://localhost:8091/v1/chat/completions \ -H "Content-Type: application/json" \ -d '{ "messages": [ { "role": "user", "content": [ {"type": "text", "text": "<|im_start|>A ceramic teapot on a wooden table<|im_end|>"} ] } ], "modalities": ["image"], "extra_body": { "height": 512, "width": 512, "num_inference_steps": 25, "cfg_text_scale": 4.0, "seed": 42 } }' | jq -r '.choices[]?.message.content[]? | select(.image_url.url) | .image_url.url' \ | head -n 1 \ | cut -d',' -f2- \ | base64 -d > /tmp/bagel_online.png ls -lh /tmp/bagel_online.png ``` ### 2x CUDA GPUs Create a custom deploy config from `vllm_omni/deploy/bagel.yaml` and move the diffusion stage to GPU 1: ```yaml stages: - stage_id: 0 devices: "0" # keep the remaining stage-0 settings from bagel.yaml - stage_id: 1 devices: "1" # keep the remaining stage-1 settings from bagel.yaml ``` Then start serving with that config: ```bash vllm serve ByteDance-Seed/BAGEL-7B-MoT \ --omni \ --port 8091 \ --deploy-config /path/to/custom_bagel_2gpu.yaml ``` Use the online curl request from the `1x A100 80GB` section to verify that the server returns an image.