Buckets:
| # 빠른 시작 | |
| Modular Diffusers는 유연하고 사용자 정의 가능한 파이프라인을 빠르게 구축하기 위한 프레임워크입니다. 이러한 파이프라인은 표준 `DiffusionPipeline`의 범위를 넘어설 수 있습니다. Modular Diffusers의 핵심은 새로운 워크플로우에 맞게 다른 블록과 결합할 수 있는 [ModularPipelineBlocks](/docs/diffusers/main/ko/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks)입니다. 이 블록들은 생성 작업을 실행하기 위한 사용자 친화적인 인터페이스인 [ModularPipeline](/docs/diffusers/main/ko/api/modular_diffusers/pipeline#diffusers.ModularPipeline)으로 변환됩니다. | |
| 이 가이드에서는 모듈형 파이프라인을 실행하는 방법, 그 구조를 이해하는 방법, 그리고 구성 블록을 수정하여 파이프라인을 커스터마이징하는 방법을 보여줍니다. [DiffusionPipeline](/docs/diffusers/main/ko/api/pipelines/overview#diffusers.DiffusionPipeline)에 익숙하시다면, 무엇이 다른지 확인하기 위해 먼저 [Coming from DiffusionPipeline](./coming_from_diffusion_pipeline)을 읽어보세요. | |
| ## 파이프라인 실행 | |
| [ModularPipeline](/docs/diffusers/main/ko/api/modular_diffusers/pipeline#diffusers.ModularPipeline)는 모듈형 파이프라인을 로드하고 실행하며 관리하기 위한 주요 인터페이스입니다. | |
| ```py | |
| import torch | |
| from diffusers import ModularPipeline, ComponentsManager | |
| # Use ComponentsManager to enable auto CPU offloading for memory efficiency | |
| manager = ComponentsManager() | |
| manager.enable_auto_cpu_offload(device="cuda:0") | |
| pipe = ModularPipeline.from_pretrained("Qwen/Qwen-Image", components_manager=manager) | |
| pipe.load_components(dtype=torch.bfloat16) | |
| image = pipe( | |
| prompt="cat wizard with red hat, gandalf, lord of the rings, detailed, fantasy, cute, adorable, Pixar, Disney", | |
| ).images[0] | |
| image | |
| ``` | |
| [from_pretrained()](/docs/diffusers/main/ko/api/modular_diffusers/pipeline#diffusers.ModularPipeline.from_pretrained)는 지연 로딩을 사용합니다. 구성을 읽어 각 구성 요소를从哪里 로드할지 파악하지만, [load_components()](/docs/diffusers/main/ko/api/modular_diffusers/pipeline#diffusers.ModularPipeline.load_components)를 호출할 때까지 실제 모델 가중치를 로드하지 않습니다. 이를 통해 구성 요소의 로드 시점과 방식을 제어할 수 있습니다. | |
| > [!TIP] | |
| > `ComponentsManager`에 `enable_auto_cpu_offload`를 사용하면 필요에 따라 모델이 CPU와 GPU 사이로 자동으로 이동하여 Qwen-Image와 같은 대규모 모델의 메모리 사용량을 줄입니다. 자세한 내용은 [ComponentsManager](./components_manager) 가이드를 참고하세요. | |
| > | |
| > 오프로딩이 필요하지 않다면 `components_manager` 인수를 제거하고 `to("cuda")`를 사용하여 파이프라인을 수동으로 원하는 장치로 이동하세요. | |
| [파이프라인 만들기](https://huggingface.co/docs/diffusers/modular_diffusers/modular_pipeline#creating-a-pipeline) 및 [컴포넌트 로드](https://huggingface.co/docs/diffusers/modular_diffusers/modular_pipeline#loading-components) 가이드에서 파이프라인 생성 및 로드에 대해 자세히 알아보세요. | |
| ## 구조 이해하기 | |
| [ModularPipeline](/docs/diffusers/main/ko/api/modular_diffusers/pipeline#diffusers.ModularPipeline)는 두 부분으로 구성됩니다: **정의**(블록)와 **상태**(로드된 컴포넌트와 설정). | |
| print을 사용하여 파이프라인의 상태를 확인합니다. 구성 요소, 로딩 상태 및 구성이 표시됩니다. | |
| ```py | |
| print(pipe) | |
| ``` | |
| ``` | |
| QwenImageModularPipeline { | |
| "_blocks_class_name": "QwenImageAutoBlocks", | |
| "_class_name": "QwenImageModularPipeline", | |
| "_diffusers_version": "0.37.0.dev0", | |
| "transformer": [ | |
| "diffusers", | |
| "QwenImageTransformer2DModel", | |
| { | |
| "pretrained_model_name_or_path": "Qwen/Qwen-Image", | |
| "revision": null, | |
| "subfolder": "transformer", | |
| "type_hint": [ | |
| "diffusers", | |
| "QwenImageTransformer2DModel" | |
| ], | |
| "variant": null | |
| } | |
| ], | |
| ... | |
| } | |
| ``` | |
| `pipe.blocks`를 통해 정의를 접근할 수 있습니다. 이는 파이프라인의 워크플로, 입력, 출력 및 계산 로직을 정의하는 [ModularPipelineBlocks](/docs/diffusers/main/ko/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks)입니다. | |
| ```py | |
| print(pipe.blocks) | |
| ``` | |
| ``` | |
| QwenImageAutoBlocks( | |
| Class: SequentialPipelineBlocks | |
| Description: Auto Modular pipeline for text-to-image, image-to-image, inpainting, and controlnet tasks using QwenImage. | |
| Supported workflows: | |
| - `text2image`: requires `prompt` | |
| - `image2image`: requires `prompt`, `image` | |
| - `inpainting`: requires `prompt`, `mask_image`, `image` | |
| - `controlnet_text2image`: requires `prompt`, `control_image` | |
| ... | |
| Components: | |
| text_encoder (`Qwen2_5_VLForConditionalGeneration`) | |
| vae (`AutoencoderKLQwenImage`) | |
| transformer (`QwenImageTransformer2DModel`) | |
| ... | |
| Sub-Blocks: | |
| [0] text_encoder (QwenImageAutoTextEncoderStep) | |
| [1] vae_encoder (QwenImageAutoVaeEncoderStep) | |
| [2] controlnet_vae_encoder (QwenImageOptionalControlNetVaeEncoderStep) | |
| [3] denoise (QwenImageAutoCoreDenoiseStep) | |
| [4] decode (QwenImageAutoDecodeStep) | |
| ) | |
| ``` | |
| 출력은 다음을 반환합니다: | |
| - 지원되는 워크플로(text2image, image2image, inpainting 등) | |
| - 구성 요소인 서브 블록(text_encoder, vae_encoder, denoise, decode) | |
| ### 워크플로 | |
| 이 파이프라인은 여러 워크플로를 지원하며, 제공한 입력에 따라 동작을 조정합니다. 예를 들어, 파이프라인에 `image`를 전달하면 텍스트-이미지 대신 이미지-이미지 워크플로가 실행됩니다. 내부 동작 방식에 대한 자세한 내용은 [AutoPipelineBlocks](https://huggingface.co/docs/diffusers/modular_diffusers/auto_pipeline_blocks) 가이드에서 확인하세요. | |
| ```py | |
| from diffusers.utils import load_image | |
| input_image = load_image("https://github.com/Trgtuan10/Image_storage/blob/main/cute_cat.png?raw=true") | |
| image = pipe( | |
| prompt="cat wizard with red hat, gandalf, lord of the rings, detailed, fantasy, cute, adorable, Pixar, Disney", | |
| image=input_image, | |
| ).images[0] | |
| ``` | |
| `get_workflow()`을 사용하여 특정 워크플로의 블록을 추출합니다. 워크플로 이름(예: `"image2image"`, `"inpainting"`, `"controlnet_text2image"`)을 전달하면 해당 워크플로에 관련되는 블록만 가져옵니다. 이는 특정 워크플로를 사용자 지정하거나 디버깅하려는場合に 유용합니다. `pipe.blocks.available_workflows`를 확인하여 사용 가능한 모든 워크플로를 볼 수 있습니다. | |
| ```py | |
| img2img_blocks = pipe.blocks.get_workflow("image2image") | |
| ``` | |
| ### 서브 블록 | |
| Blocks는 다른 Blocks를 포함할 수 있습니다. `pipe.blocks`는 최상위 블록 정의(여기서는 `QwenImageAutoBlocks`)를 제공하며, `sub_blocks`를 사용하면 그 안의 더 작은 블록에 접근할 수 있습니다. | |
| `QwenImageAutoBlocks`는 `text_encoder`, `vae_encoder`, `controlnet_vae_encoder`, `denoise`, `decode`로 구성됩니다. | |
| 이러한 서브 블록은 순차적으로 실행되며 데이터는 하나의 블록에서 다음 블록으로 선형적으로 흐릅니다. 각 블록의 `intermediate_outputs`이 다음 블록의 `inputs`으로 사용 가능합니다. [`SequentialPipelineBlocks`](./sequential_pipeline_blocks)가 작동하는 방식입니다. | |
| `sub_blocks` 속성을 통해 액세스할 수 있습니다. `doc` 속성은 입력, 출력 및 구성 요소를 포함한 블록의 전체 문서를 확인하는 데 유용합니다. | |
| ```py | |
| vae_encoder_block = pipe.blocks.sub_blocks["vae_encoder"] | |
| print(vae_encoder_block.doc) | |
| ``` | |
| 이 블록은 [init_pipeline()](/docs/diffusers/main/ko/api/modular_diffusers/pipeline_blocks#diffusers.ModularPipelineBlocks.init_pipeline)을 사용하여 독립적으로 실행되도록 파이프라인으로 변환할 수 있습니다. | |
| ```py | |
| vae_encoder_pipe = vae_encoder_block.init_pipeline() | |
| # Reuse the VAE we already loaded, we can reuse it with update_components() method | |
| vae_encoder_pipe.update_components(vae=pipe.vae) | |
| # Run just this block | |
| image_latents = vae_encoder_pipe(image=input_image).image_latents | |
| print(image_latents.shape) | |
| ``` | |
| 새로 로드하는 대신 원래 파이프라인의 VAE를 재사용하여 메모리 사용량을 효율적으로 유지합니다. [컴포넌트 로드](https://huggingface.co/docs/diffusers/modular_diffusers/modular_pipeline#loading-components) 가이드에서 자세히 알아보세요. | |
| 블록은 구성 가능(composable)하므로, 블록을 추가하거나 제거하거나 교체하여 파이프라인의 정의를 수정하고 새로운 워크플로를 만들 수 있습니다. 다음 섹션에서는 ControlNet 파이프라인에 canny edge detection 블록을 추가하여, 사전 처리된 canny edge map 대신 일반 이미지를 전달할 수 있도록 합니다. | |
| ## 새 워크플로우 구성 | |
| ControlNet 파이프라인에 canny edge detection 블록을 추가해 보겠습니다. 먼저 Hub에서 미리 만들어진 canny 블록을 로드합니다(직접 만들려면 [Building Custom Blocks](https://huggingface.co/docs/diffusers/modular_diffusers/custom_blocks)를 참고하세요). | |
| ```py | |
| from diffusers.modular_pipelines import ModularPipelineBlocks | |
| # Load a canny block from the Hub | |
| canny_block = ModularPipelineBlocks.from_pretrained( | |
| "diffusers-internal-dev/canny-filtering", | |
| trust_remote_code=True, | |
| ) | |
| print(canny_block.doc) | |
| ``` | |
| ``` | |
| class CannyBlock | |
| Inputs: | |
| image (`Union[Image, ndarray]`): | |
| Image to compute canny filter on | |
| low_threshold (`int`, *optional*, defaults to 50): | |
| Low threshold for the canny filter. | |
| high_threshold (`int`, *optional*, defaults to 200): | |
| High threshold for the canny filter. | |
| ... | |
| Outputs: | |
| control_image (`PIL.Image`): | |
| Canny map for input image | |
| ``` | |
| `get_workflow`를 사용하여 `QwenImageAutoBlocks`에서 ControlNet 워크플로를 추출합니다. | |
| ```py | |
| # Get the controlnet workflow that we want to work with | |
| blocks = pipe.blocks.get_workflow("controlnet_text2image") | |
| print(blocks.doc) | |
| ``` | |
| ``` | |
| class SequentialPipelineBlocks | |
| Inputs: | |
| prompt (`str`): | |
| The prompt or prompts to guide image generation. | |
| control_image (`Image`): | |
| Control image for ControlNet conditioning. | |
| ... | |
| ``` | |
| 추출된 워크플로우는 [`SequentialPipelineBlocks`](./sequential_pipeline_blocks)이며 현재 `control_image`를 입력으로 요구합니다. 파이프라인이 일반 이미지를 대신 받아들이도록 canny 블록을 맨 앞에 삽입하세요. | |
| ```py | |
| # Insert canny at the beginning | |
| blocks.sub_blocks.insert("canny", canny_block, 0) | |
| # Check the updated structure: CannyBlock is now listed as first sub-block | |
| print(blocks) | |
| # Check the updated doc | |
| print(blocks.doc) | |
| ``` | |
| ``` | |
| class SequentialPipelineBlocks | |
| Inputs: | |
| image (`Union[Image, ndarray]`): | |
| Image to compute canny filter on | |
| low_threshold (`int`, *optional*, defaults to 50): | |
| Low threshold for the canny filter. | |
| high_threshold (`int`, *optional*, defaults to 200): | |
| High threshold for the canny filter. | |
| prompt (`str`): | |
| The prompt or prompts to guide image generation. | |
| ... | |
| ``` | |
| 이제 파이프라인은 `control_image` 대신 `image`를 입력으로 받습니다. 시퀀스의 블록은 데이터를 자동으로 공유하므로, canny 블록의 출력(`control_image`)은 이를 필요로 하는 denoise 블록으로 전달되고, canny 블록의 입력(`image`)은 이전 블록에서 이를 제공하지 않으므로 파이프라인 입력이 됩니다. | |
| 수정된 블록으로 파이프라인을 생성하고 ControlNet 모델을 로드합니다. ControlNet은 원래 모델 저장소의 일부가 아니므로 별도로 로드한 뒤 [update_components()](/docs/diffusers/main/ko/api/modular_diffusers/pipeline#diffusers.ModularPipeline.update_components)로 추가합니다. | |
| ```py | |
| pipeline = blocks.init_pipeline("Qwen/Qwen-Image", components_manager=manager) | |
| pipeline.load_components(dtype=torch.bfloat16) | |
| # Load the ControlNet model | |
| controlnet_spec = pipeline.get_component_spec("controlnet") | |
| controlnet_spec.pretrained_model_name_or_path = "InstantX/Qwen-Image-ControlNet-Union" | |
| controlnet = controlnet_spec.load(dtype=torch.bfloat16) | |
| pipeline.update_components(controlnet=controlnet) | |
| ``` | |
| 이제 파이프라인을 실행합니다. canny 블록은 ControlNet을 위해 이미지를 전처리합니다. | |
| ```py | |
| from diffusers.utils import load_image | |
| prompt = "cat wizard with red hat, gandalf, lord of the rings, detailed, fantasy, cute, adorable, Pixar, Disney" | |
| image = load_image("https://github.com/Trgtuan10/Image_storage/blob/main/cute_cat.png?raw=true") | |
| output = pipeline( | |
| prompt=prompt, | |
| image=image, | |
| ).images[0] | |
| output | |
| ``` | |
| ## 다음 단계 | |
| Modular Diffusers의 핵심 구성 요소를 이해해 보세요: | |
| - [ModularPipelineBlocks](./pipeline_block): 파이프라인의 단계를 정의하는 기본 단위입니다. | |
| - [SequentialPipelineBlocks](./sequential_pipeline_blocks): 블록을 순서대로 실행되도록 체인합니다. | |
| - [AutoPipelineBlocks](./auto_pipeline_blocks): 여러 워크플로를 지원하는 파이프라인을 생성합니다. | |
| - [상태](./modular_diffusers_states): 블록 간 데이터 공유 방식. | |
| [커스텀 블록 만들기](./custom_blocks) 가이드에서 커스텀 로직을 사용하여 나만의 블록을 만드는 방법을 배워보세요. | |
| [`ComponentsManager`](./components_manager)를 사용하여 여러 파이프라인 간에 모델을 공유하고 메모리를 효율적으로 관리하세요. | |
| 모듈형 파이프라인을 워크플로우를 구축하기 위한 시각적 노드 기반 인터페이스인 [Mellon](https://github.com/cubiq/Mellon)에 연결합니다. Modular Diffusers로 구축한 커스텀 블록은 Mellon과 즉시 호환되며 UI 코드가 필요하지 않습니다. 자세한 내용은 Mellon 가이드를 참고하세요. | |
Xet Storage Details
- Size:
- 14.2 kB
- Xet hash:
- 16a6cba73811fadf795cb365fd873fddaa8aeb1943c4be1781b719088b10c8df
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.