Nodes/comfyui-cyclist/Loop Manager
ComfyUI Node

Loop Manager

The loop counter that keeps Cyclist workflows from overwriting themselves

By Pos13·Created 2 years ago·Updated 2 years ago· 33
Loop Manager
    • STRING
    loop_idForLoop_1
    incrementby_interrupt_node

    ComfyUI can't actually loop. The graph is a DAG - a node can't feed itself, and the engine flat-out refuses to run a workflow with a cycle in it. So how does a pack called Cyclist do loops? It cheats the queue. Each time you press Queue Prompt is one iteration; you save a result at the end of the run and load it back at the start of the next one. Loop Manager is the little node that makes that bookkeeping bearable.

    At heart it just hands you a string - the loop_id - that everything else in the pack keys off. Memorize/Recall use it as a variable name; the Override/Reload save nodes use it as a filename. Point five nodes at the same loop_id and they're all reading and writing the same slot. That's the whole idea, and on its own it sounds trivial. The reason the node exists is the increment behaviour.

    Why you'd reach for it

    Here's the problem it solves. You run a loop, it converges, you interrupt it. Now you want to start a fresh loop - but all your saved state (the memorized values, the ForLoop_1.png on disk) is still sitting there from the last run. If you just queue again, iteration one of your new loop reads the old loop's leftovers. Cyclist ships a "New Cycle" button for exactly this: it bumps every loop_id and filename widget so the next run starts clean. Loop Manager automates pressing that button.

    The two inputs that matter

    • loop_id (STRING, default ForLoop_1) - the name of this loop. If you run more than one loop in a graph, give each its own id so they don't stomp on each other.
    • increment (enum) - the actual brain of the node. Three settings:
      • never - the id never changes on its own; behaves like a plain string constant.
      • by_interrupt_node - when an Interrupt node fires (your stop condition was met), the id auto-advances so your finished result doesn't get clobbered by the next queued run.
      • on_any_interrupt - same as above, plus it advances when you manually cancel the queue. Handy for "skip the failures" workflows where you bail on a bad gen and want the next attempt to start fresh.

    The single output is a STRING - wire it into the loop_id/filename inputs of your Memorize, Recall, Override and Reload nodes.

    How to install it

    Two ways, same as the rest of Cyclist:

    • ComfyUI Manager - open the Manager, search comfyui-cyclist, install, restart.
    • Manually - cd ComfyUI/custom_nodes && git clone https://github.com/Pos13/comfyui-cyclist, then restart ComfyUI.

    No models, no pip wheels, no CUDA anything - it's pure Python glue.

    Things that'll trip you up

    Worth saying plainly: this pack is archived. The author put a note right at the top of the README that they're not maintaining it anymore, and it barely registers on the community radar - it's a clever niche tool, not a staple like rgthree or Impact Pack. It still works, but you're on your own if a ComfyUI update breaks something.

    Two gotchas specific to the increment feature. First, the "New Cycle" logic that Loop Manager rides on only rewrites loop_id and filename widgets, plus Primitive nodes wired into them - it will not touch a string coming out of a "String Const," "String Op," or "Recall String" node. If you're feeding your loop id through one of those, the auto-increment silently does nothing. Second, if you're using Auto Queue to run the loop hands-free, note that ComfyUI unchecks that box automatically whenever an interrupt fires, so a converged loop stops instead of instantly restarting the next one - you re-check it by hand each cycle. Slightly annoying, but it's a deliberate guard against runaway short-circuits.

    Categorycyclist

    Inputs (2)

    NameTypeDefaultDescription
    loop_idSTRINGForLoop_1
    incrementCOMBOby_interrupt_node3 options: never, by_interrupt_node, on_any_interrupt

    Outputs (1)

    NameTypeDescription
    STRINGSTRING