Re: [PATCH 1/1] delete multiple tags in a single transaction
From: Elijah Newren <hidden>
Date: 2019-08-08 18:15:38
On Wed, Aug 7, 2019 at 9:11 PM Phil Hord [off-list ref] wrote:
From: Phil Hord <redacted> 'git tag -d' accepts one or more tag refs to delete, but each deletion is done by calling `delete_ref` on each argv. This is painfully slow when removing from packed refs. Use delete_refs instead so all the removals can be done inside a single transaction with a single write.
Nice, thanks for working on this.
I have a repo with 24,000 tags, most of which are not useful to any developers. Having this many refs slows down many operations that would otherwise be very fast. Removing these tags when they've been accidentally fetched again takes about 30 minutes using delete_ref.
I also get really slow times on a repo with ~20,000 tags (though order ~3 minutes rather than ~30, probably due to having an SSD on this machine) -- but ONLY IF the refs are packed first (git pack-refs --all). If the refs are loose, it's relatively quick to delete a dozen thousand or so tags (order of a few seconds). It might be worth mentioning in the commit message that this only makes a significant difference in the case where the refs are packed.
git tag -l feature/* | xargs git tag -d Removing the same tags using delete_refs takes less than 5 seconds.
It appears this same bug also affects `git branch -d` when deleting lots of branches (or remote tracking branches) and they are all packed; could you apply the same fix there? In constrast, it appears that `git update-ref --stdin` is fast regardless of whether the refs are packed, e.g. git tag -l feature/* | sed -e 's%^%delete refs/tags/%' | git update-ref --stdin finishes quickly (order of a few seconds).