Don't fire change events while traversing the
chain node graph, instead gather the events and
fire them after the traversal to avoid side effects
of the change events from modifying the chain graph.

fix #2031
fix #3197