Drag-resize on a long clip fires hundreds of state updates per second. Anything less than constant-time updates breaks playback smoothness. The naïve approach — nested arrays of tracks containing arrays of clips — cannot survive that.
We normalized everything. Tracks, clips, effects, and markers became id-keyed maps. Updates became pinpoint. Selectors became derived. Both playback and renderer started reading from the same selector layer, which closed the live-vs-export divergence gap by construction.
Pick the data shape before the framework
If your render and your preview disagree, the renderer is almost never the right place to fix it. Move the answer into shared state. The renderer is a consumer, not an authority.