Buckets:
| # ModularPipeline | |
| [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) converte [ModularPipelineBlocks](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) em um pipeline executável que carrega modelos e executa as etapas de computação definidas nos blocos. É a interface principal para executar um pipeline e a API é muito semelhante à do [DiffusionPipeline](/docs/diffusers/v0.43.0/pt/api/pipelines/overview#diffusers.DiffusionPipeline), mas com algumas diferenças importantes. | |
| - **O carregamento é preguiçoso.** Com o [DiffusionPipeline](/docs/diffusers/v0.43.0/pt/api/pipelines/overview#diffusers.DiffusionPipeline), [from_pretrained()](/docs/diffusers/v0.43.0/pt/api/pipelines/overview#diffusers.DiffusionPipeline.from_pretrained) cria o pipeline e carrega todos os modelos ao mesmo tempo. Com o [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline), a criação e o carregamento são duas etapas separadas: [from_pretrained()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained) lê a configuração e sabe de onde carregar cada componente, mas não carrega efetivamente os pesos do modelo. Você carrega os modelos depois com [load_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components), onde você passa argumentos de carregamento como `dtype` e `quantization_config`. | |
| - **Duas formas de criar um pipeline.** Você pode usar [from_pretrained()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained) com um repositório de modelo diffusers existente — ele mapeia automaticamente para os blocos de pipeline padrão e, em seguida, converte para um [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) sem configuração adicional. Você pode verificar o [modular_pipelines_directory](https://github.com/huggingface/diffusers/tree/main/src/diffusers/modular_pipelines) para ver quais modelos são atualmente suportados. Você também pode montar seu próprio pipeline a partir de [ModularPipelineBlocks](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) e convertê-lo com o método [init_pipeline()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) (veja [Criando um pipeline](#creating-a-pipeline) para mais detalhes). | |
| - **A execução do pipeline é a mesma.** Uma vez carregado, você chama o pipeline com os mesmos argumentos a que está acostumado. Um único [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) pode suportar múltiplos fluxos de trabalho (texto-para-imagem, imagem-para-imagem, inpainting, etc.) quando os blocos do pipeline usam [`AutoPipelineBlocks`](./auto_pipeline_blocks) para selecionar automaticamente o fluxo de trabalho com base nas suas entradas. | |
| Abaixo estão exemplos completos para texto-para-imagem, imagem-para-imagem e inpainting com 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") | |
| ``` | |
| Este guia mostrará como criar um [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline), gerenciar seus componentes e executar o pipeline. | |
| ## Criando um pipeline | |
| Existem duas formas de criar um [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline). Monte e crie um pipeline a partir de [ModularPipelineBlocks](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) com [init_pipeline()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline), ou carregue um pipeline existente com [from_pretrained()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained). | |
| Você também pode inicializar um [`ComponentsManager`](./components_manager) para gerenciar a colocação de dispositivos e a memória. Se você não precisar de offloading automático, pode pular isso e mover o pipeline para o seu dispositivo manualmente com `pipeline.to("cuda")`. | |
| > [!TIP] | |
| > Consulte a documentação do [ComponentsManager](./components_manager) para mais detalhes sobre como ele pode ajudar a gerenciar componentes em diferentes fluxos de trabalho. | |
| ### init_pipeline | |
| [init_pipeline()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) converte qualquer [ModularPipelineBlocks](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks) em um [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline). | |
| Vamos definir um bloco mínimo para ver como ele funciona: | |
| ```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 | |
| ``` | |
| Chame [init_pipeline()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) para convertê-lo em um pipeline. O atributo `blocks` no pipeline são os blocos a partir dos quais ele foi criado — eles determinam as entradas, saídas e a lógica de computação esperadas. | |
| ```py | |
| block = MyBlock() | |
| pipe = block.init_pipeline() | |
| pipe.blocks | |
| ``` | |
| ``` | |
| MyBlock { | |
| "_class_name": "MyBlock", | |
| "_diffusers_version": "0.37.0.dev0" | |
| } | |
| ``` | |
| > [!WARNING] | |
| > Os blocos são mutáveis — você pode adicionar, remover ou trocar blocos livremente antes de criar um pipeline. No entanto, uma vez que um pipeline é criado, modificar `pipeline.blocks` não afetará o pipeline, pois ele retorna uma cópia. Se você deseja uma estrutura de blocos diferente, crie um novo pipeline após modificar os blocos. | |
| Quando você chama [init_pipeline()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline) sem um repositório, ele usa o `pretrained_model_name_or_path` definido no [ComponentSpec](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec) do bloco para determinar de onde carregar cada componente. Imprimir o pipeline mostra a configuração de carregamento dos componentes. | |
| ```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 | |
| } | |
| ] | |
| } | |
| ``` | |
| Se você passar um repositório para [init_pipeline()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline), ele sobrescreve o caminho de carregamento ao corresponder os componentes do seu bloco à configuração do pipeline nesse repositório (`model_index.json` ou `modular_model_index.json`). Consulte [Modular repository](#modular-repository) para saber como as especificações de carregamento são registradas e salvas. | |
| No exemplo abaixo, o `pretrained_model_name_or_path` será atualizado para `"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 | |
| } | |
| ] | |
| } | |
| ``` | |
| Se um componente do seu bloco não existir no repositório, ele permanece como `null` e é ignorado durante o [load_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components). | |
| ### from_pretrained | |
| [from_pretrained()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained) é uma maneira conveniente de criar um [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) sem definir os blocos você mesmo. | |
| Ele funciona com três tipos de repositórios. | |
| **Um repositório de diffusers padrão.** Passe qualquer repositório de modelo suportado e ele será mapeado automaticamente para os blocos de pipeline padrão. Os modelos atualmente suportados incluem SDXL, Wan, Qwen, Z-Image, Flux e Flux2. | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| components = ComponentsManager() | |
| pipeline = ModularPipeline.from_pretrained( | |
| "stabilityai/stable-diffusion-xl-base-1.0", components_manager=components | |
| ) | |
| ``` | |
| **Um repositório modular.** Esses repositórios contêm um `modular_model_index.json` que especifica a classe de cada componente e de onde carregá-lo, com os componentes armazenados ao lado dele. Consulte [Repositório modular](#modular-repository) para saber como criar um. | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| components = ComponentsManager() | |
| pipeline = ModularPipeline.from_pretrained( | |
| "MiniMaxAI/MiniMax-H3", components_manager=components | |
| ) | |
| ``` | |
| **Um repositório modular com código personalizado.** Alguns repositórios incluem blocos de pipeline personalizados junto com a configuração de carregamento. Adicione `trust_remote_code=True` para carregá-los. Consulte [Blocos personalizados](./custom_blocks) para saber como criar os seus próprios. | |
| ```py | |
| from diffusers import ModularPipeline, ComponentsManager | |
| components = ComponentsManager() | |
| pipeline = ModularPipeline.from_pretrained( | |
| "diffusers/Florence2-image-Annotator", trust_remote_code=True, components_manager=components | |
| ) | |
| ``` | |
| Quando os blocos do pipeline definem fluxos de trabalho (consulte `pipeline.blocks.available_workflows`), passe `workflow=` para manter apenas os blocos daquele fluxo de trabalho — o mesmo recorte de [get_workflow()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.get_workflow). O pipeline então declara apenas os componentes usados por aquele fluxo de trabalho, e sua docstring descreve exatamente as entradas daquele fluxo de trabalho. | |
| ```py | |
| pipeline = ModularPipeline.from_pretrained("Qwen/Qwen-Image", workflow="inpainting") | |
| ``` | |
| ## Carregando componentes | |
| A [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) não é instanciada automaticamente com componentes. Ela apenas carrega a configuração e as especificações dos componentes. Você pode carregar os componentes com [load_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components). | |
| Isso carregará todos os componentes que possuem uma especificação de carregamento válida. | |
| ```py | |
| import torch | |
| pipeline.load_components(dtype=torch.float16) | |
| ``` | |
| Você também pode carregar componentes específicos pelo nome. O exemplo abaixo carrega apenas o `text_encoder`. | |
| ```py | |
| pipeline.load_components(names=["text_encoder"], dtype=torch.float16) | |
| ``` | |
| Em um pipeline cujos blocos definem fluxos de trabalho, `workflow=` carrega apenas os componentes que o fluxo de trabalho utiliza. O pipeline mantém todos os seus blocos, portanto, essa é a maneira conveniente de executar um único pipeline em vários fluxos de trabalho: cada chamada adiciona apenas o que o novo fluxo de trabalho ainda não possui. | |
| ```py | |
| pipeline.load_components(workflow="inpainting", dtype=torch.float16) | |
| ``` | |
| Após o carregamento, a impressão do pipeline mostra quais componentes foram carregados — os dois primeiros campos mudam de `null` para a biblioteca e a classe do componente. | |
| ```py | |
| pipeline | |
| ``` | |
| ``` | |
| # text_encoder is loaded - shows library and class | |
| "text_encoder": [ | |
| "transformers", | |
| "CLIPTextModel", | |
| { ... } | |
| ] | |
| # unet is not loaded yet - still null | |
| "unet": [ | |
| null, | |
| null, | |
| { ... } | |
| ] | |
| ``` | |
| Argumentos de palavra-chave como `dtype`, `variant`, `revision` e `quantization_config` são repassados para `from_pretrained()` de cada componente. Você pode passar um único valor para aplicar a todos os componentes, ou um dict para definir valores por componente. | |
| ```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/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components) carrega apenas os componentes que ainda não foram carregados e que possuem uma especificação de carregamento válida. Isso significa que, se você já configurou um componente no pipeline, chamar [load_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components) novamente não o recarregará. | |
| ## Atualizando componentes | |
| [update_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.update_components) substitui um componente no pipeline por um novo. Quando um componente é atualizado, as especificações de carregamento também são atualizadas na configuração do pipeline e [load_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components) o ignorará nas chamadas subsequentes. | |
| ### De AutoModel | |
| Você pode passar um objeto de modelo carregado com `AutoModel.from_pretrained()`. Modelos carregados dessa forma são automaticamente marcados com suas informações de carregamento. | |
| ```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) | |
| ``` | |
| ### De ComponentSpec | |
| Use [get_component_spec()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.get_component_spec) para obter uma cópia da especificação atual do componente, modificá-la e carregar um novo componente. | |
| ```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) | |
| ``` | |
| Você também pode criar um [ComponentSpec](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec) do zero. | |
| Nem todos os componentes são carregados a partir de pesos pré-treinados — alguns são criados a partir de uma configuração (listados em `pipeline.config_component_names`). Para esses, use [create()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_components#diffusers.ComponentSpec.create) em vez de [load()](/docs/diffusers/v0.43.0/pt/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) | |
| ``` | |
| Ou simplesmente passe o objeto diretamente. | |
| ```py | |
| from diffusers.guiders import ClassifierFreeGuidance | |
| guider = ClassifierFreeGuidance(guidance_scale=5.0) | |
| pipeline.update_components(guider=guider) | |
| ``` | |
| Consulte o guia [Guiders](../using-diffusers/guiders) para mais detalhes sobre os guiders disponíveis e como configurá-los. | |
| ## Dividir um pipeline em etapas | |
| Como os blocos são composíveis, você pode desmontar um pipeline e reconstruí-lo em pipelines separados para cada etapa. O exemplo abaixo mostra como podemos separar o bloco do codificador de texto do restante do pipeline, para que você possa codificar o prompt de forma independente e passar os embeddings para o pipeline principal. | |
| ```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/pt/api/modular_diffusers/pipeline_components#diffusers.ComponentsManager) gerencia a memória entre vários pipelines. Diferentemente das estratégias de offloading em [DiffusionPipeline](/docs/diffusers/v0.43.0/pt/api/pipelines/overview#diffusers.DiffusionPipeline), que seguem uma ordem fixa, o [ComponentsManager](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline_components#diffusers.ComponentsManager) toma decisões de offloading dinamicamente a cada vez que uma passagem de modelo para frente é executada, com base na situação atual de memória. Isso significa que ele funciona independentemente de quantos pipelines você cria ou em que ordem você os executa. Consulte o guia de [ComponentsManager](./components_manager) para mais detalhes. | |
| Se os estágios do pipeline compartilham componentes (por exemplo, o mesmo VAE usado para codificação e decodificação), você pode usar [update_components()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.update_components) para passar um componente já carregado para outro pipeline, em vez de carregá-lo novamente. | |
| ## Repositório modular | |
| Um repositório é obrigatório se os blocos do pipeline usarem *componentes pré-treinados*. O repositório fornece especificações de carregamento e metadados. | |
| [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) funciona com repositórios regulares do diffusers sem necessidade de configuração adicional. No entanto, você também pode criar um *repositório modular* para mais flexibilidade. Um repositório modular contém um arquivo `modular_model_index.json` com os seguintes 3 elementos. | |
| - `library` e `class` mostram de qual biblioteca o componente foi carregado e sua classe. Se for `null`, o componente ainda não foi carregado. | |
| - `loading_specs_dict` contém as informações necessárias para carregar o componente, como o repositório e a subpasta de onde ele é carregado. | |
| ```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) | |
| ``` | |
| Por padrão, [save_pretrained()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.save_pretrained) grava cada componente atualmente carregado que o Diffusers pode serializar. Componentes que não estão carregados, ou que não podem ser serializados, não são gravados e mantêm suas especificações de carregamento existentes. | |
| ### Salvar uma cópia autossuficiente | |
| Carregue todos os componentes e, em seguida, salve. Cada especificação aponta para o resultado, portanto, ele é recarregado inteiramente de um único local, inclusive offline. | |
| ```py | |
| pipe = ModularPipeline.from_pretrained("MiniMaxAI/MiniMax-H3") | |
| pipe.load_components() | |
| pipe.save_pretrained("path/to/local-copy") | |
| ``` | |
| O destino registrado em `modular_model_index.json` é onde [save_pretrained()](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline.save_pretrained) grava: o `save_directory` para um salvamento local, ou o `repo_id` quando você passa `push_to_hub=True`. | |
| Mover os arquivos de qualquer outra forma não reescreve o índice. Uma cópia baixada com `hf download --local-dir` continua funcionando: quando um pipeline é carregado de um diretório local, cada componente cujos arquivos estão presentes nesse diretório é carregado dele em vez do repositório registrado. Uma cópia enviada com `hf upload` continua apontando para o local antigo, portanto, atualize o índice manualmente nesse caso. | |
| Com `huggingface_hub>=1.32.0`, arquivos idênticos com suporte a Xet podem compartilhar um único payload em cache entre qualquer repositório do Hub. Isso inclui arquivos individuais em um checkpoint fragmentado: um fragmento com o mesmo hash Xet pode ser reutilizado mesmo quando outros fragmentos diferem. Ambos os downloads devem usar o mesmo diretório de cache do Hub com suporte a symlinks. Alterar o dtype, a serialização ou as fronteiras dos fragmentos pode alterar os hashes dos arquivos e impedir a reutilização. Isso economiza tráfego de download e espaço em disco, não a memória usada pelos componentes carregados. | |
| O cache compartilhado é feito da melhor forma possível. Definir `HF_HUB_DISABLE_SHARED_BLOBS=1` ainda suporta o carregamento, mas faz o cache de cópias separadas. As referências de componentes existentes em `modular_model_index.json` permanecem inalteradas; mantenha as referências externas para componentes que não são armazenados no repositório modular. | |
| ### Referenciando componentes em outros repositórios | |
| A especificação de carregamento de um componente em `modular_model_index.json` pode apontar para um repositório diferente. Por exemplo, [diffusers/flux2-bnb-4bit-modular](https://huggingface.co/diffusers/flux2-bnb-4bit-modular) carrega seu transformer quantizado de `diffusers/FLUX.2-dev-bnb-4bit` e os componentes restantes de `black-forest-labs/FLUX.2-dev`. | |
| Preferimos fortemente repositórios autossuficientes: manter todos os componentes juntos torna um pipeline mais fácil de baixar, compartilhar e usar offline, sem depender de outros repositórios. Use referências entre repositórios apenas quando você intencionalmente quiser que um componente seja hospedado em outro local. | |
| Pass `overwrite_modular_index=False` para manter as especificações de carregamento em `modular_model_index.json` como estão. Um componente salvo cuja especificação de carregamento está vazia ainda é preenchido com o destino, pois não há nada a preservar. | |
| Com `huggingface_hub>=1.32.0`, arquivos idênticos com suporte Xet podem compartilhar um único payload em cache entre repositórios por meio de links simbólicos, evitando downloads duplicados e uso de disco. Referências entre repositórios não são necessárias para isso. Consulte [Salvar uma cópia autossuficiente](#save-a-self-contained-copy) para os requisitos e limitações do cache compartilhado. | |
| #### Atualizar um índice modular existente | |
| As referências existentes ao repositório original continuam funcionando. Se uma referência era usada apenas para evitar downloads duplicados, prefira atualizá-la para carregar do repositório modular assim que os arquivos de componentes estiverem disponíveis lá. | |
| Primeiro, verifique se o repositório modular contém a mesma configuração de componentes e todos os arquivos de pesos necessários, incluindo o índice de pesos e todos os shards para um checkpoint particionado. Os hashes Xet correspondentes determinam quais arquivos de pesos podem reutilizar o cache compartilhado. Mantenha referências a componentes ausentes ou carregados intencionalmente de outro checkpoint. | |
| Edite apenas a especificação de carregamento relevante em uma cópia local de `modular_model_index.json`. Por exemplo, para usar um VAE armazenado em `vae/` no repositório modular com a mesma variante de pesos: | |
| ```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") | |
| ``` | |
| Isso também remove o campo legado `repo`. Uma revisão do repositório original não identifica uma revisão no destino: use `None` para o branch padrão do destino ou fixe uma revisão de destino que contenha o componente. Ajuste `subfolder` e `variant` se os nomes dos arquivos forem diferentes. | |
| Antes de publicar o índice atualizado, carregue-o com `ModularPipeline.from_pretrained("path/to/local-copy")`, chame `load_components(names="vae")` e verifique se o componente é carregado com os parâmetros esperados. Envie apenas o índice editado; salvar novamente os pesos pode alterar seus hashes e impedir a reutilização do cache. | |
| ### Código personalizado | |
| Um repositório modular também pode incluir blocos de pipeline personalizados como código Python. Isso permite compartilhar blocos especializados que não são nativos do Diffusers. Por exemplo, [diffusers/Florence2-image-Annotator](https://huggingface.co/diffusers/Florence2-image-Annotator) contém blocos personalizados junto com a configuração de carregamento: | |
| ``` | |
| 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 | |
| ``` | |
| O arquivo `config.json` contém uma chave `auto_map` que informa ao [ModularPipeline](/docs/diffusers/v0.43.0/pt/api/modular_diffusers/pipeline#diffusers.ModularPipeline) onde encontrar os blocos personalizados: | |
| ```json | |
| { | |
| "_class_name": "Florence2AnnotatorBlocks", | |
| "auto_map": { | |
| "ModularPipelineBlocks": "block.Florence2AnnotatorBlocks" | |
| } | |
| } | |
| ``` | |
| Carregue repositórios de código personalizados com `trust_remote_code=True`, conforme mostrado em [from_pretrained](#frompretrained). Consulte [Blocos personalizados](./custom_blocks) para saber como criar e compartilhar os seus. | |
Xet Storage Details
- Size:
- 28.8 kB
- Xet hash:
- ea343c4d1eba8a64ffada4fb9a0fb9a320a0d77da82171bac78e6394374d7d92
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.