mirror of
https://github.com/comfyanonymous/ComfyUI.git
synced 2026-03-15 06:07:33 +08:00
fix: gate provider lookups to outputs cache and fix UI coercion
- Add `enable_providers` flag to BasicCache so only the outputs cache
triggers external provider lookups/stores. The objects cache stores
node class instances, not CacheEntry values, so provider calls were
wasted round-trips that always missed.
- Remove `or {}` coercion on `result.ui` — an empty dict passes the
`is not None` gate in execution.py and causes KeyError when the
history builder indexes `["output"]` and `["meta"]`. Preserving
`None` correctly skips the ui_node_outputs addition.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
e6bb7f03dd
commit
fa24f4ee60
@ -148,9 +148,10 @@ class CacheKeySetInputSignature(CacheKeySet):
|
|||||||
self.get_ordered_ancestry_internal(dynprompt, ancestor_id, ancestors, order_mapping)
|
self.get_ordered_ancestry_internal(dynprompt, ancestor_id, ancestors, order_mapping)
|
||||||
|
|
||||||
class BasicCache:
|
class BasicCache:
|
||||||
def __init__(self, key_class):
|
def __init__(self, key_class, enable_providers=False):
|
||||||
self.key_class = key_class
|
self.key_class = key_class
|
||||||
self.initialized = False
|
self.initialized = False
|
||||||
|
self.enable_providers = enable_providers
|
||||||
self.dynprompt: DynamicPrompt
|
self.dynprompt: DynamicPrompt
|
||||||
self.cache_key_set: CacheKeySet
|
self.cache_key_set: CacheKeySet
|
||||||
self.cache = {}
|
self.cache = {}
|
||||||
@ -239,6 +240,8 @@ class BasicCache:
|
|||||||
CacheValue, _contains_self_unequal, _logger
|
CacheValue, _contains_self_unequal, _logger
|
||||||
)
|
)
|
||||||
|
|
||||||
|
if not self.enable_providers:
|
||||||
|
return
|
||||||
if not _has_cache_providers():
|
if not _has_cache_providers():
|
||||||
return
|
return
|
||||||
if not self._is_external_cacheable_value(value):
|
if not self._is_external_cacheable_value(value):
|
||||||
@ -274,6 +277,8 @@ class BasicCache:
|
|||||||
CacheValue, _contains_self_unequal, _logger
|
CacheValue, _contains_self_unequal, _logger
|
||||||
)
|
)
|
||||||
|
|
||||||
|
if not self.enable_providers:
|
||||||
|
return None
|
||||||
if not _has_cache_providers():
|
if not _has_cache_providers():
|
||||||
return None
|
return None
|
||||||
if _contains_self_unequal(cache_key):
|
if _contains_self_unequal(cache_key):
|
||||||
@ -296,7 +301,7 @@ class BasicCache:
|
|||||||
_logger.warning(f"Provider {provider.__class__.__name__} returned invalid outputs")
|
_logger.warning(f"Provider {provider.__class__.__name__} returned invalid outputs")
|
||||||
continue
|
continue
|
||||||
from execution import CacheEntry
|
from execution import CacheEntry
|
||||||
return CacheEntry(ui=result.ui or {}, outputs=list(result.outputs))
|
return CacheEntry(ui=result.ui, outputs=list(result.outputs))
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
_logger.warning(f"Cache provider {provider.__class__.__name__} error on lookup: {e}")
|
_logger.warning(f"Cache provider {provider.__class__.__name__} error on lookup: {e}")
|
||||||
|
|
||||||
@ -354,8 +359,8 @@ class BasicCache:
|
|||||||
return result
|
return result
|
||||||
|
|
||||||
class HierarchicalCache(BasicCache):
|
class HierarchicalCache(BasicCache):
|
||||||
def __init__(self, key_class):
|
def __init__(self, key_class, enable_providers=False):
|
||||||
super().__init__(key_class)
|
super().__init__(key_class, enable_providers=enable_providers)
|
||||||
|
|
||||||
def _get_cache_for(self, node_id):
|
def _get_cache_for(self, node_id):
|
||||||
assert self.dynprompt is not None
|
assert self.dynprompt is not None
|
||||||
@ -432,8 +437,8 @@ class NullCache:
|
|||||||
return self
|
return self
|
||||||
|
|
||||||
class LRUCache(BasicCache):
|
class LRUCache(BasicCache):
|
||||||
def __init__(self, key_class, max_size=100):
|
def __init__(self, key_class, max_size=100, enable_providers=False):
|
||||||
super().__init__(key_class)
|
super().__init__(key_class, enable_providers=enable_providers)
|
||||||
self.max_size = max_size
|
self.max_size = max_size
|
||||||
self.min_generation = 0
|
self.min_generation = 0
|
||||||
self.generation = 0
|
self.generation = 0
|
||||||
@ -501,8 +506,8 @@ RAM_CACHE_OLD_WORKFLOW_OOM_MULTIPLIER = 1.3
|
|||||||
|
|
||||||
class RAMPressureCache(LRUCache):
|
class RAMPressureCache(LRUCache):
|
||||||
|
|
||||||
def __init__(self, key_class):
|
def __init__(self, key_class, enable_providers=False):
|
||||||
super().__init__(key_class, 0)
|
super().__init__(key_class, 0, enable_providers=enable_providers)
|
||||||
self.timestamps = {}
|
self.timestamps = {}
|
||||||
|
|
||||||
def clean_unused(self):
|
def clean_unused(self):
|
||||||
|
|||||||
@ -127,15 +127,15 @@ class CacheSet:
|
|||||||
|
|
||||||
# Performs like the old cache -- dump data ASAP
|
# Performs like the old cache -- dump data ASAP
|
||||||
def init_classic_cache(self):
|
def init_classic_cache(self):
|
||||||
self.outputs = HierarchicalCache(CacheKeySetInputSignature)
|
self.outputs = HierarchicalCache(CacheKeySetInputSignature, enable_providers=True)
|
||||||
self.objects = HierarchicalCache(CacheKeySetID)
|
self.objects = HierarchicalCache(CacheKeySetID)
|
||||||
|
|
||||||
def init_lru_cache(self, cache_size):
|
def init_lru_cache(self, cache_size):
|
||||||
self.outputs = LRUCache(CacheKeySetInputSignature, max_size=cache_size)
|
self.outputs = LRUCache(CacheKeySetInputSignature, max_size=cache_size, enable_providers=True)
|
||||||
self.objects = HierarchicalCache(CacheKeySetID)
|
self.objects = HierarchicalCache(CacheKeySetID)
|
||||||
|
|
||||||
def init_ram_cache(self, min_headroom):
|
def init_ram_cache(self, min_headroom):
|
||||||
self.outputs = RAMPressureCache(CacheKeySetInputSignature)
|
self.outputs = RAMPressureCache(CacheKeySetInputSignature, enable_providers=True)
|
||||||
self.objects = HierarchicalCache(CacheKeySetID)
|
self.objects = HierarchicalCache(CacheKeySetID)
|
||||||
|
|
||||||
def init_null_cache(self):
|
def init_null_cache(self):
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user