""" Inject apply_rotary_emb on comfy.ldm.qwen_image.model before any custom node __init__. ComfyUI-nunchaku loads before ComfyUI-QwenImageLoraLoader (Windows listdir order), so __init__.py alone is too late. prestartup_script.py runs from main.execute_prestartup_script(). """ import importlib.util import logging import os logger = logging.getLogger(__name__) _PATCH_DIR = os.path.join(os.path.dirname(os.path.abspath(__file__)), "patches") _NUNCHAKU_PATCH_PATH = os.path.join(_PATCH_DIR, "nunchaku_patch.py") _DOCSTRING_PATCH_PATH = os.path.join(_PATCH_DIR, "transformers_qwen_vl_docstring_patch.py") _IP_KWARGS_PATCH_PATH = os.path.join(_PATCH_DIR, "transformers_image_processor_kwargs_patch.py") def _load_patch_module(module_name: str, path: str): spec = importlib.util.spec_from_file_location(module_name, path) if spec is None or spec.loader is None: raise RuntimeError(f"Failed to load patch module spec from {path}") module = importlib.util.module_from_spec(spec) spec.loader.exec_module(module) return module # Load the nunchaku patch module once; reuse it for warning suppression and the # apply_rotary_emb compat shim. _patch_module = None try: _patch_module = _load_patch_module( "comfyui_qwenimageloraloader_nunchaku_patch_prestartup", _NUNCHAKU_PATCH_PATH, ) except Exception: logger.exception("ComfyUI-QwenImageLoraLoader prestartup: failed to load nunchaku patch module") # Install the cosmetic 'Torch already imported' warning filter first, before any # prestartup step imports comfy.ldm (which imports torch) and before main.py logs it. if _patch_module is not None: try: if _patch_module.suppress_torch_preimport_warning(): logger.debug( "ComfyUI-QwenImageLoraLoader prestartup: torch pre-import warning suppressed" ) except Exception: logger.exception( "ComfyUI-QwenImageLoraLoader prestartup: torch warning suppression failed" ) try: _docstring_patch_module = _load_patch_module( "comfyui_qwenimageloraloader_docstring_patch_prestartup", _DOCSTRING_PATCH_PATH, ) if _docstring_patch_module.apply_transformers_causal_lm_docstring_patch(): logger.info("ComfyUI-QwenImageLoraLoader prestartup: CausalLM ModelOutput docstring patch applied") else: logger.debug( "ComfyUI-QwenImageLoraLoader prestartup: CausalLM ModelOutput docstring patch not applied" ) except Exception: logger.exception("ComfyUI-QwenImageLoraLoader prestartup: CausalLM ModelOutput docstring patch failed") # ImageProcessorKwargs docstring patch (deepseek_vl_hybrid / kimi_k25 / paddleocr_vl # [ERROR] "but not documented" noise): wraps get_args_doc_from_source at prestartup, # before any custom node imports those transformers modules. try: _ip_kwargs_patch_module = _load_patch_module( "comfyui_qwenimageloraloader_image_processor_kwargs_patch_prestartup", _IP_KWARGS_PATCH_PATH, ) if _ip_kwargs_patch_module.apply_transformers_image_processor_kwargs_patch(): logger.info( "ComfyUI-QwenImageLoraLoader prestartup: ImageProcessorKwargs docstring patch applied" ) else: logger.debug( "ComfyUI-QwenImageLoraLoader prestartup: ImageProcessorKwargs docstring patch not applied" ) except Exception: logger.exception( "ComfyUI-QwenImageLoraLoader prestartup: ImageProcessorKwargs docstring patch failed" ) if _patch_module is not None: try: if _patch_module.apply_qwen_image_apply_rotary_emb_compat(): logger.info("ComfyUI-QwenImageLoraLoader prestartup: apply_rotary_emb compat applied") else: logger.debug( "ComfyUI-QwenImageLoraLoader prestartup: apply_rotary_emb compat not needed or already present" ) except Exception: logger.exception("ComfyUI-QwenImageLoraLoader prestartup: apply_rotary_emb compat failed")