At commit dc58c10, OpenCut’s highest activity-weighted risk is concentrated in its timeline interaction layer and audio pipeline: useTimelineDragDrop carries a recent commit activity of 15.46 — meaning it is not merely complex but is being actively changed right now, making structural issues a live regression risk rather than a deferred cleanup item. Across 2,797 total functions, 123 are rated critical, and all five top hotspots sit in the ‘fire’ quadrant, where high structural complexity and high recent commit activity intersect. OpenCut is an open-source video editor; these functions sit at the core of its editing UX and media playback, which explains both the complexity and the pressure to keep changing them.
The table below ranks functions by activity-weighted risk — a score that multiplies structural complexity by recent commit frequency. A function that is both hard to understand (high cyclomatic complexity) and actively changing is a higher priority than one that is complex but untouched. CC = cyclomatic complexity (independent execution paths); ND = max nesting depth; FO = fan-out (distinct callees).
Top 5 Hotspots
| Function | File | Risk | CC | ND | FO |
|---|---|---|---|---|---|
useTimelineDragDrop | apps/web/src/hooks/timeline/use-timeline-drag-drop.ts | 16.6 | 15 | 5 | 42 |
runClipIterator | apps/web/src/core/managers/audio-manager.ts | 15.4 | 18 | 5 | 8 |
useElementInteraction | apps/web/src/hooks/timeline/element/use-element-interaction.ts | 15.1 | 18 | 3 | 37 |
parseTimeCode | apps/web/src/lib/time.ts | 15.1 | 53 | 3 | 5 |
collectAudioElements | apps/web/src/lib/media/audio.ts | 15.0 | 18 | 4 | 12 |
Hotspot Analysis
useTimelineDragDrop — apps/web/src/hooks/timeline/use-timeline-drag-drop.ts
Based on its name and location in the timeline hooks directory, this function almost certainly manages the drag-and-drop interaction model for the video editing timeline — one of the most state-intensive surfaces in any editor. Its fan-out of 42 is the highest in the dataset, meaning it calls 42 distinct functions and is broadly coupled to the rest of the application; a change here has an unusually wide blast radius. With CC 15, ND 5, and a recent commit activity of 15.46, the function is both structurally complex and actively changing — the detected god-function and deeply-nested patterns confirm it is accumulating responsibilities that belong elsewhere, and every new commit to it is made against a backdrop of 15 independent execution paths and 5 levels of nesting.
Recommendation: Before the next feature addition, write characterization tests that cover the major drag event paths (given CC 15, aim for at least 15 test cases), then extract discrete sub-hooks — for example, drop-target resolution, snap-to-grid logic, and ghost-element positioning — to reduce fan-out and isolate future change blast radius.
runClipIterator — apps/web/src/core/managers/audio-manager.ts
The name and location suggest this function iterates over audio clips within the audio manager — likely advancing playback state, handling clip boundaries, or scheduling audio segments frame by frame. Its CC of 18 means 18 independent execution paths through what is probably a tight media-clock loop, and its ND of 5 indicates deeply nested conditional logic that is hard to reason about in isolation. With an activity-weighted risk score of 15.38, this is the second most urgent function in the codebase — the complex_branching and exit_heavy patterns flag that many of those 18 paths terminate early, each one a gap where test coverage can silently lapse as the code evolves.
Recommendation: Map each of the 18 cyclomatic paths to an explicit test case before refactoring; then apply extract-method to pull early-exit guard clauses into named predicate functions, which will reduce nesting depth and make the branching structure visible at a glance.
useElementInteraction — apps/web/src/hooks/timeline/element/use-element-interaction.ts
Sitting one level deeper in the timeline hook hierarchy than useTimelineDragDrop, this function likely handles pointer and keyboard interactions scoped to individual timeline elements — clicks, drags, selections, and possibly resize handles. Its fan-out of 37 is almost as wide as useTimelineDragDrop’s 42, confirming it is a second god-function in the same subsystem, and with CC 18 it has 18 independent paths despite a relatively shallow ND of 3 — meaning the branching is wide rather than deeply nested. A recent commit activity of 14.0 confirms it is under active development, so its 18 exit paths (the exit_heavy pattern) represent 18 places where a change can introduce a regression that existing tests may not catch.
Recommendation: Audit the 37 fan-out callees to identify which belong to drag-drop concerns already handled by useTimelineDragDrop; consolidating overlapping responsibilities between these two hooks would reduce coupling in both functions simultaneously and is a higher-leverage move than line-level cleanup.
Patterns Found
Antipatterns detected across the top functions in this snapshot:
| Pattern | Occurrences |
|---|---|
exit_heavy | 5 |
long_function | 4 |
complex_branching | 3 |
god_function | 3 |
deeply_nested | 2 |
These labels belong to two tiers — Tier 1 (structural): complex_branching, deeply_nested, exit_heavy, long_function, god_function. Tier 2 (relational/temporal): hub_function, cyclic_hub, middle_man, neighbor_risk, stale_complex, churn_magnet, shotgun_target, volatile_god.
Key Takeaways
useTimelineDragDrophas a fan-out of 42 — the broadest coupling surface in the top hotspots — so any refactoring session should start by mapping its 42 callees and partitioning them into cohesive sub-hooks before touching any logic.parseTimeCodeinapps/web/src/lib/time.tshas a CC of 53 — more than three times higher than the next most complex hotspot — yet only 5 fan-out callees, making it an isolated but extreme branching risk; it is the single highest-priority candidate for a table-driven or regex-based rewrite to collapse its 53 paths.- All five critical functions share the exit_heavy pattern, meaning test suites must cover early-return branches explicitly; before any refactoring sprint, run a coverage report scoped to these five files and treat uncovered exit paths as blocking gaps.
Reproduce This Analysis
git clone https://github.com/OpenCut-app/OpenCut
cd OpenCut
git checkout dc58c10e64fae45f370b42494ebe0a74561a0c2d
hotspots analyze . --mode snapshot --explain-patterns --force
To run the same analysis on your own codebase, run hotspots analyze . --mode snapshot in any local git repo — no configuration required.
Hotspots highlights structural and activity risk — not “bad code.” Findings are a prioritization aid, not a bug predictor. Editorial policy →