Fold fixups into the change that owns them
tovio change absorb — what it operates on, how it attributes, and when it declines.
Written By Dustin
Last updated 28 minutes ago
tovio change absorb --dry-runtovio change absorbDistributes your current change — the tip commit of the lane you are on — into the earlier unlanded changes that own the files it fixes, then re-stacks the rest. Commit your fixups first: absorb reads the tip commit, not the working copy.
The problem it solves
You are working on a stack, review comes back on three changes at once, you fix all three and commit. Manually splitting those fixes back across the right changes is tedious and easy to get wrong. Absorb does the attribution for you.
How it attributes, most conservative first
- A file exactly one unlanded ancestor touched folds whole into that ancestor.
- A file several ancestors touched, whose fixup edit blames to exactly one of them, folds line-level — only that owned hunk is spliced into that ancestor.
- Everything else stays in your change. Absorb never guesses.
The stack it considers is the current lane's first-parent chain back to where it forked from main.
It only ever improves
A line-level splice can make the cascade conflict when the fix sits next to a later ancestor's edit. Absorb runs a trial cascade first and rolls back any path that would gain a conflict, leaving it in your change. So absorb never introduces a conflict you did not already have. Every change id is preserved, and the whole thing is one reversible undo.
Always dry-run first
tovio change absorb --dry-runPrints the post-rollback routing plan — which file would fold into which ancestor, and which stay — without advancing the lane.
When it declines
TVO-OP-016— nothing to absorb: every edit was new code, or spanned several ancestors, or there is no unlanded stack forked frommain, or this change already landed.TVO-CONFLICT-003— your fixup change itself carries unresolved conflicts. Resolve them first: distributing it would copy a conflict object into an ancestor.
A merge commit anywhere in the unlanded stack is refused too, for the same reason rebase and split refuse one.
Undo
tovio undo