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

Intercept network resource requests / defining resource loader #1502

Open
SebJansen opened this issue Aug 7, 2024 · 13 comments
Open

Intercept network resource requests / defining resource loader #1502

SebJansen opened this issue Aug 7, 2024 · 13 comments
Labels
enhancement New feature or request

Comments

@SebJansen
Copy link

SebJansen commented Aug 7, 2024

Is your feature request related to a problem? Please describe.
JSDOM has the ability to define custom resource loaders, to avoid the need for network requests, by going through the filesystem instead. This saves precious milliseconds.

JSDOM resource loaders also have access to the requesting HTML element; eg if a style element is requesting a CSS file, the loader can get it from the filesystem instead and then replace the element with a <style> element with the CSS inlined to prevent the client needing to make an additional network request for the CSS file upon first page being served.

Describe the solution you'd like
Some way to intercept network requests and instead serve them from the filesystem. Perhaps this is already possible with HappyDOM but merely undocumented.

Describe alternatives you've considered
Overriding window.fetch requires some properties like browser frame, which are not exposed during eg new Window(). Perhaps with a little guidance it is possible to document a way to override fetch.

@SebJansen SebJansen added the enhancement New feature or request label Aug 7, 2024
@Doeke
Copy link

Doeke commented Aug 12, 2024

I've also just run into this issue, the code I need to test at some point adds a <link> tag to load a webfont which results in AbortErrors (in Fetch.onAsyncTaskManagerAbort) while running tests.

Edit: All I have found is the setting disableCSSFileLoading, but no way to intercept or mock it. This setting also annoyingly still prints errors to stdout (NotSupportedError) every time a CSS file is requested

@mariusrak
Copy link

Hi, i also very much need this. I do requests only inside my own server and do not need to go through network. So this intercepting fetch request would greatly increase performance and security.

@OlaviSau
Copy link

Hi :) We also would greatly appreciate this, again currently using patch-package to get around this.

@OlaviSau
Copy link

#1556 Just an example of something that could work.

@SebJansen
Copy link
Author

SebJansen commented Sep 27, 2024

Maybe it's simpler to build this feature if we see it as overriding (some part of) Happy's caching behavior, that is executed in addition to preexisting behavior, only if this 'Cache 'Interceptor' is defined during initialization

@SebJansen
Copy link
Author

#1556 Just an example of something that could work.

Looks like a clean and simple solution! :)

I hope capricorn86 see this so that he can steer us into a certain direction

There's the happy-dom-without-node package that might be polluted if we go a little crazy here with nodejs specific code

@OlaviSau
Copy link

@SebJansen I discussed it with a colleague and although file urls would work, the caching would be a bit tricky as files can change at any moment. It is probably wiser to implement a full interceptor instead.

@capricorn86
Copy link
Owner

Hi! 👋
I agree that something is needed, but I'm not sure what the best solution would be yet 😅 Another feature I would like is to make it possible to simulate a local web-server that is served from a "public" directory. It should also be easy to add transformers for resources loaded.

If you feel that this should be prioritized, I recommend adding a 👍 to the ticket. There are a lot of feature requests to sort between and the thumb indicate that several has voted for it.

@mariusrak
Copy link

Hi, I'm trying to replace JSDOM with happy-dom. I think, JSDOM solves this problem just right. You can define ResourceLoader in options an provide a class that implements fetch() method it should return Buffer with result. It would be nice if it would process not only buffer but also http.response, but that's just minor detail. Anyways, this mechanism works great for me, I implement custom simulation of a local server as you mention and it works together very well. What do you think about this approach?

@capricorn86
Copy link
Owner

@mariusrak I will have to look into it in more detail. I think that the downside of using a class is that it is not very declarative. It could be nice to be able to send in some settings with the rules. Perhaps both and easy and an advanced option can be supported.

@mariusrak
Copy link

@capricorn86 there are some stuff you cannot achieve by declarative approach and rules. I'm using JSDOM inside worker, I need to send custom message to main thread on fetch. Even if you made some config options for this particular case, somebody will for sure come up with something that is not implemented. Can we go for start with the imperative way and maybe later introduce some declarative API?

@OlaviSau
Copy link

@capricorn86 We also use happy-dom inside an worker and the interceptor (implemented using patch-package) is used to provide assets directly from the file system. To me - an user defined interceptor seems to be the best solution as only the user knows when the files are supposed to update, doing that with a declarative approach is hard to imagine, but I am looking forward to seeing / hearing your ideas :)

@SebJansen
Copy link
Author

@capricorn86 We also use happy-dom inside an worker and the interceptor (implemented using patch-package) is used to provide assets directly from the file system. To me - an user defined interceptor seems to be the best solution as only the user knows when the files are supposed to update, doing that with a declarative approach is hard to imagine, but I am looking forward to seeing / hearing your ideas :)

Agreed. I think something as trivial as authorization often requires complicated and special logic that is more suitable to an imperative flow.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

5 participants