Buckets:
| # ModularPipeline | |
| [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline) преобразует [ModularPipelineBlocks](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) в исполняемый конвейер, который загружает модели и выполняет вычислительные шаги, определённые в блоках. Это основной интерфейс для запуска конвейера, и его API очень похож на [DiffusionPipeline](/docs/diffusers/v0.43.0/ru/api/pipelines/overview#diffusers.DiffusionPipeline), но с несколькими ключевыми отличиями. | |
| - **Loading is lazy.** With [DiffusionPipeline](/docs/diffusers/v0.43.0/ru/api/pipelines/overview#diffusers.DiffusionPipeline), [from_pretrained()](/docs/diffusers/v0.43.0/ru/api/pipelines/overview#diffusers.DiffusionPipeline.from_pretrained) creates the pipeline and loads all models at the same time. With [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline), creating and loading are two separate steps: [from_pretrained()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained) reads the configuration and knows where to load each component from, but doesn't actually load the model weights. You load the models later with [load_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components), which is where you pass loading arguments like `dtype` and `quantization_config`. | |
| - **Два способа создания пайплайна.** Можно использовать [from_pretrained()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained) с существующим репозиторием модели diffusers — он автоматически сопоставляется с блоками пайплайна по умолчанию, а затем преобразуется в [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline) без дополнительной настройки. Список поддерживаемых моделей можно найти в [modular_pipelines_directory](https://github.com/huggingface/diffusers/tree/main/src/diffusers/modular_pipelines). Также можно собрать собственный пайплайн из [ModularPipelineBlocks](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) и преобразовать его с помощью метода [init_pipeline()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) (подробнее см. [Создание пайплайна](#creating-a-pipeline)). | |
| - **Running the pipeline is the same.** Once loaded, you call the pipeline with the same arguments you're used to. A single [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline) can support multiple workflows (text-to-image, image-to-image, inpainting, etc.) when the pipeline blocks use [`AutoPipelineBlocks`](./auto_pipeline_blocks) to automatically select the workflow based on your inputs. | |
| Ниже приведены полные примеры для генерации изображений по тексту, преобразования изображения в изображение и инпейнтинга с SDXL. | |
| ```py | |
| import torch | |
| from diffusers import ModularPipeline | |
| pipeline = ModularPipeline.from_pretrained("stabilityai/stable-diffusion-xl-base-1.0") | |
| pipeline.load_components(dtype=torch.float16) | |
| pipeline.to("cuda") # or "mps", "xpu", "cpu" | |
| image = pipeline(prompt="Astronaut in a jungle, cold color palette, muted colors, detailed, 8k").images[0] | |
| image.save("modular_t2i_out.png") | |
| ``` | |
| ```py | |
| import torch | |
| from diffusers import ModularPipeline | |
| from diffusers.utils import load_image | |
| pipeline = ModularPipeline.from_pretrained("stabilityai/stable-diffusion-xl-base-1.0") | |
| pipeline.load_components(dtype=torch.float16) | |
| pipeline.to("cuda") # or "mps", "xpu", "cpu" | |
| url = "https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/sdxl-text2img.png" | |
| init_image = load_image(url) | |
| prompt = "a dog catching a frisbee in the jungle" | |
| image = pipeline(prompt=prompt, image=init_image, strength=0.8).images[0] | |
| image.save("modular_i2i_out.png") | |
| ``` | |
| ```py | |
| import torch | |
| from diffusers import ModularPipeline | |
| from diffusers.utils import load_image | |
| pipeline = ModularPipeline.from_pretrained("stabilityai/stable-diffusion-xl-base-1.0") | |
| pipeline.load_components(dtype=torch.float16) | |
| pipeline.to("cuda") # or "mps", "xpu", "cpu" | |
| img_url = "https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/sdxl-text2img.png" | |
| mask_url = "https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/sdxl-inpaint-mask.png" | |
| init_image = load_image(img_url) | |
| mask_image = load_image(mask_url) | |
| prompt = "A deep sea diver floating" | |
| image = pipeline(prompt=prompt, image=init_image, mask_image=mask_image, strength=0.85).images[0] | |
| image.save("modular_inpaint_out.png") | |
| ``` | |
| В этом руководстве показано, как создать [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline), управлять его компонентами и запустить конвейер. | |
| ## Создание конвейера | |
| There are two ways to create a [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline). Assemble and create a pipeline from [ModularPipelineBlocks](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) with [init_pipeline()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline), or load an existing pipeline with [from_pretrained()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained). | |
| Вы также можете инициализировать [`ComponentsManager`](./components_manager) для управления размещением на устройствах и управлением памятью. Если автоматическое выгружение не требуется, вы можете пропустить этот шаг и вручную переместить конвейер на ваше устройство с помощью `pipeline.to("cuda")`. | |
| > [!TIP] | |
| > См. документацию [ComponentsManager](./components_manager) для получения подробной информации о том, как он помогает управлять компонентами в разных рабочих процессах. | |
| ### init_pipeline | |
| [init_pipeline()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) преобразует любой [ModularPipelineBlocks](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) в [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline). | |
| Определим минимальный блок, чтобы посмотреть, как он работает: | |
| ```py | |
| from transformers import CLIPTextModel | |
| from diffusers.modular_pipelines import ( | |
| ComponentSpec, | |
| ModularPipelineBlocks, | |
| PipelineState, | |
| ) | |
| class MyBlock(ModularPipelineBlocks): | |
| @property | |
| def expected_components(self): | |
| return [ | |
| ComponentSpec( | |
| name="text_encoder", | |
| type_hint=CLIPTextModel, | |
| pretrained_model_name_or_path="openai/clip-vit-large-patch14", | |
| ), | |
| ] | |
| def __call__(self, components, state: PipelineState) -> PipelineState: | |
| return components, state | |
| ``` | |
| Вызовите [init_pipeline()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline), чтобы преобразовать его в пайплайн. Атрибут `blocks` пайплайна содержит блоки, из которых он был создан, — они определяют ожидаемые входные и выходные данные, а также логику вычислений. | |
| ```py | |
| block = MyBlock() | |
| pipe = block.init_pipeline() | |
| pipe.blocks | |
| ``` | |
| ``` | |
| MyBlock { | |
| "_class_name": "MyBlock", | |
| "_diffusers_version": "0.37.0.dev0" | |
| } | |
| ``` | |
| > [!WARNING] | |
| > Блоки изменяемы — вы можете свободно добавлять, удалять или заменять блоки до создания конвейера. Однако, как только конвейер создан, изменение `pipeline.blocks` не повлияет на конвейер, так как возвращается копия. Если вам нужна другая структура блоков, создайте новый конвейер после изменения блоков. | |
| При вызове [init_pipeline()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) без указания репозитория используется `pretrained_model_name_or_path`, определённый в [ComponentSpec](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec) блока, чтобы определить, откуда загружать каждый компонент. Вывод пайплайна показывает конфигурацию загрузки компонентов. | |
| ```py | |
| pipe | |
| ModularPipeline { | |
| "_blocks_class_name": "MyBlock", | |
| "_class_name": "ModularPipeline", | |
| "_diffusers_version": "0.37.0.dev0", | |
| "text_encoder": [ | |
| null, | |
| null, | |
| { | |
| "pretrained_model_name_or_path": "openai/clip-vit-large-patch14", | |
| "revision": null, | |
| "subfolder": "", | |
| "type_hint": [ | |
| "transformers", | |
| "CLIPTextModel" | |
| ], | |
| "variant": null | |
| } | |
| ] | |
| } | |
| ``` | |
| Если вы передадите репозиторий в [init_pipeline()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline), он переопределит путь загрузки, сопоставляя компоненты вашего блока с конфигурацией пайплайна в этом репозитории (`model_index.json` или `modular_model_index.json`). См. [Modular repository](#modular-repository), чтобы узнать, как спецификации загрузки записываются и сохраняются. | |
| В примере ниже `pretrained_model_name_or_path` будет обновлено до `"stabilityai/stable-diffusion-xl-base-1.0"`. | |
| ```py | |
| pipe = block.init_pipeline("stabilityai/stable-diffusion-xl-base-1.0") | |
| pipe | |
| ModularPipeline { | |
| "_blocks_class_name": "MyBlock", | |
| "_class_name": "ModularPipeline", | |
| "_diffusers_version": "0.37.0.dev0", | |
| "text_encoder": [ | |
| null, | |
| null, | |
| { | |
| "pretrained_model_name_or_path": "stabilityai/stable-diffusion-xl-base-1.0", | |
| "revision": null, | |
| "subfolder": "text_encoder", | |
| "type_hint": [ | |
| "transformers", | |
| "CLIPTextModel" | |
| ], | |
| "variant": null | |
| } | |
| ] | |
| } | |
| ``` | |
| Если компонент в вашем блоке отсутствует в репозитории, он остаётся `null` и пропускается при вызове [load_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components). | |
| ### from_pretrained | |
| [from_pretrained()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained) — удобный способ создать [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline), не определяя блоки самостоятельно. | |
| Он работает с тремя типами репозиториев. | |
| **Обычный репозиторий diffusers.** Передайте любой поддерживаемый репозиторий модели, и он автоматически сопоставится с блоками стандартного пайплайна. В настоящее время поддерживаются модели SDXL, Wan, Qwen, Z-Image, Flux и Flux2. | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| components = ComponentsManager() | |
| pipeline = ModularPipeline.from_pretrained( | |
| "stabilityai/stable-diffusion-xl-base-1.0", components_manager=components | |
| ) | |
| ``` | |
| **Модульный репозиторий.** Эти репозитории содержат файл `modular_model_index.json`, в котором указаны классы каждого компонента и источники их загрузки, при этом сами компоненты хранятся рядом с этим файлом. См. [Модульный репозиторий](#modular-repository), чтобы узнать, как его создать. | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| components = ComponentsManager() | |
| pipeline = ModularPipeline.from_pretrained( | |
| "MiniMaxAI/MiniMax-H3", components_manager=components | |
| ) | |
| ``` | |
| **Модульный репозиторий с собственным кодом.** Некоторые репозитории содержат наряду с конфигурацией загрузки собственные блоки конвейера. Добавьте `trust_remote_code=True`, чтобы загрузить их. О том, как создать собственные блоки, см. в разделе [Собственные блоки](./custom_blocks). | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| components = ComponentsManager() | |
| pipeline = ModularPipeline.from_pretrained( | |
| "diffusers/Florence2-image-Annotator", trust_remote_code=True, components_manager=components | |
| ) | |
| ``` | |
| Когда блоки пайплайна определяют рабочие процессы (см. `pipeline.blocks.available_workflows`), передайте `workflow=`, чтобы оставить только блоки этого рабочего процесса — это та же обрезка, что и в [get_workflow()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.get_workflow). Тогда пайплайн объявляет только те компоненты, которые использует данный рабочий процесс, а его docstring описывает именно его входные данные. | |
| ```py | |
| pipeline = ModularPipeline.from_pretrained("Qwen/Qwen-Image", workflow="inpainting") | |
| ``` | |
| ## Загрузка компонентов | |
| [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline) не инициализируется автоматически с компонентами. Он загружает только конфигурацию и спецификации компонентов. Загрузить компоненты можно с помощью [load_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components). | |
| Это загрузит все компоненты, для которых определена корректная спецификация загрузки. | |
| ```py | |
| import torch | |
| pipeline.load_components(dtype=torch.float16) | |
| ``` | |
| Вы также можете загрузить конкретные компоненты по имени. В примере ниже загружается только `text_encoder`. | |
| ```py | |
| pipeline.load_components(names=["text_encoder"], dtype=torch.float16) | |
| ``` | |
| В конвейере, блоки которого определяют рабочие процессы, параметр `workflow=` загружает только те компоненты, которые используются этим рабочим процессом. Конвейер сохраняет все свои блоки, поэтому это удобный способ запускать один конвейер для разных рабочих процессов: каждый вызов добавляет лишь то, чего ещё не хватает новому рабочему процессу. | |
| ```py | |
| pipeline.load_components(workflow="inpainting", dtype=torch.float16) | |
| ``` | |
| После загрузки вывод пайплайна показывает, какие компоненты загружены — первые два поля меняются с `null` на библиотеку и класс компонента. | |
| ```py | |
| pipeline | |
| ``` | |
| ``` | |
| # text_encoder is loaded - shows library and class | |
| "text_encoder": [ | |
| "transformers", | |
| "CLIPTextModel", | |
| { ... } | |
| ] | |
| # unet is not loaded yet - still null | |
| "unet": [ | |
| null, | |
| null, | |
| { ... } | |
| ] | |
| ``` | |
| Параметры, передаваемые по имени, такие как `dtype`, `variant`, `revision` и `quantization_config`, передаются в `from_pretrained()` для каждого компонента. Можно передать одно значение, чтобы применить его ко всем компонентам, или словарь, чтобы задать значения для каждого компонента отдельно. | |
| ```py | |
| # apply bfloat16 to all components | |
| pipeline.load_components(dtype=torch.bfloat16) | |
| # different dtypes per component | |
| pipeline.load_components(dtype={"transformer": torch.bfloat16, "default": torch.float32}) | |
| ``` | |
| [load_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components) загружает только те компоненты, которые ещё не были загружены и для которых задано корректное описание загрузки. Это означает, что если вы уже установили компонент в конвейере, повторный вызов [load_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components) не перезагрузит его. | |
| ## Обновление компонентов | |
| [update_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.update_components) заменяет компонент в конвейере новым. При обновлении компонента спецификации загрузки также обновляются в конфигурации конвейера, и [load_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components) будет пропускать его при последующих вызовах. | |
| ### Из AutoModel | |
| Вы можете передать объект модели, загруженный с помощью `AutoModel.from_pretrained()`. Модели, загруженные таким образом, автоматически помечаются информацией о загрузке. | |
| ```py | |
| from diffusers import AutoModel | |
| unet = AutoModel.from_pretrained( | |
| "RunDiffusion/Juggernaut-XL-v9", subfolder="unet", variant="fp16", dtype=torch.float16 | |
| ) | |
| pipeline.update_components(unet=unet) | |
| ``` | |
| ### Из ComponentSpec | |
| Используйте [get_component_spec()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.get_component_spec), чтобы получить копию текущей спецификации компонента, изменить её и загрузить новый компонент. | |
| ```py | |
| unet_spec = pipeline.get_component_spec("unet") | |
| # modify to load from a different repository | |
| unet_spec.pretrained_model_name_or_path = "RunDiffusion/Juggernaut-XL-v9" | |
| # load and update | |
| unet = unet_spec.load(dtype=torch.float16) | |
| pipeline.update_components(unet=unet) | |
| ``` | |
| Вы также можете создать [ComponentSpec](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec) с нуля. | |
| Не все компоненты загружаются из предобученных весов — некоторые создаются на основе конфигурации (перечислены в `pipeline.config_component_names`). Для них используйте [create()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec.create) вместо [load()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec.load). | |
| ```py | |
| guider_spec = pipeline.get_component_spec("guider") | |
| guider_spec.config = {"guidance_scale": 5.0} | |
| guider = guider_spec.create() | |
| pipeline.update_components(guider=guider) | |
| ``` | |
| Или просто передайте объект напрямую. | |
| ```py | |
| from diffusers.guiders import ClassifierFreeGuidance | |
| guider = ClassifierFreeGuidance(guidance_scale=5.0) | |
| pipeline.update_components(guider=guider) | |
| ``` | |
| См. руководство [Guiders](../using-diffusers/guiders) для получения подробной информации о доступных guiders и способах их настройки. | |
| ## Разделение конвейера на этапы | |
| Поскольку блоки комбинируемы, вы можете разобрать пайплайн и собрать из него отдельные пайплайны для каждого этапа. В примере ниже показано, как можно выделить блок text encoder из остальной части пайплайна, чтобы независимо закодировать промпт и передать эмбеддинги в основной пайплайн. | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| import torch | |
| device = "cuda" # or "mps", "xpu", "cpu" | |
| dtype = torch.bfloat16 | |
| repo_id = "black-forest-labs/FLUX.2-klein-4B" | |
| # get the blocks and separate out the text encoder | |
| blocks = ModularPipeline.from_pretrained(repo_id).blocks | |
| text_block = blocks.sub_blocks.pop("text_encoder") | |
| # use ComponentsManager to handle offloading across multiple pipelines | |
| manager = ComponentsManager() | |
| manager.enable_auto_cpu_offload(device=device) | |
| # create separate pipelines for each stage | |
| text_encoder_pipeline = text_block.init_pipeline(repo_id, components_manager=manager) | |
| pipeline = blocks.init_pipeline(repo_id, components_manager=manager) | |
| # encode text | |
| text_encoder_pipeline.load_components(dtype=dtype) | |
| text_embeddings = text_encoder_pipeline(prompt="a cat").get_by_kwargs("denoiser_input_fields") | |
| # denoise and decode | |
| pipeline.load_components(dtype=dtype) | |
| output = pipeline( | |
| **text_embeddings, | |
| num_inference_steps=4, | |
| ).images[0] | |
| ``` | |
| [ComponentsManager](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_components#diffusers.ComponentsManager) управляет памятью в нескольких конвейерах. В отличие от стратегий выгрузки в [DiffusionPipeline](/docs/diffusers/v0.43.0/ru/api/pipelines/overview#diffusers.DiffusionPipeline), которые следуют фиксированному порядку, [ComponentsManager](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline_components#diffusers.ComponentsManager) принимает решения о выгрузке динамически при каждом проходе модели вперёд, исходя из текущего состояния памяти. Это означает, что он работает независимо от количества созданных конвейеров и порядка их выполнения. Подробнее см. в руководстве по [ComponentsManager](./components_manager). | |
| Если этапы конвейера используют общие компоненты (например, одна и та же VAE для кодирования и декодирования), вы можете использовать [update_components()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.update_components), чтобы передать уже загруженный компонент в другой конвейер, а не загружать его заново. | |
| ## Модульный репозиторий | |
| Репозиторий требуется, если блоки конвейера используют *предобученные компоненты*. Репозиторий предоставляет спецификации загрузки и метаданные. | |
| [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline) работает с обычными репозиториями diffusers без дополнительной настройки. Однако для большей гибкости можно создать *модульный репозиторий*. Модульный репозиторий содержит файл `modular_model_index.json` с тремя элементами. | |
| - `library` и `class` показывают, из какой библиотеки был загружен компонент и его класс. Если `null`, компонент ещё не был загружен. | |
| - `loading_specs_dict` содержит информацию, необходимую для загрузки компонента, например, репозиторий и подпапку, из которых он загружается. | |
| ```py | |
| from diffusers import ModularPipeline | |
| # load from a regular repo | |
| pipeline = ModularPipeline.from_pretrained("stabilityai/stable-diffusion-xl-base-1.0") | |
| pipeline.load_components() | |
| # push as a modular repository | |
| pipeline.save_pretrained("local/path", repo_id="my-username/sdxl-modular", push_to_hub=True) | |
| ``` | |
| По умолчанию [save_pretrained()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.save_pretrained) записывает каждый загруженный в данный момент компонент, который Diffusers может сериализовать. Компоненты, которые не загружены или не могут быть сериализованы, не записываются и сохраняют свои существующие спецификации загрузки. | |
| ### Сохранить автономную копию | |
| Загрузите все компоненты, а затем сохраните. Каждая спецификация указывает на результат, поэтому он полностью перезагружается из одного места, включая офлайн-режим. | |
| ```py | |
| pipe = ModularPipeline.from_pretrained("MiniMaxAI/MiniMax-H3") | |
| pipe.load_components() | |
| pipe.save_pretrained("path/to/local-copy") | |
| ``` | |
| Путь назначения, записанный в `modular_model_index.json`, — это то место, куда [save_pretrained()](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline.save_pretrained) записывает данные: `save_directory` при сохранении локально или `repo_id`, если вы передаёте `push_to_hub=True`. | |
| Перемещение файлов любым другим способом не обновляет индекс. Копия, загруженная с помощью `hf download --local-dir`, по-прежнему работает: при загрузке пайплайна из локального каталога каждый компонент, файлы которого присутствуют в этом каталоге, загружается из него, а не из указанного в индексе репозитория. Копия, загруженная с помощью `hf upload`, по-прежнему указывает на старое расположение, поэтому в этом случае необходимо вручную обновить индекс. | |
| Начиная с `huggingface_hub>=1.32.0`, идентичные файлы, использующие Xet, могут разделять один кэшированный payload между любыми репозиториями Hub. Это касается отдельных файлов в шардированном чекпоинте: шард с одинаковым Xet-хэшем может быть переиспользован, даже если другие шарды отличаются. Оба процесса загрузки должны использовать один и тот же каталог кэша Hub с поддержкой символьных ссылок. Изменение dtype, способа сериализации или границ шардов может изменить хэши файлов и предотвратить переиспользование. Это экономит трафик загрузки и место на диске, но не память, используемую загруженными компонентами. | |
| Общее кэширование работает в режиме best-effort. Установка переменной `HF_HUB_DISABLE_SHARED_BLOBS=1` по-прежнему поддерживает загрузку, но кэширует отдельные копии. Существующие ссылки на компоненты в `modular_model_index.json` остаются без изменений; сохраняйте внешние ссылки для компонентов, которые не хранятся в модульном репозитории. | |
| ### Ссылки на компоненты в других репозиториях | |
| Спецификация загрузки компонента в `modular_model_index.json` может указывать на другой репозиторий. Например, [diffusers/flux2-bnb-4bit-modular](https://huggingface.co/diffusers/flux2-bnb-4bit-modular) загружает свой квантованный трансформер из `diffusers/FLUX.2-dev-bnb-4bit`, а остальные компоненты — из `black-forest-labs/FLUX.2-dev`. | |
| Мы настоятельно рекомендуем использовать самодостаточные репозитории: объединение всех компонентов в одном месте упрощает загрузку, обмен и использование пайплайна в автономном режиме без зависимости от других репозиториев. Используйте ссылки на другие репозитории только в том случае, если вы намеренно хотите разместить компонент в другом месте. | |
| Передайте `overwrite_modular_index=False`, чтобы сохранить спецификации загрузки в `modular_model_index.json` без изменений. Сохранённый компонент с пустой спецификацией загрузки всё равно будет дополнен целевым значением, так как сохранять нечего. | |
| Начиная с версии `huggingface_hub>=1.32.0`, идентичные файлы, использующие Xet, могут разделять один кэшированный payload между репозиториями через символические ссылки, что позволяет избежать дублирования загрузок и использования дискового пространства. Для этого не требуется создавать ссылки между репозиториями. Требования и ограничения для общего кэша описаны в разделе [Сохранение автономной копии](#save-a-self-contained-copy). | |
| #### Обновление существующего модульного индекса | |
| Существующие ссылки на исходный репозиторий продолжают работать. Если ссылка использовалась только для предотвращения дублирования загрузок, рекомендуется обновить её для загрузки из модульного репозитория, как только файлы компонентов станут там доступны. | |
| Сначала убедитесь, что модульный репозиторий содержит ту же конфигурацию компонентов и все необходимые файлы весов, включая индекс весов и каждый шард для шардированного чекпоинта. Совпадение хешей Xet определяет, какие файлы весов можно повторно использовать из общего кэша. Сохраняйте ссылки на компоненты, которые отсутствуют или намеренно загружаются из другого чекпоинта. | |
| Измените только соответствующую спецификацию загрузки в локальной копии `modular_model_index.json`. Например, чтобы использовать VAE, хранящийся в `vae/` в модульном репозитории, с тем же вариантом весов: | |
| ```py | |
| import json | |
| from pathlib import Path | |
| index_path = Path("path/to/local-copy/modular_model_index.json") | |
| index = json.loads(index_path.read_text()) | |
| spec = index["vae"][2] | |
| spec["pretrained_model_name_or_path"] = "my-username/my-modular-repo" | |
| spec.pop("repo", None) | |
| spec["subfolder"] = "vae" | |
| spec["revision"] = None | |
| index_path.write_text(json.dumps(index, indent=2) + "\n") | |
| ``` | |
| Это также удаляет устаревшее поле `repo`. Ревизия из исходного репозитория не определяет ревизию в целевом: используйте `None` для ветки по умолчанию целевого репозитория или зафиксируйте ревизию целевого репозитория, содержащую компонент. При необходимости скорректируйте `subfolder` и `variant`, если имена файлов различаются. | |
| Перед публикацией обновленного индекса загрузите его с помощью `ModularPipeline.from_pretrained("path/to/local-copy")`, вызовите `load_components(names="vae")` и убедитесь, что компонент загружается с ожидаемыми параметрами. Загружайте только отредактированный индекс; повторное сохранение весов может изменить их хеши и помешать повторному использованию кэша. | |
| ### Пользовательский код | |
| Модульный репозиторий также может включать пользовательские блоки конвейера в виде Python-кода. Это позволяет делиться специализированными блоками, которые не являются нативными для Diffusers. Например, [diffusers/Florence2-image-Annotator](https://huggingface.co/diffusers/Florence2-image-Annotator) содержит пользовательские блоки наряду с конфигурацией загрузки: | |
| ``` | |
| Florence2-image-Annotator/ | |
| ├── block.py # Custom pipeline blocks implementation | |
| ├── config.json # Pipeline configuration and auto_map | |
| ├── mellon_config.json # UI configuration for Mellon | |
| └── modular_model_index.json # Component loading specifications | |
| ``` | |
| Файл `config.json` содержит ключ `auto_map`, который указывает [ModularPipeline](/docs/diffusers/v0.43.0/ru/api/modular_diffusers/pipeline#diffusers.ModularPipeline), где искать пользовательские блоки: | |
| ```json | |
| { | |
| "_class_name": "Florence2AnnotatorBlocks", | |
| "auto_map": { | |
| "ModularPipelineBlocks": "block.Florence2AnnotatorBlocks" | |
| } | |
| } | |
| ``` | |
| Загружайте репозитории с пользовательским кодом с помощью `trust_remote_code=True`, как показано в [from_pretrained](#frompretrained). О том, как создавать и делиться собственными блоками, см. в разделе [Custom blocks](./custom_blocks). | |
Xet Storage Details
- Size:
- 37.9 kB
- Xet hash:
- 1d5565691abed01a8aa18175c97587d8769846d0d2807578e58e83c0dd86bc51
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.