diff --git a/comfy_api/v3/helpers.py b/comfy_api/v3/helpers.py index 77a0aa898..019c725f4 100644 --- a/comfy_api/v3/helpers.py +++ b/comfy_api/v3/helpers.py @@ -5,7 +5,10 @@ def first_real_override(cls: type, name: str, *, base: type) -> Optional[Callabl """Return the *callable* override of `name` visible on `cls`, or None if every implementation up to (and including) `base` is the placeholder defined on `base`. """ - base_func = getattr(base, name).__func__ + base_attr = getattr(base, name, None) + if base_attr is None: + return None + base_func = base_attr.__func__ for c in cls.mro(): # NodeB, NodeA, ComfyNodeV3, object … if c is base: # reached the placeholder – we're done break diff --git a/comfy_api/v3/io.py b/comfy_api/v3/io.py index 60517c0a2..c2733bf14 100644 --- a/comfy_api/v3/io.py +++ b/comfy_api/v3/io.py @@ -1115,8 +1115,6 @@ class ComfyNodeV3: """Optionally, define this function to fingerprint inputs; equivalent to V1's IS_CHANGED.""" raise NotImplementedError - fingerprint_inputs = None - @classmethod def check_lazy_status(cls, **kwargs) -> list[str]: """Optionally, define this function to return a list of input names that should be evaluated. @@ -1133,8 +1131,6 @@ class ComfyNodeV3: """ return [name for name in kwargs if kwargs[name] is None] - check_lazy_status = None - @classmethod def GET_SERIALIZERS(cls) -> list[Serializer]: return [] diff --git a/execution.py b/execution.py index 844e34cee..bfddc0ada 100644 --- a/execution.py +++ b/execution.py @@ -54,7 +54,7 @@ class IsChangedCache: class_def = nodes.NODE_CLASS_MAPPINGS[class_type] has_is_changed = False is_changed_name = None - if issubclass(class_def, io.ComfyNodeV3) and getattr(class_def, "fingerprint_inputs", None) is not None: + if issubclass(class_def, io.ComfyNodeV3) and helpers.first_real_override(class_def, "fingerprint_inputs", base=io.ComfyNodeV3) is not None: has_is_changed = True is_changed_name = "fingerprint_inputs" elif hasattr(class_def, "IS_CHANGED"): @@ -411,7 +411,11 @@ def execute(server, dynprompt, caches, current_item, extra_data, executed, promp obj = class_def() caches.objects.set(unique_id, obj) - if getattr(obj, "check_lazy_status", None) is not None: + if issubclass(class_def, io.ComfyNodeV3): + lazy_status_present = helpers.first_real_override(class_def, "check_lazy_status", base=io.ComfyNodeV3) is not None + else: + lazy_status_present = getattr(obj, "check_lazy_status", None) is not None + if lazy_status_present: required_inputs = _map_node_over_list(obj, input_data_all, "check_lazy_status", allow_interrupt=True, hidden_inputs=hidden_inputs) required_inputs = set(sum([r for r in required_inputs if isinstance(r,list)], [])) required_inputs = [x for x in required_inputs if isinstance(x,str) and (