htmx icon indicating copy to clipboard operation
htmx copied to clipboard

v1.9.x: massive performance degradation on big pages

Open David-Guillot opened this issue 1 year ago • 10 comments

Hi there,

After upgrading htmx from 1.8.x to 1.9.x we experienced some major performance issues on big pages performing many htmx requests.

Firefox Profiler showed me the culprit: this line. Nothing surprising here: our page is quite big, and it's background-loading some new stuff quite often. At the end of each AJAX request, at htmx-settle time, an XPATH query is run against the whole DOM to find some hx-on elements (we don't use this feature, we have no hx-on on this page).

David-Guillot avatar Nov 21 '23 11:11 David-Guillot

since you mentioned hx-on: did you mean this line? https://github.com/bigskysoftware/htmx/blob/v1.9.0/src/htmx.js#L1887

function processHxOn(elt) {
    var hxOnValue = getAttributeValue(elt, 'hx-on');

hastebrot avatar Nov 21 '23 21:11 hastebrot

Ah sorry I forgot to target a tag, thanks @hastebrot for pointing that out. No it's that one, introduced in v1.9.3. It performs a wild XPATH query.

David-Guillot avatar Nov 21 '23 22:11 David-Guillot

Performance got back to normal (i.e. great) after rollback to v1.9.2.

David-Guillot avatar Nov 21 '23 22:11 David-Guillot

@David-Guillot Would you mind linking with a permalink? The link you have now is to an empty line, presumably because that line number is something different in the current master branch.

EDIT: got it

alexpetros avatar Nov 27 '23 15:11 alexpetros

Shouldn't the xpath expression that looks for the hx-on be prefixed with a period (.)?

To quote from the documentation of document.evaluate:

Further optimization can be achieved by careful use of the context parameter. For example, if you know the content you are looking for is somewhere inside the body tag, you can use this:

document.evaluate(".//h2", document.body, null, XPathResult.ANY_TYPE, null);

Notice in the above document.body has been used as the context instead of document so the xpath starts from the body element. (In this example, the "." is important to indicate that the querying should start from the context node, document.body. If the "." was left out (leaving //h2) the query would start from the root node (html) which would be more wasteful.)

In HTMX's source, I think elt is meant to be the starting point of the query, but because the period is missing, the entire document is searched instead.

By the way, the fallback code that emulates document.evaluate if that function is not available also scans the entire document, it does nothing with the given elt parameter.

svenberkvens avatar Nov 28 '23 21:11 svenberkvens

Hey @David-Guillot I am looking at this perf issue now

1cg avatar Nov 30 '23 21:11 1cg

Hey @David-Guillot we have a pr from @Telroshan w/ a fix for this:

https://github.com/bigskysoftware/htmx/pull/2060

it looks good to me so I'm going to integrate in into dev as part of 1.9.10. Would you be willing to try out a pre-release version to verify that it addresses your perf issues?

1cg avatar Nov 30 '23 21:11 1cg

I guess it's already available here [1] for testing.

[1] https://cdn.jsdelivr.net/gh/bigskysoftware/htmx@dev/src/htmx.js

hastebrot avatar Dec 01 '23 04:12 hastebrot

Hey @1cg , yes I can confirm the dev version fixes the issue! Thanks @Telroshan for the fix :clap: . This issue can be closed as soon as #2060 is part of a release :+1:

David-Guillot avatar Dec 01 '23 08:12 David-Guillot

@David-Guillot can you test against the current dev branch again? We added the ability to use only dashes (JSX doesn't like colons) and made the query slightly more complicated. I want to make sure it doesn't affect you again.

1cg avatar Dec 15 '23 18:12 1cg

Hi there,

I can confirm that v1.9.10 is still blazing fast :zap:

Closing this :tada:

David-Guillot avatar Jan 08 '24 14:01 David-Guillot