Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: nested stylesheets should have absolute URLs #1533

Merged

Conversation

jeffdnguyen
Copy link
Contributor

hello 👋 - I identified an issue with nested stylesheets while looking into the asset manager PR.

The PR has a comment that outlines the problem in more detail

The tl;dr is that for style tags, we are assuming any URLs inside of a style tag must share the same file path as the document the style tag is on. This causes nested stylesheets (think style tag that imports another stylesheet) to have incorrect urls in the snapshot. In order to fix this, I decided the best route would be to determine those absolute paths sooner when stringifying the stylesheets.

Copy link

changeset-bot bot commented Jul 11, 2024

🦋 Changeset detected

Latest commit: acf1cb9

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 18 packages
Name Type
rrweb-snapshot Patch
rrweb Patch
rrdom Patch
rrdom-nodejs Patch
rrweb-player Patch
@rrweb/all Patch
@rrweb/replay Patch
@rrweb/record Patch
@rrweb/types Patch
@rrweb/packer Patch
@rrweb/web-extension Patch
rrvideo Patch
@rrweb/rrweb-plugin-console-record Patch
@rrweb/rrweb-plugin-console-replay Patch
@rrweb/rrweb-plugin-sequential-id-record Patch
@rrweb/rrweb-plugin-sequential-id-replay Patch
@rrweb/rrweb-plugin-canvas-webrtc-record Patch
@rrweb/rrweb-plugin-canvas-webrtc-replay Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@jeffdnguyen jeffdnguyen marked this pull request as ready for review July 11, 2024 22:48
@jeffdnguyen jeffdnguyen force-pushed the jn-correct-absolute-urls-for-nested-stylesheets branch 2 times, most recently from 7c329f9 to 8f6498d Compare July 16, 2024 02:21
@jeffdnguyen jeffdnguyen force-pushed the jn-correct-absolute-urls-for-nested-stylesheets branch from 88fbb74 to c6c0ee3 Compare July 16, 2024 02:31
Copy link
Contributor

@eoghanmurray eoghanmurray left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we just need to avoid the extra .map call as per my other comment; I can make the other changes at a later date.

@jeffdnguyen jeffdnguyen force-pushed the jn-correct-absolute-urls-for-nested-stylesheets branch from f26eacf to 27432e2 Compare July 16, 2024 16:51
@eoghanmurray
Copy link
Contributor

So something in 27432e2 has caused the test to fail; unfortunately they didn't run automatically after you pushed to the PR, not sure why

@eoghanmurray
Copy link
Contributor

eoghanmurray commented Jul 17, 2024

I've also got 3 commits in https://github.com/eoghanmurray/rrweb/tree/jn-correct-absolute-urls-for-nested-stylesheets that I'd like you to cherry-pick / pull in here first ... one of them adds a new test.
I'd need some sort of access credentials for pendo-io to be able to commit directly, not sure why that's not the case; maybe it's the 'allow access to maintainers' checkbox in your right hand column for this PR?

@jeffdnguyen
Copy link
Contributor Author

jeffdnguyen commented Jul 17, 2024

So something in 27432e2 has caused the test to fail; unfortunately they didn't run automatically after you pushed to the PR, not sure why

Good catch! I think I know why, moving the absolultifyURLs call into stringifyRule means I need to use the import rule's stylesheet's href and not the parent stylesheet href. Also need to call it not just after importStringified is populated in the case of a stylesheet with urls that wasn't imported (in this case use the parent href).

@jeffdnguyen
Copy link
Contributor Author

I've also got 3 commits in https://github.com/eoghanmurray/rrweb/tree/jn-correct-absolute-urls-for-nested-stylesheets that I'd like you to cherry-pick / pull in here first ... one of them adds a new test. I'd need some sort of access credentials for pendo-io to be able to commit directly, not sure why that's not the case; maybe it's the 'allow access to maintainers' checkbox in your right hand column for this PR?

Weird...I'm not seeing that checkbox but will look into that. In the meantime happy to cherry pick!

@eoghanmurray
Copy link
Contributor

Also I'm urging the rest of the core team to merge in the following soon:
#1437

I imagine there would be extensive conflicts with this one, so if you are at all going back to the drawing board, then we could keep the tests from this PR and build upon that first. If that's too much let's go ahead with this one and I'll handle the rebase on the other.

@jeffdnguyen
Copy link
Contributor Author

Update

  • Cherry picked your commits (thanks for making those!)
  • Handled that non import case
  • Clarified with the jpg names as you suggested

Copy link
Contributor

@eoghanmurray eoghanmurray left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just the moving of code out of the try/catch and I think we'll be good to merge

@jeffdnguyen
Copy link
Contributor Author

Made the change! 🤞

@eoghanmurray
Copy link
Contributor

I've made a few more changes on top, including playing around with a benchmark as I was worried about the now-per-rule calls to absolutifyURL (which turned out fine)

pendo-io/rrweb@jn-correct-absolute-urls-for-nested-stylesheets...eoghanmurray:rrweb:jn-correct-absolute-urls-for-nested-stylesheets

@jeffdnguyen
Copy link
Contributor Author

Cherry-picked your commits in. Nice job with deduping the fallback behavior, that feels much better! Glad the benchmark turned out fine, did not think to do that 😅

@jeffdnguyen
Copy link
Contributor Author

@eoghanmurray Please let me know if there is anything left I need to do to or can help with to get this merged 😄

@Juice10
Copy link
Contributor

Juice10 commented Jul 23, 2024

Can we use postcss instead of regex to replace/absolutify urls in the css? We've had a lot of issues with regular expressions not being the same as the spec and having some buggy edge cases. We've added postcss recently which should be much more stable.

@jeffdnguyen
Copy link
Contributor Author

Can we use postcss instead of regex to replace/absolutify urls in the css? We've had a lot of issues with regular expressions not being the same as the spec and having some buggy edge cases. We've added postcss recently which should be much more stable.

@Juice10 I love the idea! Would you be open to me opening a seperate/followup PR to explore that instead? Mainly since I wanted to keep the scope of this PR to changing when we try to absolutify and not the how/implementation of the function.

@eoghanmurray
Copy link
Contributor

eoghanmurray commented Jul 23, 2024

@Juice10 this PR is for the record side; postcss is used on the replay side, so big -1 from me for introducing postcss dependency for recording. We've been using the absoluteURLs regex for ages already (this doesn't change that) and nobody has reported any issues.

I did explore a couple of further commits on top of this PR which isolate the url regex replace to just the rule bit of the css (and not the selector bit). I had performance rather than correctness in mind with that, as after this PR we are applying the regex to each rule, rather than to the entire block of css. I figured this PR was complete enough so will introduce those changes properly in a new PR if this is accepted.

Side note: postcss could be made redundant at replay time if I complete #1480 successfully.

@Juice10
Copy link
Contributor

Juice10 commented Jul 25, 2024

@Juice10 this PR is for the record side; postcss is used on the replay side, so big -1 from me for introducing postcss dependency for recording. We've been using the absoluteURLs regex for ages already (this doesn't change that) and nobody has reported any issues.

Fair point @eoghanmurray! Merging this as is, thanks for contributing @jeffdnguyen

@Juice10 Juice10 merged commit d350da8 into rrweb-io:master Jul 25, 2024
6 checks passed
eoghanmurray added a commit to eoghanmurray/rrweb that referenced this pull request Jul 26, 2024
The prior 'dynamic stylesheet' route is now the main route for serializing a stylesheet; dynamic stylesheet were missed out in rrweb-io#1533 but are caught in this PR by the tests added in that PR as the stylesheet handling is simplified/centralised
eoghanmurray added a commit to eoghanmurray/rrweb that referenced this pull request Jul 26, 2024
The prior 'dynamic stylesheet' route is now the main route for serializing a stylesheet; dynamic stylesheet were missed out in rrweb-io#1533 but are caught in this PR by the tests added in that PR as the stylesheet handling is simplified/centralised
jeffdnguyen added a commit to pendo-io/rrweb that referenced this pull request Jul 29, 2024
* Replace relative URLs with absolute URLs when stringifying stylesheets

* Add test to show desired behavior for imported stylesheets from seperate directory

* Rename `absoluteToStylesheet` to `absolutifyURLs` and call it once after stringifying imported stylesheet

* Don't create the intermediary array of the spread operator

* Formalize that `stringifyRule` should expect a sheet href

* Ensure a <style> element can also import and gets it's url absolutized

* Handle case where non imported stylesheet has relative urls that need to be absolutified

* Clarify in test files where jpegs are expected to appear in absolutified urls

* Move absolutifyURLs call for import rules out of trycatch

* Add a benchmarking test for stringifyStylesheet

* Avoid the duplication on how to fall back

---------

Co-authored-by: Eoghan Murray <eoghan@getthere.ie>
Co-authored-by: eoghanmurray <eoghanmurray@users.noreply.github.com>
jeffdnguyen added a commit to pendo-io/rrweb that referenced this pull request Jul 29, 2024
* Replace relative URLs with absolute URLs when stringifying stylesheets

* Add test to show desired behavior for imported stylesheets from seperate directory

* Rename `absoluteToStylesheet` to `absolutifyURLs` and call it once after stringifying imported stylesheet

* Don't create the intermediary array of the spread operator

* Formalize that `stringifyRule` should expect a sheet href

* Ensure a <style> element can also import and gets it's url absolutized

* Handle case where non imported stylesheet has relative urls that need to be absolutified

* Clarify in test files where jpegs are expected to appear in absolutified urls

* Move absolutifyURLs call for import rules out of trycatch

* Add a benchmarking test for stringifyStylesheet

* Avoid the duplication on how to fall back

---------

Co-authored-by: Eoghan Murray <eoghan@getthere.ie>
Co-authored-by: eoghanmurray <eoghanmurray@users.noreply.github.com>
eoghanmurray added a commit to eoghanmurray/rrweb that referenced this pull request Aug 2, 2024
The prior 'dynamic stylesheet' route is now the main route for serializing a stylesheet; dynamic stylesheet were missed out in rrweb-io#1533 but are caught in this PR by the tests added in that PR as the stylesheet handling is simplified/centralised
eoghanmurray added a commit that referenced this pull request Aug 6, 2024
Support a contrived/rare case where a <style> element has multiple text node children (this is usually only possible to recreate via javascript append) ... this PR fixes cases where there are subsequent text mutations to these nodes; previously these would have been lost

* In this scenario, a new CSS comment may now be inserted into the captured `_cssText` for a <style> element to show where it should be broken up into text elements upon replay: `/* rr_split */`
* The new 'can record and replay style mutations' test is the principal way to the problematic scenarios, and is a detailed 'catch-all' test with many checks to cover most of the ways things can fail
* There are new tests for splitting/rebuilding the css using the rr_split marker
* The prior 'dynamic stylesheet' route is now the main route for serializing a stylesheet; dynamic stylesheet were missed out in #1533 but that case is now covered with this PR

This PR was originally extracted from #1475 so the  initial motivation was to change the approach on stringifying <style> elements to do so in a single place.  This is also the motivating factor for always serializing <style> elements via the `_cssText` attribute rather than in it's childNodes; in #1475 we will be delaying populating `_cssText` for performance and instead recorrding them as assets.

Thanks for the detailed review to  Justin Halsall <Juice10@users.noreply.github.com> & Yun Feng <https://github.com/YunFeng0817>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants