From a42251cc29bd6e36c0955fcbd7d19e2f7f595321 Mon Sep 17 00:00:00 2001 From: Robin Malfait Date: Mon, 19 May 2025 16:41:40 +0200 Subject: [PATCH] Improve performance of upgrade tool (#18068) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This PR improves the performance of the upgrade tool due to a regression introduced by https://github.com/tailwindlabs/tailwindcss/pull/18057 Essentially, we had to make sure that we are not in `` tags because we don't want to migrate declarations in there such as `flex-shrink: 0;` The issue with this approach is that we checked _before_ the candidate if a `` tag after the candidate. We would basically do this check for every candidate that matches. Running this on our Tailwind UI codebase, this resulted in a bit of a slowdown: ```diff - Before: ~13s + After: ~5m 39s ``` ... quite the difference. This is because we have a snapshot file that contains ~650k lines of code. Looking for `` tags in a file that large is expensive, especially if we do it a lot. I ran some numbers and that file contains ~1.8 million candidates. Anyway, this PR fixes that by doing a few things: 1. We will compute the `` tag positions only once per file and cache it. This allows us to re-use this work for every candidate that needs it. 2. We track the positions, which means that we can simply check if a candidate's location is within any of 2 start and end tags. If so, we skip it. Running the numbers now gets us to: ```diff - Before: ~5m 39s + After: ~9s ``` Much better! --------- Co-authored-by: Jordan Pittman --- CHANGELOG.md | 2 +- .../codemods/template/is-safe-migration.ts | 53 +++++++++++++++---- 2 files changed, 45 insertions(+), 10 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f4ab2a1e5..a5fb9603d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,7 +9,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Fixed -- Upgrade: Do not migrate declarations that look like candidates in `` is present after the candidate - location.contents.slice(location.end).includes('') + location.contents.slice(location.end, location.end + 2)?.match(/^:\s/) ) { - return false + // Compute all `` tag +// - All `` +// - No nested `', offset) + if (endTag === -1) return ranges + offset = endTag + 1 + + ranges.push(startTag, endTag) + } +})