alesgenova / post-me

📩 Use web Workers and other Windows through a simple Promise API

Home Page:https://www.npmjs.com/package/post-me

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

handshake code expects global.window to exist

cmawhorter opened this issue · comments

Edit: that change prevents the error about an unsupported worker, but it looks like isWindow is used in many places. i'll just inject a global.

I based my tests on the ones here (but with mocha), and it fails because this code checks thisWindow against a global Window that doesn't exist for me:

post-me/src/handshake.ts

Lines 106 to 115 in 5763644

if (isWindow(thisWindow) && isWindow(otherWindow)) {
addMessageListener = makeWindowAddMessageListener(
thisWindow,
acceptedOrigin
);
}
if (isWindow(thisWindow) && !isWindow(otherWindow)) {
addMessageListener = makeWorkerAddMessageListener(otherWindow);
}

I'm guessing jest is doing something to inject the global. Otherwise I don't understand how the tests are passing.

It works if I change it to (like postMessage above). I have no idea if it's correct though:

    if (isWindow(thisWindow) && isWindow(otherWindow)) {
      addMessageListener = makeWindowAddMessageListener(
        thisWindow,
        acceptedOrigin
      );
    }
    else {
      addMessageListener = makeWorkerAddMessageListener(thisWindow); // maybe otherWindow?
    }

Hi,

I'm trying to understand the issue you're facing.

Is the problem happening when you are trying to run the existing tests with mocha?
Or is the problem happening when you're trying to establish a handshake with some type of worker I haven't yet tested it with (for example a service worker) in a real browser?

The handshake code is trying to be somewhat smart and determine whether we are dealing with a browser window or a worker (using the isWindow method), and adapting the logic accordingly. There can be quite some room for improvement there :)

Is the problem happening when you are trying to run the existing tests with mocha?

Yes, in mocha. I copied/refactored your tests to help get testing in my app off the ground. I'd guess this option is causing the global Window to be injected into the environment and if you remove it you'll see the issue.

It wasn't a big deal to work around. I just added (global as any).Window = { name: 'Window' }; to run before my tests and my tests are all running in mocha fine now.

As for the issue. For comparison, this code to determine postMessage has an else in case isWindow is false but the code to determine addMessageListener does not. So if the global doesn't exist it will not find an addMessageListener and incorrectly error saying the environment is unsupported.

But overall this is great. Love the types for events and methods. Super easy to get up and running.

I'm glad you're liking the library! And thank you for your recent PR!

I have been experimenting with a few new ideas today, and have opened a PR that among other things removes the isWindow method altogether, and delegates the distinction between worker and window outside of the handshake code.
This should make it easier to have the library work with any type of worker in the future, by adding new objects that implement the new Messenger interface.

Would you mind taking a look? #12

I took a look and I like it. However I'm not able to get it to work with my app and I don't know why.

Would you accept a PR to add debug? I know it's an ext dep but it's tree is small.

Also -- could I build out the demo a bit? Right now parent and child are sharing a domain and I think it may be masking some issues.

I would love to have better debug, but I'm not sure about adding a dependency that to the bundle.
How about having a default no-op debug function that is called in strategic places, which the consumer can override with a real debug function?

Regarding the window being on different domains: there were definitely some issues up until this PR which I didn't notice (accessing certain properties on the cross-origin window would be blocked by the browser). As of #12 at least the demo app works when the parent and children are on different origins (http://localhost:5000 and http://localhost:5001).

Of course you are more than welcome to extend the demo application, it can be really helpful to diagnose corner cases that wouldn't surface in the mock test environment!

I took a look and I like it. However I'm not able to get it to work with my app and I don't know why.

Forgot to mention, that PR slightly changed the API (docs in the README are updated), maybe that's causing your app to be broken?

no-op debug function that is called in strategic places, which the consumer can override

Perfect. Works for me.

works when the parent and children are on different origins (http://localhost:5000 and http://localhost:5001)

I guess I should run it before I open my big mouth. I just looked through the code and it looked like it was served from a single. Cool, perfect!

Forgot to mention, that PR slightly changed the API

I saw that and even manually applied that retry code when it didn't work, but still no luck. No errors or anything. I added some console.logs and the parent was sending messages but for some reason the handshake wasn't succeeding. 🤷

no-op debug function that is called in strategic places, which the consumer can override

Perfect. Works for me.

I have implemented a first version of the debugger here: #31
It's pretty much ready for merge, just need to update the documentation, but you can already see how to use it in the PR message. Let me know if this works for you.

I saw that and even manually applied that retry code when it didn't work, but still no luck. No errors or anything. I added some console.logs and the parent was sending messages but for some reason the handshake wasn't succeeding. shrug

Have you sorted this out? If you provide me with a minimal example maybe I can catch what the issue is.

After I ran into problems I tried a little bit to track down the issue without success. I'd forked prior to my PR and built out my app using the fork, and everything has been working.

Now that my app is done I probably won't be touching the postmessage component for a little while but I've opened an issue to switch away from our fork next time it's revisited, so I'll be back at some point in the future. Once the connection is established everything works flawlessly. Huge help, thanks!

The one thing -- even with my fork -- I've always had to set both parent and child origin to asterisk. I have no idea why. In my case it's ok because other auth is in place, but it's not ideal.

At any rate, feel free to close this issue since I think you addressed the problem. Thanks!

Thank you for the feedback, per your request I'll close this issue.

If in the future you want to get to the bottom of the cross-origin problem, feel free to open a new issue!